[Caml-list] Change of behaviour of ocaml -make-runtime with 3.11.0
1. With OCaml 3.11.0, if I write ocamlc.opt -o myrun -make_runtime unix.cma ocamlc.opt -o essai -use_runtime myrun unix.cma essai.ml (with essai.ml: let x = Unix.time() in Format.printf "Here1 %...@." x;;) and then ./essai I get the following error message: Fatal error: cannot load shared library dllunix Reason: /usr/local/lib/ocaml/stublibs/dllunix.so: undefined symbol: caml_copy_int64 2. Until version 3.10.2, it was OK 3. I understandd that now, it is not necessary to use a custom runtime, as ocamlrun can load dynamically dllunix.so (in that case, ./essai works OK). However, I would like that my Makefiles remain compatible with recent versions of OCaml. Bertrand Jeannet ___ Caml-list mailing list. Subscription management: http://yquem.inria.fr/cgi-bin/mailman/listinfo/caml-list Archives: http://caml.inria.fr Beginner's list: http://groups.yahoo.com/group/ocaml_beginners Bug reports: http://caml.inria.fr/bin/caml-bugs
[Caml-list] printf "%a" vs sprintf "%a"
For people that do not use OCaml batteries, a sprintf function similar to (Printf|Format).printf can be defined using kfprintf: let sprintf format = let buffer = Buffer.create 512 in let fmt = Format.formatter_of_buffer buffer in Format.kfprintf (begin fun fmt -> Format.pp_print_flush fmt (); let s = Buffer.contents buffer in Buffer.clear buffer; s end) fmt format The types are different: Format.fprintf : Format.formatter -> ('a, Format.formatter, unit, unit) format4 -> 'a val sprintf : ('a, Format.formatter, unit, string) format4 -> 'a = but that is normal, as sprintf should return a string. Bertrand Jeannet ___ Caml-list mailing list. Subscription management: http://yquem.inria.fr/cgi-bin/mailman/listinfo/caml-list Archives: http://caml.inria.fr Beginner's list: http://groups.yahoo.com/group/ocaml_beginners Bug reports: http://caml.inria.fr/bin/caml-bugs
[Caml-list] Re: Optimizing Float Ref's (Yaron Minsky)
The problem may not only be unboxing, but also allocation. In your first code, you allocate two new cells each time you enter in the j-loop (one for the boxed float, and one for the reference cell "sum" pointing to it). You should first move the line "let sum = ref 0.0" before the i-loop and just write at the same place "sum := 0". I will not be as efficient as your second version (because you still have boxing), but it should still be much better. Bertrand On Aug 28, 2009, at 4:32 PM, Will M Farr wrote: Hello all, I'm running OCaml 3.11.1, and I noticed something strange in some native code for matrix multiply today. The code was let mmmul store m1 m2 = let (ni,nk) = dims m1 and (nk2,nj) = dims m2 and (sni,snj) = dims store in assert(nk=nk2); assert(ni=sni); assert(nj=snj); for i = 0 to ni - 1 do let row1 = m1.(i) and srow = store.(i) in for j = 0 to nj - 1 do let sum = ref 0.0 in (* Un-boxed float ref? *) for k = 0 to nk - 1 do let row2 = Array.unsafe_get m2 k in let x = Array.unsafe_get row1 k and y = Array.unsafe_get row2 j in sum := !sum +. x*.y done; Array.unsafe_set srow j !sum done done; store (I compiled with ocamlopt.) It multiplies the matrices (represented as arrays of arrays of floats) m1 and m2 together and puts the result into the matrix store. Profiling the code, I noticed a call to caml_modify during the execution of this function! Turns out that the culprit was the float ref "sum". Changing to the following code (which eliminates the float ref, and uses the <- and .( ) operators instead of unsafe_set and unsafe_get) eliminated that call, and sped things up tremendously: let mmmul store m1 m2 = let (ni,nk) = dims m1 and (nk2,nj) = dims m2 in for i = 0 to ni - 1 do let row1 = m1.(i) and srow = store.(i) in for j = 0 to nj - 1 do srow.(j) <- 0.0; for k = 0 to nk - 1 do let row2 = Array.unsafe_get m2 k in let x = row1.(k) and y = row2.(j) in srow.(j) <- srow.(j) +. x*.y done done done; store But, I thought that float ref's were automatically unboxed by the compiler when they didn't escape the local context. Is this a complier bug, is there a bad interaction with unsafe_get and unsafe_set, or is there something else going on that I don't understand? Any enlightenment would be appreciated. Thanks! Will ___ Caml-list mailing list. Subscription management: http://yquem.inria.fr/cgi-bin/mailman/listinfo/caml-list Archives: http://caml.inria.fr Beginner's list: http://groups.yahoo.com/group/ocaml_beginners Bug reports: http://caml.inria.fr/bin/caml-bugs ___ Caml-list mailing list. Subscription management: http://yquem.inria.fr/cgi-bin/mailman/listinfo/caml-list Archives: http://caml.inria.fr Beginner's list: http://groups.yahoo.com/group/ocaml_beginners Bug reports: http://caml.inria.fr/bin/caml-bugs -- Projet POP-ART, INRIA Rhône-Alpes Zirst - 655 avenue de l'Europe - Montbonnot F-38334 Saint Ismier Cedex Fax: +33 (0)4 76 61 52 52 Tel: +33 (0)4 76 61 52 76 bertrand.jean...@inrialpes.fr ___ Caml-list mailing list. Subscription management: http://yquem.inria.fr/cgi-bin/mailman/listinfo/caml-list Archives: http://caml.inria.fr Beginner's list: http://groups.yahoo.com/group/ocaml_beginners Bug reports: http://caml.inria.fr/bin/caml-bugs
[Caml-list] Re: Ocamldoc and multiple packages
Subject: [Caml-list] Ocamldoc and multiple packages From: Alexey Rodriguez Date: Fri, 11 Sep 2009 17:47:09 +0200 To: OCaml List To: OCaml List Dear list, I am trying to build ocamldoc documentation for an ocaml project that contains multiple packages (collections of modules built using -for-pack and -pack). My current setup generates documentation for each package but it won't generate hyperlinks to modules in other packages (module not found errors). I tried using the -load and -dump commands to allow ocamldoc see the ocamldoc-results of the referred to package, but I still get problems. I suspect that the problem arises because ocamldoc does not have a -pack option, so it always sees modules in a flat way. So if you have package Pack1 with module A, and module B in Pack2 which refers to Pack1.A.t, ocamldoc cannot solve this reference because it does not know that module A is inside another module called Pack1. The solutions I see right now seem to involve more effort than I am willing to spend. So, before I embark on a task that might take too long I would like to ask for tips on this. How do you perform ocamldoc generation for projects with multiple packages? Thanks! Cheers, Alexey I wrote very recently a small script that packs source modules into a big module, and takes care of ocamldoc convention, which is to interpret in each file the first (** *) comment as the title associated to the module. I am very bad at sh and gawk script, so the result (given below) is not very elegant... It would of course be better (and much more robust) to have a direct support in ocamldoc. Bertrand --- #/bin/sh # command line (very primitive...) if test $1 != "-o"; then echo "ocamlpack: usage: ocamlpack -o outputmodule -title module1 module2 ..." exit -1 fi shift out=$1 shift if test $1 != "-title"; then echo "ocamlpack: usage: ocamlpack -o outputmodule -title module1 module2 ..." exit -1 fi shift outtitle=$1 shift # prepare output /bin/rm -f $out.ml $out.mli echo "(** $outtitle *)">$out.ml echo "(** $outtitle *)">$out.mli # iterate on input module, for i in $*; do name=$i # 1.A Look for the first (** *) comment, and output it to out.ml # (see ocamldoc convention) gawk -v name=$name ' BEGIN { start=1 # isolate module name from path/modulename nb = split(name, dirname, "/") name = dirname[nb] if (RLENGTH>0) name = substr(name,RINDEX,length(name)-RINDEX) # Capitalize the module name hd = toupper(substr(name,1,1)) tl = substr(name,2,length(name)-1) } # Look for the first (** *) comment, and output it { if (start==1) { match($0, /\(\*\*([ ]+)([^*]*)([ ]+)\*\)/ ) if (RLENGTH>0){ start=0 title=substr($0,RSTART+4,RLENGTH-7) print "\n(** {1 Module [",hd tl "]:",title "} *)\n" print "module",hd tl,"= struct" } } } END { if (start==1) { print "\n(** {1 Module [",hd tl "]} *)\n" print "module",hd tl,"= struct" } } ' $i.ml >>$out.ml # 1.B Output the rest of name.ml to out.ml gawk -v name=$name ' { if (start==1) { match($0, /\(\*\*([ ]+)([^*]*)([ ]+)\*\)/ ) if (RLENGTH>0) start=0 else print $0 } else print " ",$0 } END { print "end\n" } ' $i.ml >>$out.ml # 2.A Look for the first (** *) comment, and output it to out.mli gawk -v name=$name ' BEGIN { start=1 nb = split(name, dirname, "/") name = dirname[nb] if (RLENGTH>0) name = substr(name,RINDEX,length(name)-RINDEX) hd = toupper(substr(name,1,1)) tl = substr(name,2,length(name)-1) } { if (start==1) { match($0, /\(\*\*([ ]+)([^*]*)([ ]+)\*\)/ ) if (RLENGTH>0){ start=0 title=substr($0,RSTART+4,RLENGTH-7) print "\n(** {1 Module [",hd tl "]:",title "} *)\n" print "module",hd tl,": sig" } } } END { if (start==1) { print "\n(** {1 Module [",hd tl "]} *)\n" print "module",hd tl,": sig" } } ' $i.mli >>$out.mli # 2.B Output the rest of name.mli to out.mli gawk -v name=$name ' { if (start==1) { match($0, /\(\*\*([ ]+)([^*]*)([ ]+)\*\)/ ) if (RLENGTH>0) start=0 else print $0 } else print " ",$0 } END { print "end\n" } ' $i.mli >>$out.mli done ___ Caml-list mailing list. Subscription management: http://yquem.inria.fr/cgi-bin/mailman/listinfo/caml-list Archives: http://caml.inria.fr Beginner's list: http://groups.yahoo.com/group/ocaml_beginners Bug reports: http://caml.inria.fr/bin/caml-bugs