Caml1999I036b\#Tmc'rewriteh@&Lambda&lambda@@@&lambda@@@@@@.lambda/tmc.mliQ [ [Q [ y@@B@@@H#Tmc0z;t M(Warnings0;w.Q=1)Unit_info08a AnMͼ %Types0#`O(ߍLF.Type_immediacy0GuQT@<=%Subst09,+bmT-Stdlib__Uchar0d"W-x9.Stdlib__Domain0iW',P6wz.Stdlib__Digest0 Jjrڵ6.Stdlib__Buffer0_?K|/V>O}~Nࠠ&Stdlib0y{x!O!%Shape0OĸT>b)Primitive0{mV|{J $Path09{ְZsv)Parsetree0Z<4$PC+Outcometree0yl4>Yfܠ$Misc0  =73 Z )Longident0@#j,6.Nt蠠(Location0nݹV 2f-V )Load_path02&9Q҄;L&Lambda0 [, U(Z,Identifiable0XnAZ4eҠ%Ident0y43a$+*Format_doc0Mv9630A #Env0؞X:Fݗ))Debuginfo0.6硏]fSvi*Data_types0-k(.I7*Cmi_format0KuEB젠0CamlinternalLazy0;x#5䢜hLm8CamlinternalFormatBasics0oZ2t,ݠ5Build_path_prefix_map0gMOBnM`(Asttypes0E\eǥ]k6e@@@Caml1999T036(!dC#Tmc*ocaml.text&_none_@@A w Tail-modulo-cons optimization. {b Warning:} this module is unstable and part of {{!Compiler_libs}compiler-libs}. .lambda/tmc.mliRVNP@@@@@@3@@@@@@#intA;@@@A@@@@@:@A@$charB;@@A@@@@@>@A@&stringQ;@@ A@@@@@B@@@%bytesC;@@ A@@@@@F@@@%floatD;@@A@@@@@J@@@$boolE;@@%falsec@@T@$trued@@Z@@@A@@@@@[@A@$unitF;@@"()e@@e@@@A@@@@@f@A@ #exnG;@@@A@@@@@j@@@#effH;@@O@A@A@@@@@@s@@@,continuationI;@@Q@@P@B@A@nY@@@@@@@@@%arrayJ;@@R@A@A@@@@@@@@@ $listK;@@S@A"[]f@@@"::g@@@T@@@ @@A@Y@@@@@@@@&optionL;@@V@A$Noneh@@@$Somei@@@@@A@Y@@@@@@@@)nativeintM;@@A@@@@@@@@%int32N;@@A@@@@@@@@%int64O;@@A@@@@@@@@&lazy_tP;@@X@AJA@Y@@@@@@@@5extension_constructorR;@@A@@@@@@@@*floatarrayS;@@A@@@@@@@@&iarrayT;@@Y@A[A@Y@@@@@@@@*atomic_locU;@@Z@AdA@@@@@@@@@.Assert_failure`#@@@@@J@@@@@@@@[@@A=ocaml.warn_on_literal_pattern @ @0Division_by_zero]#@@@A  @+End_of_file\#$@@@A@'FailureY#,@'@@A!$$@0Invalid_argumentX#5@0@@A*$-#-@-Match_failureV#>@@=@9@;@@a@@A;5>4>@)Not_foundZ#O@@@AC=F<F@-Out_of_memoryW#W@@@AKENDN@.Stack_overflow^#_@@@ASMVLV@.Sys_blocked_io_#g@@@A[U^T^@)Sys_error[#o@j@@Ad^g]g@:Undefined_recursive_modulea#x@@w@s@u@@h@@Auoxnx@:Continuation_already_takenb#@@@A}wv@&Stdlib@Ax  TMC (Tail Modulo Cons) is a code transformation that rewrites transformed functions in destination-passing-style, in such a way that certain calls that were not in tail position in the original program become tail-calls in the transformed program. As a classic example, the following program {| let[@tail_mod_cons] rec map f = function | [] -> [] | x :: xs -> let y = f x in y :: map f xs |} becomes (expressed in almost-source-form; the translation is in fact at the Lambda-level) {| let rec map f = function | [] -> [] | x :: xs -> let y = f x in let dst = y :: Placeholder in map_dps dst 1 f xs; dst and map_dps dst offset f = function | [] -> dst.offset <- [] | x :: xs -> let y = f x in let dst' = y :: Placeholder in dst.offset <- dst'; map_dps dst 1 f fx |} In this example, the expression (y :: map f xs) had a call in non-tail-position, and it gets rewritten into tail-calls. TMC handles all such cases where the continuation of the call (what needs to be done after the return) is a "construction", the creation of a (possibly nested) data block. The code transformation generates two versions of the input function, the "direct" version with the same type and behavior as the original one (here just [map]), and the "destination-passing-style" version (here [map_dps]). Any call to the original function from outside the let..rec declaration gets transformed into a call into the direct version, which will itself call the destination-passing-style versions on recursive calls that may benefit from it (they are in tail-position modulo constructors). Because of this inherent code duplication, the transformation may not always improve performance. In this implementation, TMC is opt-in, we only transform functions that the user has annotated with an attribute to request the transformation. XRRM J L@@@@@@ࠐ&Lambda&LambdaO N SO N Y@@A3@ @AO N N@@@'rewritegQ [ _Q [ f@б@г&lambdaQ [ iQ [ o@@ @@@ @@г*&lambdaQ [ sQ [ y@@ @@@ *@@@@@ -@@@Q [ [ @@B@@ @@3@,@@3@6. @A@ H************************************************************************A@@A@L@ H BMMBM@ H OCaml CC@ H DD3@ J Frédéric Bour E44E4@ H Gabriel Scherer, projet Partout, INRIA Saclay FF@ I Basile Clément, projet Cambium, INRIA Paris GG@ H HHj@ H Copyright 2020 Institut National de Recherche en Informatique et IkkIk@ H en Automatique. JJ@ H  KKQ@ H All rights reserved. This file is distributed under the terms of LRRLR@ H the GNU Lesser General Public License version 2.1, with the MM@ H special exception on linking described in the file LICENSE. N N8@ H %O99&O9@ H************************************************************************+P,P@ x* Tail-modulo-cons optimization. {b Warning:} this module is unstable and part of {{!Compiler_libs}compiler-libs}. 1 * TMC (Tail Modulo Cons) is a code transformation that rewrites transformed functions in destination-passing-style, in such a way that certain calls that were not in tail position in the original program become tail-calls in the transformed program. As a classic example, the following program {| let[@tail_mod_cons] rec map f = function | [] -> [] | x :: xs -> let y = f x in y :: map f xs |} becomes (expressed in almost-source-form; the translation is in fact at the Lambda-level) {| let rec map f = function | [] -> [] | x :: xs -> let y = f x in let dst = y :: Placeholder in map_dps dst 1 f xs; dst and map_dps dst offset f = function | [] -> dst.offset <- [] | x :: xs -> let y = f x in let dst' = y :: Placeholder in dst.offset <- dst'; map_dps dst 1 f fx |} In this example, the expression (y :: map f xs) had a call in non-tail-position, and it gets rewritten into tail-calls. TMC handles all such cases where the continuation of the call (what needs to be done after the return) is a "construction", the creation of a (possibly nested) data block. The code transformation generates two versions of the input function, the "direct" version with the same type and behavior as the original one (here just [map]), and the "destination-passing-style" version (here [map_dps]). Any call to the original function from outside the let..rec declaration gets transformed into a call into the direct version, which will itself call the destination-passing-style versions on recursive calls that may benefit from it (they are in tail-position modulo constructors). Because of this inherent code duplication, the transformation may not always improve performance. In this implementation, TMC is opt-in, we only transform functions that the user has annotated with an attribute to request the transformation. @-./boot/ocamlc)-nostdlib"-I&./boot*-use-prims2runtime/primitives"-g0-strict-sequence*-principal(-absname"-w8+a-4-9-40-41-42-44-45-48+-warn-error"+a*-bin-annot/-strict-formats"-I&lambda"-I%utils"-I'parsing"-I&typing"-I(bytecomp"-I,file_formats"-I&lambda"-I*middle_end"-I2middle_end/closure"-I2middle_end/flambda"-I=middle_end/flambda/base_types"-I'asmcomp"-I&driver"-I(toplevel"-I%tools"-I'runtime"-I1otherlibs/dynlink"-I-otherlibs/str"-I4otherlibs/systhreads"-I.otherlibs/unix"-I8otherlibs/runtime_events"-cno S/home/teraram/ci/builds/workspace/parallel-build/flambda/true/label/ocaml-manycores >10/.-,+*)('&%$#"! @@0ZRgLfC*3@@@(Asttypes0E\eǥ]k6e5Build_path_prefix_map0gMOBnM`8CamlinternalFormatBasics0oZ2t,ݠ0CamlinternalLazy0;x#5䢜hLm*Cmi_format0KuEB젠*Data_types0-k(.I7)Debuginfo0.6硏]fSvi#Env0؞X:Fݗ)*Format_doc0Mv9630A %Ident0y43a$+,Identifiable0XnAZ4eҠ40 [, U(Z)Load_path02&9Q҄;L(Location0nݹV 2f-V )Longident0@#j,6.Nt蠠$Misc0  =73 Z +Outcometree0yl4>Yfܠ)Parsetree0Z<4$PC$Path09{ְZsv)Primitive0{mV|{J %Shape0OĸT>b&Stdlib0y{x!O!.Stdlib__Buffer0_?K|/V>O}~Nࠠ.Stdlib__Digest0 Jjrڵ6.Stdlib__Domain0iW',P6wz.Stdlib__Either0FԤ) 4'>.Stdlib__Format0)n[-Ob/Stdlib__Hashtbl0^iaxG$+,Stdlib__Lazy0OM>x9