This site is updated infrequently. For up-to-date information, please visit the new OCaml website at ocaml.org.

Disabling the OCaml garbage collector
[ Home ] [ Index: by date | by threads ]
[ Search: ]

[ Message by date: previous | next ] [ Message in thread: previous | next ] [ Thread: previous | next ]
 Date: 2007-12-04 (20:14) From: Raj Bandyopadhyay Subject: Re: [Caml-list] Disabling the OCaml garbage collector
```Dear all,

As a followup to this discussion, I have been trying to understand
the OCaml/C interface better. Here's a very small program that I've
been trying to get to work. It's a mutually recursive function, one
part in C and the other in OCaml.

(* (* Implement this in C *)
let factC g n = if n=0 then [] else ("C",n)::(g (n-1));;
*)

external factC: (int ->(string * int) list) -> int -> ((string * int)
list)= "caml_factC"
let factO g n = if n=0 then [] else ("OCaml",n)::(g (n-1));;
let rec fact n = factO (factC fact) n;;

fact 12000;;

The C function corresponding to factC is quite short, however the
program crashes for values of n > about 11,000. I have tried
inserting the code to register global roots (currently commented
out), however, that makes no difference to the point of crash. I was
just wondering if there is some really obvious step that I am
missing, or using the wrong allocation function in Caml or something
like that. Any suggestions would be welcome. I apologize in advice
for inflicting code on you all, but I am out of ideas right now :(

/*
let factC g n =
if n=0 then
[]
else
("C",n)::(g (n-1))
*/
value caml_factC(value g,value n){
CAMLparam2(g,n);
CAMLlocal3(e,l,new_l);

//C value for n
int locn = Int_val(n);

//2 cases
if (locn <= 0){
CAMLreturn(Val_int(0)); //empty list
}
else {
e = alloc_tuple(2);  //allocate a new list element
("C",n)
Store_field(e,0,copy_string("C"));
Store_field(e,1,n);

//callback the closure g
if(Tag_val(g) == Closure_tag) {
//PROGRAM CRASHES HERE for large n and never returns from callback
l = callback(g,Val_int(locn-1));
} else {
exit(1);
}
//cons this tuple to the list obtained by callback
new_l = alloc(2,0); //structured list value, tag is 0
Store_field(new_l,0,e);
Store_field(new_l,1,l);

//now we should register e,l and new_l with the GC
//The program crashes at the same point (n>11000) regdless of
whether the following
//code is commented out or not.
/*
Vstore *roots = (Vstore *)caml_stat_alloc(sizeof
(Vstore));
roots->v1 = e;
roots->v2 = l;
roots->v3 = new_l;
caml_register_global_root(&roots->v1);
caml_register_global_root(&roots->v2);
caml_register_global_root(&roots->v3);
CAMLreturn(roots->v3); //newly constructed list
*/

CAMLreturn(new_l); //newly constructed list
}
}

Thanks!
Raj

```