From: Christophe Raffalli <christophe.raffalli@univ-savoie.fr>
To: caml-list@yquem.inria.fr
Subject: Re: [Caml-list] Re: Is OCaml fast?
Date: Wed, 24 Nov 2010 18:57:17 +0100 [thread overview]
Message-ID: <4CED51FD.6020305@univ-savoie.fr> (raw)
In-Reply-To: <loom.20101124T181441-844@post.gmane.org>
[-- Attachment #1.1: Type: text/plain, Size: 3043 bytes --]
Hello,
Here is a test of gctweak.ml on the "now famous" binary-tree shootout bench ...
As you can see it is a 30% speed up which is not too bad, just adding
a file on the compilation command line !
I reattached the file, because I correct a few comments in it ... and a syntax error
that is only visible when not using camlp4 in ocaml-3.11.2 ( { get () with ... } is
valid with camlp4 and invalid without ???) ... Anyway, more work on Gctweak is still needed ...
raffalli@d45-lama:~/Caml$ ocamlopt -o binary_tree gctweak.ml binary_tree.ml ; time ./binary_tree 20
stretch tree of depth 21 check: -1
2097152 trees of depth 4 check: -2097152
524288 trees of depth 6 check: -524288
131072 trees of depth 8 check: -131072
32768 trees of depth 10 check: -32768
8192 trees of depth 12 check: -8192
2048 trees of depth 14 check: -2048
512 trees of depth 16 check: -512
128 trees of depth 18 check: -128
32 trees of depth 20 check: -32
long lived tree of depth 20 check: -1
real 0m19.212s
user 0m18.960s
sys 0m0.180s
raffalli@d45-lama:~/Caml$ ocamlopt -o binary_tree binary_tree.ml ; time ./binary_tree 20
stretch tree of depth 21 check: -1
2097152 trees of depth 4 check: -2097152
524288 trees of depth 6 check: -524288
131072 trees of depth 8 check: -131072
32768 trees of depth 10 check: -32768
8192 trees of depth 12 check: -8192
2048 trees of depth 14 check: -2048
512 trees of depth 16 check: -512
128 trees of depth 18 check: -128
32 trees of depth 20 check: -32
long lived tree of depth 20 check: -1
real 0m27.484s
user 0m27.270s
sys 0m0.110s
Here is the run with debug := 1 and you see that minor heap size is guessed at
524288, with almost no promoted word (model = 1 means no promoted word)
raffalli@d45-lama:~/Caml$ ocamlopt -o binary_tree gctweak.ml binary_tree.ml ; time ./binary_tree 20
MHS DOUBLED <- 65536 (model 3.996155)
MHS DOUBLED <- 131072 (model 3.000397)
stretch tree of depth 21 check: -1
MHS DOUBLED <- 262144 (model 2.495375)
MHS DOUBLED <- 524288 (model 1.027698)
2097152 trees of depth 4 check: -2097152
524288 trees of depth 6 check: -524288
131072 trees of depth 8 check: -131072
32768 trees of depth 10 check: -32768
8192 trees of depth 12 check: -8192
2048 trees of depth 14 check: -2048
512 trees of depth 16 check: -512
128 trees of depth 18 check: -128
32 trees of depth 20 check: -32
long lived tree of depth 20 check: -1
real 0m19.342s
user 0m19.100s
sys 0m0.170s
--
Christophe Raffalli
Universite de Savoie
Batiment Le Chablais, bureau 21
73376 Le Bourget-du-Lac Cedex
tel: (33) 4 79 75 81 03
fax: (33) 4 79 75 87 42
mail: Christophe.Raffalli@univ-savoie.fr
www: http://www.lama.univ-savoie.fr/~RAFFALLI
---------------------------------------------
IMPORTANT: this mail is signed using PGP/MIME
At least Enigmail/Mozilla, mutt or evolution
can check this signature. The public key is
stored on www.keyserver.net
---------------------------------------------
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.2: gctweak.ml --]
[-- Type: text/x-ocaml; name="gctweak.ml", Size: 6155 bytes --]
open Gc
(* adjustable parameters, should be a functor ? *)
let space_overhead = 100
let gamma = 3.0 (* time in major slice attached to a minor GC / time for minor GC
: should use a real estimation, here just a guess !!! *)
let reactivity = 0.6 (* between 0.5 and 1.0, less or equal than 0.5 is not very reasonable:
it is likely to double the minor_heap_size at each major GC, Decrease
if reactivity is not important to you *)
let retraction_coef = 0.9 (* between 0.0 and 1.0. the smaller, the less oscillation
in the minor heap size. 0.0: never decrease minor heap *)
let debug = ref 1 (* between 0 and 4, 2 and above is for debugging only *)
let max_minor_heap_size = 1 lsl 25 (* the names is clear,
rounded to the power of 2 below *)
let major_heap_increment_ratio = 0.5 (* proportional heap increment ratio *)
(* End of tuning constants *)
(* Justification:
We use a model saying that the time in each GC slice is
T = K * (m + gamma * r * m * f) where
m = minor heap size (goes away in O())
gamma = define above
r = ratio of promoted word at each minor cycle
f = (space_overhead + 100) / space_overhead used as an estimation
of free space in major heap after collection
K a time constant
in the sum abobe:
- K * m is the time in the minor GC
- K * gamma * r * m * f is the time in the major GC slice for each minor GC
If gamma * f is more than 1 (which is likely), it is easy to see that
increasing m, if it decreases r enough, will both increase overall speed and
time is a GC slice, increasing therefore both speed and reactivity.
More precisely, the model says that this is OK to double the size of the
minor heap when 1 + gamma * f * r > 2*(1 + gamma * f * r') where r is the ratio
associated to m and r' is the ratio associated to 2*m.
The code below keeps and update a table of ponderated average value of
1 + gamma * f * r for all used heap size and tries to make sensible decision
looking at it.
*)
let param = get ()
let _ = set { param with space_overhead = space_overhead }
let main_coef = (* gamma * f *)
gamma *.
(float) (space_overhead + 100) /.(float) (space_overhead)
let ratio_double = 1.0 /. reactivity
let ratio_half = ratio_double /. retraction_coef
(* tranlated log2 of the minor heap size, used at initialization only *)
let index m =
let rec fn i m =
if m <= 32768 then i else fn (i + 1) (m / 2)
in
fn 0 m
(* a table to store 1 + gamma * f * r for each heap size *)
let max_index = index max_minor_heap_size
let model_table = Array.create (max_index+1) None
let old_heap_words = ref (quick_stat ()).heap_words
let old_promoted_words = ref 0.0
let old_minor_collections = ref 0
let minor_heap_size = ref param.minor_heap_size
let minor_heap_index_size = ref (index param.minor_heap_size)
let _ = create_alarm (fun () ->
let s = quick_stat () in
(* tweak minor heap size *)
let promoted_words = s.promoted_words in
let minor_collections = s.minor_collections in
let delta_promoted_words = promoted_words -. !old_promoted_words in
let delta_minor_collections = minor_collections - !old_minor_collections in
old_promoted_words := promoted_words;
old_minor_collections := minor_collections;
let ratio = delta_promoted_words /. (float) delta_minor_collections
/. (float) !minor_heap_size
in
let new_model = 1.0 +. gamma *. ratio in
let i = !minor_heap_index_size in
let mean_model = match model_table.(i) with None -> new_model |
Some r -> (r +. new_model) /. 2.0
in
model_table.(i) <- Some mean_model;
if !debug > 2 then begin
let i = ref 0 in
while !i <= max_index && model_table.(!i) <> None do
match model_table.(!i) with
| None -> assert false
| Some r -> Printf.fprintf stderr "model(%d) = %f - " !i r; incr i
done;
Printf.fprintf stderr "\n"; flush stderr;
end;
let lower_double, lower_half =
if i <= 0 then true, false else
match model_table.(i-1) with
| None -> false, true
| Some r -> let x = 2.0 *. mean_model /. r in
(i < max_index) && x < ratio_double, x > ratio_half
in
let upper_double, upper_half =
if i >= max_index then false, true else
match model_table.(i+1) with
| None -> true, false
| Some r -> let x = 2.0 *. r /. mean_model in
x < ratio_double, (i > 0) && x > ratio_half
in
if !debug > 2 then begin
Printf.fprintf stderr "ld = %b, lh = %b, ud = %b, uh = %b\n"
lower_double lower_half upper_double upper_half;
flush stderr;
end;
if (lower_half && not upper_double) || (upper_half && not lower_double) then begin
minor_heap_size := !minor_heap_size / 2;
minor_heap_index_size := i - 1;
if !debug > 0 then begin
Printf.fprintf stderr "MHS HALFED <- %d (model %f)\n" !minor_heap_size mean_model;
flush stderr;
end;
set { (get ()) with minor_heap_size = !minor_heap_size }
end else
if (lower_double && not upper_half) || (upper_double && not lower_half) then begin
minor_heap_size := !minor_heap_size * 2;
minor_heap_index_size := i + 1;
if !debug > 0 then begin
Printf.fprintf stderr "MHS DOUBLED <- %d (model %f)\n" !minor_heap_size mean_model;
flush stderr;
end;
set { (get ()) with minor_heap_size = !minor_heap_size }
end else
if !debug > 1 then begin
Printf.fprintf stderr "MHS UNCHANGED (model %f) mean_model\n" mean_model;
flush stderr;
end;
(* tweak major heap increment to be a fraction of major heap size *)
if !old_heap_words <> s.heap_words then begin
old_heap_words := s.heap_words;
let major_heap_increment = max (124*1024) (int_of_float (float s.heap_words *. major_heap_increment_ratio) )in
(* Printf.fprintf stderr "MHI <- %d \n" major_heap_increment;
flush stderr; *)
set { (get ()) with major_heap_increment = major_heap_increment; }
end;
)
[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 262 bytes --]
next prev parent reply other threads:[~2010-11-24 17:57 UTC|newest]
Thread overview: 113+ messages / expand[flat|nested] mbox.gz Atom feed top
2010-11-22 13:21 Thanassis Tsiodras
2010-11-22 13:35 ` [Caml-list] " Gregory Bellier
2010-11-22 13:39 ` Lukasz Stafiniak
2010-11-22 13:42 ` Thomas Fischbacher
2010-11-22 13:43 ` Sylvain Le Gall
2010-11-22 13:55 ` [Caml-list] " Dario Teixeira
2010-11-23 2:11 ` Isaac Gouy
[not found] ` <999386690.746882.1290478813177.JavaMail.root@zmbs4.inria.fr>
2010-11-23 9:12 ` [Caml-list] " Fabrice Le Fessant
2010-11-23 17:56 ` Isaac Gouy
2010-11-23 19:54 ` [Caml-list] " Mark Diekhans
2010-11-23 20:04 ` Isaac Gouy
2010-11-23 22:56 ` [Caml-list] " oliver
2010-11-23 23:54 ` Jon Harrop
2010-11-24 1:24 ` Erik de Castro Lopo
2010-11-25 11:17 ` Jon Harrop
2010-11-22 14:04 ` Gerd Stolpmann
2010-11-22 14:22 ` [was: Re: Is OCaml fast?] OCaml Shootout task force Sylvain Le Gall
2010-11-22 14:36 ` [Caml-list] Is OCaml fast? bluestorm
2010-11-22 15:01 ` Török Edwin
2010-11-22 15:54 ` Goswin von Brederlow
2010-11-22 15:02 ` Gerd Stolpmann
[not found] ` <582306206.731582.1290438133628.JavaMail.root@zmbs4.inria.fr>
2010-11-22 16:46 ` Fabrice Le Fessant
2010-11-22 18:33 ` Török Edwin
2010-11-27 21:11 ` Pierre Etchemaïté
2010-11-28 13:26 ` OCaml GC [was Is OCaml fast?] Christophe Raffalli
2010-11-28 14:29 ` [Caml-list] " Benedikt Meurer
2010-11-28 18:57 ` Eray Ozkural
2010-11-28 19:40 ` Jon Harrop
2010-11-28 19:59 ` Benedikt Meurer
2010-11-28 23:34 ` Jon Harrop
2010-11-29 12:11 ` Benedikt Meurer
2010-11-29 22:27 ` Török Edwin
[not found] ` <916556265.243293.1291069665032.JavaMail.root@zmbs1.inria.fr>
2010-12-02 12:57 ` Damien Doligez
2010-12-02 15:07 ` Török Edwin
2010-12-03 21:42 ` [Caml-list] optimizing caml_modify [was OCaml GC [was Is OCaml fast?]] ygrek
2010-11-23 2:03 ` Is OCaml fast? Isaac Gouy
2010-11-23 10:37 ` [Caml-list] " Christophe TROESTLER
2010-11-23 15:50 ` Jon Harrop
2010-11-23 18:06 ` Isaac Gouy
2010-11-23 21:34 ` [Caml-list] " Jon Harrop
2010-11-23 16:08 ` Jon Harrop
2010-11-23 18:03 ` Isaac Gouy
2010-11-23 19:14 ` [Caml-list] " Török Edwin
2010-11-23 20:17 ` Isaac Gouy
2010-11-23 21:14 ` [Caml-list] " Christophe TROESTLER
2010-11-23 21:55 ` Isaac Gouy
2010-11-23 22:25 ` [Caml-list] " Richard Jones
2010-11-24 0:11 ` Isaac Gouy
2010-11-23 17:53 ` Isaac Gouy
2010-11-23 19:24 ` [Caml-list] " Gerd Stolpmann
2010-11-23 20:28 ` Isaac Gouy
2010-11-23 20:55 ` [Caml-list] " Gerd Stolpmann
2010-11-23 21:32 ` Isaac Gouy
2010-11-24 22:28 ` [Caml-list] " Goswin von Brederlow
2010-11-23 23:21 ` evil sloot
2010-11-24 6:54 ` [Caml-list] " David Rajchenbach-Teller
2010-11-22 17:02 ` [Caml-list] " Oliver Bandel
2010-11-22 17:08 ` David Rajchenbach-Teller
2010-11-22 17:23 ` Oliver Bandel
2010-11-22 17:54 ` David Rajchenbach-Teller
2010-11-22 23:55 ` Jeff Schultz
2010-11-22 23:28 ` Eray Ozkural
2010-11-23 2:01 ` Isaac Gouy
2010-11-23 23:27 ` [Caml-list] " oliver
2010-11-24 0:23 ` Isaac Gouy
2010-11-24 1:36 ` [Caml-list] " Eray Ozkural
2010-11-24 2:13 ` Isaac Gouy
2010-11-24 4:39 ` [Caml-list] " Jeff Meister
2010-11-24 6:22 ` Andrew
2010-11-24 7:16 ` Isaac Gouy
2010-11-24 6:50 ` Isaac Gouy
2010-11-24 10:24 ` [Caml-list] " Christophe Troestler
2010-11-24 11:33 ` Eray Ozkural
2010-11-24 17:32 ` Isaac Gouy
2010-11-24 17:57 ` Christophe Raffalli [this message]
2010-11-24 19:07 ` [Caml-list] " Ed Keith
2010-11-24 19:13 ` Isaac Gouy
2010-11-24 19:17 ` [Caml-list] " David Rajchenbach-Teller
2010-11-24 22:25 ` Oliver Bandel
2010-11-25 16:59 ` Stefan Monnier
2010-11-25 18:21 ` Isaac Gouy
2010-11-25 22:11 ` [Caml-list] " Jon Harrop
[not found] ` <1534555381.33107.1290723160355.JavaMail.root@zmbs4.inria.fr>
2010-11-25 22:50 ` Fabrice Le Fessant
2010-11-26 20:25 ` Isaac Gouy
2010-11-27 18:55 ` Stefan Monnier
2010-11-28 18:14 ` [Caml-list] " oliver
2010-11-29 14:19 ` Gerd Stolpmann
2010-11-29 16:12 ` Threading and SharedMem (Re: [Caml-list] Re: Is OCaml fast?) Oliver Bandel
2010-11-29 16:24 ` Gerd Stolpmann
2010-11-29 16:33 ` Oliver Bandel
2010-11-27 15:58 ` [Caml-list] Re: Is OCaml fast? Christophe Raffalli
2010-11-28 18:17 ` oliver
2010-11-29 7:33 ` Christophe Raffalli
2010-11-29 11:25 ` Jon Harrop
2010-11-29 11:44 ` oliver
2010-11-29 17:29 ` Christophe Raffalli
2010-11-24 6:55 ` David Rajchenbach-Teller
2010-11-24 7:23 ` Isaac Gouy
2010-11-23 2:06 ` Isaac Gouy
[not found] ` <1110536178.728445.1290434684177.JavaMail.root@zmbs4.inria.fr>
2010-11-22 16:39 ` [Caml-list] " Fabrice Le Fessant
2010-11-22 17:21 ` Philippe Strauss
2010-11-22 18:33 ` Oliver Bandel
2010-11-23 1:58 ` Isaac Gouy
2010-11-24 10:29 ` [Caml-list] " David Allsopp
2010-11-24 18:39 ` Isaac Gouy
2010-11-24 20:59 ` [Caml-list] " David Allsopp
2010-11-25 0:16 ` Isaac Gouy
2010-11-24 14:07 ` [Caml-list] " Cedric Cellier
2010-11-24 14:34 ` Vincent Aravantinos
2010-11-24 15:30 ` Thanassis Tsiodras
2010-11-24 16:26 ` Oliver Bandel
2010-11-24 16:27 ` Vincent Aravantinos
2010-11-24 18:16 ` Isaac Gouy
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=4CED51FD.6020305@univ-savoie.fr \
--to=christophe.raffalli@univ-savoie.fr \
--cc=caml-list@yquem.inria.fr \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox