Legend:
Page
Library
Module
Module type
Parameter
Class
Class type
Source
Source file arbitrary.ml
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226(*****************************************************************************)(* Open Source License *)(* Copyright (c) 2021 Valentin Chaboche *)(* Copyright (c) 2021 Nomadic Labs, <contact@nomadic-labs.com> *)(* *)(* Permission is hereby granted, free of charge, to any person obtaining a *)(* copy of this software and associated documentation files (the "Software"),*)(* to deal in the Software without restriction, including without limitation *)(* the rights to use, copy, modify, merge, publish, distribute, sublicense, *)(* and/or sell copies of the Software, and to permit persons to whom the *)(* Software is furnished to do so, subject to the following conditions: *)(* *)(* The above copyright notice and this permission notice shall be included *)(* in all copies or substantial portions of the Software. *)(* *)(* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR*)(* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, *)(* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL *)(* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER*)(* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING *)(* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER *)(* DEALINGS IN THE SOFTWARE. *)(* *)(*****************************************************************************)openPpxlibmoduleHelpers=Common.HelpersmoduleInfo=Helpers.InfomoduleError=Common.ErrormoduleT=Types_helpermoduleP=Common.Ast_helpers.PatternmodulePP=Common.PpmoduleREC=Recursives_helperstypety=stringtypeenv={ty:ty;mutual_types:tylist;recursives_types:tylist}letenvty={ty;mutual_types=[];recursives_types=[]}(** [default_env env td] create a default environment from [td] if [env] is absent *)letdefault_envenvtd=Option.value~default:{ty=td.ptype_name.txt;mutual_types=[];recursives_types=REC.get_recursives_type_declarations[td];}env(** [is_rec env] looks for [env.ty] inside [env.recursives_types] *)letis_recenv=List.memenv.tyenv.recursives_types(** [extract_args loc params] extract type parameters
{[
type 'a t
(* args are ['a] *)
type 'foo * 'oof
(* args are ['foo; 'oof] *)
]} *)letextract_args~locparams=letto_pat(ct,_)=matchct.ptyp_descwith|Ptyp_vars->P.ppat_var~loc@@T.names|_->Error.case_unsupported~loc~case:"type parameters are not all Ptyp_var"()inList.mapto_patparamsletrecfrom_core_type~loc~envct=Option.value(Attributes.arbct)~default:(matchct.ptyp_descwith|Ptyp_constr({txt=ty;_},[])->T.from_longident~loc~recursives_types:env.recursives_types~mutual_types:env.mutual_typesty|Ptyp_constr({txt=x;_},args)->letf=(* TODO: recursives_types and mutual_types empty is weird *)T.from_longident~loc~recursives_types:[]~mutual_types:[]xinletargs=List.map(from_core_type~loc~env)argsinT.constr_type~loc~f~args()|Ptyp_tuplexs->from_tuple~loc~envxs|Ptyp_vars->(* TODO: they should be optional parameters *)T.Primitive.from_string~loc~recursives_types:[]~mutual_types:[]s|Ptyp_variant(rws,_,_)->from_ptyp_variant~loc~envrws|Ptyp_arrow(_,left,right)->from_arrow~loc~env(left,right)|_->Error.location_error~loc:ct.ptyp_loc~msg:"This type is not supported yet"())andfrom_arrow~loc~env(left,right)=letf=T.observable~locinletrecarrow_to_listx:expressionlist*expression=matchx.ptyp_descwith|Ptyp_arrow(_,left,right)->let(acc,x)=arrow_to_listrightin(fleft::acc,x)|_->([],from_core_type~loc~envx)inlet(obs,arb)=arrow_to_listrightinletobs=fleft::obsinT.fun_nary~locobsarbandfrom_ptyp_variant~loc~envrws=(* Transforms a row_field to the pair (variant name, arbitraries) *)letto_exprfrw=letw=Attributes.weightrw.prf_attributesinmatchrw.prf_descwith|Rtag({txt;_},_,cts)->`RTag(txt,w,List.mapfcts)|Rinheritct->`RInh(w,fct)inletf=from_core_type~loc~envinifis_recenvthenletis_leavex=not@@REC.is_recursive_row_field~locenv.tyxinletleaves=List.filter_map(funrw->ifis_leaverwthenOption.some@@to_exprfrwelseNone)rws|>T.variants~loc~ty:env.tyinletnodes=List.map(to_exprf)rws|>T.variants~loc~ty:env.tyinT.tree'~loc~leaves~nodes()elseList.map(to_exprf)rws|>T.variants~loc~ty:env.tyandfrom_type_kind~loc~env=function|Ptype_recordxs->Option.some@@from_record~loc~envxs|Ptype_variantxs->Option.some@@from_variant~loc~envxs|_->Noneandfrom_record~loc~envlabel_decls=letgens=List.map(funx->from_core_type~loc~envx.pld_type)label_declsinT.record~loc~genslabel_declsandfrom_tuple~loc~envcts=letgens=List.map(from_core_type~loc~env)ctsinT.tuple~locgensandfrom_variant~loc~envxs=ifis_recenvthenletis_leavex=not@@REC.is_recursive_constructor_declaration~locenv.tyxinletleaves=List.filter_map(funx->ifis_leavexthenOption.some@@from_constructor_decl~loc~envxelseNone)xsinletnodes=List.map(funx->from_constructor_decl~loc~envx)xsinT.tree~loc~leaves~nodes()elseList.map(from_constructor_decl~loc~env)xs|>T.constructors~locandfrom_constructor_decl~loc~envx=letkname=x.pcd_name.txtinletf~kargs=T.constructor~loc~kname~kargs()inletconstr=matchx.pcd_argswith|Pcstr_tuple[]|Pcstr_record[]->T.constructor~loc~kname()|Pcstr_tuplexs->letgens=List.map(from_core_type~loc~env)xsinletkargs=T.tuple'~locgensinf~kargs|Pcstr_recordxs->letgens=List.map(funx->from_core_type~loc~envx.pld_type)xsinletkargs=T.record'~loc~gensxsinf~kargsin(Attributes.weightx.pcd_attributes,constr)letfrom_type_declaration~loc?envtd=letenv=default_envenvtdinletis_rec=List.memenv.tyenv.recursives_typesinletargs=extract_args~loctd.ptype_paramsinletarb_from_type_kind=from_type_kind~loc~envtd.ptype_kindinletbody=match(arb_from_type_kind,td.ptype_manifest)with|(Somex,_)->x|(None,Somect)->from_core_type~loc~envct|_->assertfalse(* I don't know at that point if invariants forbids this *)inT.gen~loc~is_rec~args~ty:env.tybodyletfrom_type_declarations~locxs=lettys=List.map(funx->x.ptype_name.txt)xsinletenv={ty="";mutual_types=tys;recursives_types=REC.get_recursives_type_declarationsxs;}inletgens=List.map(funx->letty=x.ptype_name.txtinletenv={envwithty}infrom_type_declaration~loc~envx)xsinT.gens~loc~tys~gens()