1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150openImportopenAst_builder.Default(* [do_insert_unused_warning_attribute] -- If true, generated code
contains compiler attribute to disable unused warnings, instead of
inserting [let _ = ... ]. *)letdo_insert_unused_warning_attribute=reffalseletkeep_w32_impl=reffalseletkeep_w32_intf=reffalselet()=letkeep_w32_spec=Stdlib.Arg.Symbol(["impl";"intf";"both"],function|"impl"->keep_w32_impl:=true|"intf"->keep_w32_intf:=true|"both"->keep_w32_impl:=true;keep_w32_intf:=true|_->assertfalse)inletconv_w32_spec=Stdlib.Arg.Symbol(["code";"attribute"],function|"code"->do_insert_unused_warning_attribute:=false|"attribute"->do_insert_unused_warning_attribute:=true|_->assertfalse)inDriver.add_arg"-deriving-keep-w32"keep_w32_spec~doc:" Do not try to disable warning 32 for the generated code";Driver.add_arg"-deriving-disable-w32-method"conv_w32_spec~doc:" How to disable warning 32 for the generated code";Driver.add_arg"-type-conv-keep-w32"keep_w32_spec~doc:" Deprecated, use -deriving-keep-w32";Driver.add_arg"-type-conv-w32"conv_w32_spec~doc:" Deprecated, use -deriving-disable-w32-method"letkeep_w32_impl()=!keep_w32_impl||Driver.pretty()letkeep_w32_intf()=!keep_w32_intf||Driver.pretty()letkeep_w60_impl=reffalseletkeep_w60_intf=reffalselet()=letkeep_w60_spec=Stdlib.Arg.Symbol(["impl";"intf";"both"],function|"impl"->keep_w60_impl:=true|"intf"->keep_w60_intf:=true|"both"->keep_w60_impl:=true;keep_w60_intf:=true|_->assertfalse)inDriver.add_arg"-deriving-keep-w60"keep_w60_spec~doc:" Do not try to disable warning 60 for the generated code"letkeep_w60_impl()=!keep_w60_impl||Driver.pretty()letkeep_w60_intf()=!keep_w60_intf||Driver.pretty()letallow_unused_code_warnings=refOptions.default_allow_unused_code_warningslet()=Driver.add_arg"-unused-code-warnings"(Options.Forcable_bool.argallow_unused_code_warnings)~doc:" Allow ppx derivers to enable unused code warnings (default: false)"letallow_unused_code_warnings~ppx_allows_unused_code_warnings=match!allow_unused_code_warningswith|Force->true|False->false|True->ppx_allows_unused_code_warningsletallow_unused_type_warnings=refOptions.default_allow_unused_type_warningslet()=Driver.add_arg"-unused-type-warnings"(Options.Forcable_bool.argallow_unused_type_warnings)~doc:" Allow unused type warnings for types with [@@deriving ...] (default: \
false)"letallow_unused_type_warnings~ppx_allows_unused_code_warnings=match!allow_unused_type_warningswith|Force->true|False->false|True->ppx_allows_unused_code_warningsmoduleArgs=structinclude(Ast_pattern:moduletypeofstructincludeAst_patternendwithtype('a,'b,'c)t:=('a,'b,'c)Ast_pattern.t)type'aparam={name:string;pattern:(expression,'a)Ast_pattern.Packed.t;default:'a;}letargnamepattern={name;default=None;pattern=Ast_pattern.Packed.createpattern(funx->Somex);}letflagname=letpattern=pexp_ident(lident(stringname))in{name;default=false;pattern=Ast_pattern.Packed.createpatterntrue}type(_,_)t=|Nil:('m,'m)t|Cons:('m1,'a->'m2)t*'aparam->('m1,'m2)tletempty=Nillet(+>)ab=Cons(a,b)letrecnames:typeab.(a,b)t->stringlist=function|Nil->[]|Cons(t,p)->p.name::namestmoduleInstance=structtype(_,_)instance=|I_nil:('m,'m)instance|I_cons:('m1,'a->'m2)instance*'a->('m1,'m2)instanceletreccreate:typeab.(a,b)t->(string*expression)list->(a,b)instance=funspecargs->matchspecwith|Nil->I_nil|Cons(t,p)->letvalue=matchList.assoc_optp.nameargswith|None->p.default|Someexpr->Ast_pattern.Packed.parsep.patternexpr.pexp_locexprinI_cons(createtargs,value)letrecapply:typeab.(a,b)instance->a->b=funtf->matchtwithI_nil->f|I_cons(t,x)->applytfxendletapplytargsf=Instance.apply(Instance.createtargs)fend(* +-----------------------------------------------------------------+
| Generators |
+-----------------------------------------------------------------+ *)typet=stringletignore(_:t)=()typeparsed_args=|Argsof(string*expression)list|Unknown_syntaxofLocation.t*stringtype'itemderived_code={items:'itemlist;unused_code_warnings:bool}moduleGenerator=structtypederiver=ttype('a,'b)t=|T:{spec:('c,'a)Args.t;gen:ctxt:Expansion_context.Deriver.t->'b->'c;arg_names:String.Set.t;deps:deriverlist;unused_code_warnings:bool;}->('a,'b)tletdeps(Tt)=t.depsmoduleV2=structletmake?attributes:(_=[])?(deps=[])?(unused_code_warnings=false)specgen=letarg_names=String.Set.of_list(Args.namesspec)inT{spec;gen;arg_names;deps;unused_code_warnings}letmake_noarg?attributes?deps?unused_code_warningsgen=make?attributes?deps?unused_code_warningsArgs.emptygenendletmake?attributes?deps?unused_code_warningsspecgen=V2.make?attributes?deps?unused_code_warningsspec(Expansion_context.Deriver.with_loc_and_pathgen)letmake_noarg?attributes?deps?unused_code_warningsgen=make?attributes?deps?unused_code_warningsArgs.emptygenletmerge_accepted_argsl=letrecloopacc=function|[]->acc|Tt::rest->loop(String.Set.unionacct.arg_names)restinloopString.Set.emptylletcheck_argumentsnamegenerators(args:(string*expression)list)=letempty_label_error=List.filter_mapargs~f:(fun(label,e)->ifString.is_emptylabelthenSome(Location.error_extensionf~loc:e.pexp_loc"Ppxlib.Deriving: generator arguments must be labelled")elseNone)inletduplicate_argument_error=Option.map(List.find_a_dupargs~compare:(fun(a,_)(b,_)->String.compareab))~f:(fun(label,e)->Location.error_extensionf~loc:e.pexp_loc"Ppxlib.Deriving: argument labelled '%s' appears more than once"label)|>Option.to_listinletaccepted_args=merge_accepted_argsgeneratorsinletunaccepted_argument=List.filter_mapargs~f:(fun(label,e)->ifnot(String.Set.memlabelaccepted_args)thenletspellcheck_msg=matchSpellcheck.spellcheck(String.Set.elementsaccepted_args)labelwith|None->""|Somes->".\n"^sinSome(Location.error_extensionf~loc:e.pexp_loc"Ppxlib.Deriving: generator '%s' doesn't accept argument \
'%s'%s"namelabelspellcheck_msg)elseNone)inleterrors=empty_label_error@duplicate_argument_error@unaccepted_argumentinifList.lengtherrors=0thenOk()elseErrorerrorsletapply(Tt)~name:_~ctxtxargs=Args.applyt.specargs(t.gen~ctxtx)letapply_all~ctxtentry(name,generators,args)=letopenResultincheck_argumentsname.txtgeneratorsargs>>|fun()->List.mapgenerators~f:(fun(Tt)->{items=apply(Tt)~name:name.txt~ctxtentryargs;unused_code_warnings=t.unused_code_warnings;})letapply_all~ctxtentrygeneratorsext_to_item=letl=List.mapgenerators~f:(apply_all~ctxtentry)inletl1,lerr=List.partition_map(functionOke->Lefte|Errore->Righte)linletlerr=List.concatlerr|>List.map~f:(funerr->ext_to_item~loc:Location.noneerr[])inList.concatl1@[{items=lerr;unused_code_warnings=false}]endmoduleDeriver=structmoduleActual_deriver=structtypet={name:string;str_type_decl:(structure,rec_flag*type_declarationlist)Generator.toption;str_class_type_decl:(structure,class_type_declarationlist)Generator.toption;str_type_ext:(structure,type_extension)Generator.toption;str_exception:(structure,type_exception)Generator.toption;str_module_type_decl:(structure,module_type_declaration)Generator.toption;str_module_binding:(structure,module_binding)Generator.toption;sig_type_decl:(signature,rec_flag*type_declarationlist)Generator.toption;sig_class_type_decl:(signature,class_type_declarationlist)Generator.toption;sig_type_ext:(signature,type_extension)Generator.toption;sig_exception:(signature,type_exception)Generator.toption;sig_module_type_decl:(signature,module_type_declaration)Generator.toption;sig_module_decl:(signature,module_declaration)Generator.toption;}endmoduleAlias=structtypet={str_type_decl:stringlist;str_class_type_decl:stringlist;str_type_ext:stringlist;str_exception:stringlist;str_module_type_decl:stringlist;str_module_binding:stringlist;sig_type_decl:stringlist;sig_class_type_decl:stringlist;sig_type_ext:stringlist;sig_exception:stringlist;sig_module_type_decl:stringlist;sig_module_decl:stringlist;}endmoduleField=structtype('a,'b)t={name:string;get:Actual_deriver.t->('a,'b)Generator.toption;get_set:Alias.t->stringlist;}letstr_type_decl={name="type";get=(funt->t.str_type_decl);get_set=(funt->t.str_type_decl);}letstr_class_type_decl={name="class type declaration";get=(funt->t.str_class_type_decl);get_set=(funt->t.str_class_type_decl);}letstr_type_ext={name="type extension";get=(funt->t.str_type_ext);get_set=(funt->t.str_type_ext);}letstr_exception={name="exception";get=(funt->t.str_exception);get_set=(funt->t.str_exception);}letstr_module_type_decl={name="module type";get=(funt->t.str_module_type_decl);get_set=(funt->t.str_module_type_decl);}letstr_module_binding={name="module binding";get=(funt->t.str_module_binding);get_set=(funt->t.str_module_binding);}letsig_type_decl={name="signature type";get=(funt->t.sig_type_decl);get_set=(funt->t.sig_type_decl);}letsig_class_type_decl={name="signature class type";get=(funt->t.sig_class_type_decl);get_set=(funt->t.sig_class_type_decl);}letsig_type_ext={name="signature type extension";get=(funt->t.sig_type_ext);get_set=(funt->t.sig_type_ext);}letsig_exception={name="signature exception";get=(funt->t.sig_exception);get_set=(funt->t.sig_exception);}letsig_module_type_decl={name="signature module type";get=(funt->t.sig_module_type_decl);get_set=(funt->t.sig_module_type_decl);}letsig_module_decl={name="signature module declaration";get=(funt->t.sig_module_decl);get_set=(funt->t.sig_module_decl);}endtypet=Actual_deriverofActual_deriver.t|AliasofAlias.ttypePpx_derivers.deriver+=Toftletderivers()=List.filter_map(Ppx_derivers.derivers())~f:(function|name,Tt->Some(name,t)|_->None)exceptionNot_supportedofstringletresolve_actual_derivers(field:(_,_)Field.t)name=letrecloopnamecollected=ifList.existscollected~f:(fun(d:Actual_deriver.t)->String.equald.namename)thencollectedelsematchPpx_derivers.lookupnamewith|Some(T(Actual_deriverdrv))->drv::collected|Some(T(Aliasalias))->letset=field.get_setaliasinList.fold_rightset~init:collected~f:loop|_->raise(Not_supportedname)inList.rev(loopname[])letresolve_internal(field:(_,_)Field.t)name=List.map(resolve_actual_deriversfieldname)~f:(fundrv->matchfield.getdrvwith|None->raise(Not_supportedname)|Someg->(drv.name,g))letsupported_forfield=List.fold_left(derivers())~init:String.Set.empty~f:(funacc(name,_)->matchresolve_internalfieldnamewith|_->String.Set.addnameacc|exceptionNot_supported_->acc)|>String.Set.elementsletnot_supported(field:(_,_)Field.t)?(spellcheck=true)name=letspellcheck_msg=ifspellcheckthenmatchSpellcheck.spellcheck(supported_forfield)name.txtwith|None->""|Somes->".\n"^selse""inLocation.error_extensionf~loc:name.loc"Ppxlib.Deriving: '%s' is not a supported %s deriving generator%s"name.txtfield.namespellcheck_msgletresolvefieldname=tryOk(resolve_internalfieldname.txt)withNot_supportedname'->Error(not_supportedfield~spellcheck:(String.equalname.txtname')name)letresolve_allfieldderivers=letderivers_and_args,derivers_and_args_errors=List.partition_map(fun(name,args)->matchPpx_derivers.lookupname.txtwith|None->Either.Right(not_supportedfieldname)|Some(T_)->((* It's one of ours, parse the arguments now. We can't do it before since
ppx_deriving uses a different syntax for arguments. *)matchargswith|Argsl->Either.Left(Some(name,l))|Unknown_syntax(loc,msg)->Either.Right(Location.error_extensionf~loc"Ppxlib.Deriving: %s"msg))|Some_->(* It's not one of ours, ignore it. *)Either.LeftNone)derivers|>fun(l1,l2)->(List.filter_optl1,l2)in(* Set of actual deriver names *)letseen=Hashtbl.create16inletresult,dep_errors=List.fold_left~init:([],[])derivers_and_args~f:(fun(result,errors)(name,args)->matchresolvefieldnamewith|Errore->(result,errors@[e])|Oknamed_generators->letl_err=List.concat_mapnamed_generators~f:(fun(actual_deriver_name,gen)->letdup_error=ifOptions.fail_on_duplicate_derivers&&Hashtbl.memseenactual_deriver_namethen[Location.error_extensionf~loc:name.loc"Deriver %s appears twice"actual_deriver_name;]else[]inletl_err=List.concat_map(Generator.depsgen)~f:(fundep->List.filter_map(resolve_actual_deriversfielddep)~f:(fundrv->letdep_name=drv.nameinifnot(Hashtbl.memseendep_name)thenSome(Location.error_extensionf~loc:name.loc"Deriver %s is needed for %s, you need to \
add it before in the list"dep_namename.txt)elseNone))inHashtbl.setseen~key:actual_deriver_name~data:();dup_error@l_err)in(result@[(name,List.mapnamed_generators~f:snd,args)],errors@l_err))in(result,derivers_and_args_errors@dep_errors)letadd?str_type_decl?str_class_type_decl?str_type_ext?str_exception?str_module_type_decl?str_module_binding?sig_type_decl?sig_class_type_decl?sig_type_ext?sig_exception?sig_module_type_decl?sig_module_decl?extensionname=letactual_deriver:Actual_deriver.t={name;str_type_decl;str_class_type_decl;str_type_ext;str_exception;str_module_type_decl;str_module_binding;sig_type_decl;sig_class_type_decl;sig_type_ext;sig_exception;sig_module_type_decl;sig_module_decl;}inPpx_derivers.registername(T(Actual_deriveractual_deriver));(matchextensionwith|None->()|Somef->letextension=Extension.declarenameExpressionAst_pattern.(ptyp__)finDriver.register_transformation("Ppxlib.Deriving."^name)~rules:[Context_free.Rule.extensionextension]);nameletadd_aliasname?str_type_decl?str_class_type_decl?str_type_ext?str_exception?str_module_type_decl?str_module_binding?sig_type_decl?sig_class_type_decl?sig_type_ext?sig_exception?sig_module_type_decl?sig_module_declset=letalias:Alias.t=letget=functionNone->set|Someset->setin{str_type_decl=getstr_type_decl;str_class_type_decl=getstr_class_type_decl;str_type_ext=getstr_type_ext;str_exception=getstr_exception;str_module_type_decl=getstr_module_type_decl;str_module_binding=getstr_module_binding;sig_type_decl=getsig_type_decl;sig_class_type_decl=getsig_class_type_decl;sig_type_ext=getsig_type_ext;sig_exception=getsig_exception;sig_module_type_decl=getsig_module_type_decl;sig_module_decl=getsig_module_decl;}inPpx_derivers.registername(T(Aliasalias));nameendletadd=Deriver.addletadd_alias=Deriver.add_alias(* +-----------------------------------------------------------------+
| [@@deriving ] parsing |
+-----------------------------------------------------------------+ *)letinvalid_with~loc=Location.raise_errorf~loc"invalid [@@deriving ] attribute syntax"letgenerator_name_of_idlocid=matchLongident.flatten_exnidwith|l->{loc;txt=String.concat~sep:"."l}|exception_->invalid_with~locexceptionUnknown_syntaxofLocation.t*stringletparse_argumentsl=tryArgs(matchlwith|[(Nolabel,e)]->(matche.pexp_descwith|Pexp_record(fields,None)->List.mapfields~f:(fun(id,expr)->letname=matchid.txtwith|Lidents->s|_->raise_notrace(Unknown_syntax(id.loc,"simple identifier expected"))in(name,expr))|_->raise_notrace(Unknown_syntax(e.pexp_loc,"non-optional labelled argument or record expected")))|l->List.mapl~f:(fun(label,expr)->matchlabelwith|Labelleds->(s,expr)|_->raise_notrace(Unknown_syntax(expr.pexp_loc,"non-optional labelled argument expected"))))withUnknown_syntax(loc,msg)->Unknown_syntax(loc,msg)letmk_deriving_attrcontext~prefix~suffix=Attribute.declare(prefix^"deriving"^suffix)contextAst_pattern.(letgenerator_name()=map'(pexp_ident__)~f:(funlocfid->f(generator_name_of_idlocid))inletgenerator()=map(generator_name())~f:(funfx->f(x,Args[]))|||pack2(pexp_apply(generator_name())(map1(many__)~f:parse_arguments))inletgenerators=pexp_tuple(many(generator()))|||map(generator())~f:(funfx->f[x])inpstr(pstr_evalgeneratorsnil^::nil))(funx->x)(* +-----------------------------------------------------------------+
| Unused warning stuff + locations check silencing |
+-----------------------------------------------------------------+ *)letdisable_warnings_attributewarnings=letloc=Location.noneinletstring=List.sortwarnings~cmp:Int.compare|>List.map~f:(funwarning->"-"^Int.to_stringwarning)|>String.concat~sep:""in{attr_name={txt="ocaml.warning";loc};attr_payload=PStr[pstr_eval~loc(estring~locstring)[]];attr_loc=loc;}letinline_doc_attr=letloc=Location.nonein{attr_name={txt="ocaml.doc";loc};attr_payload=PStr[pstr_eval~loc(estring~loc"@inline")[]];attr_loc=loc;}(* wrap a structure in extra attributes *)letwrap_str~loc~hidest=letinclude_infos=include_infos~loc(pmod_structure~locst)inletpincl_attributes=ifhidethen[inline_doc_attr;Merlin_helpers.hide_attribute]else[inline_doc_attr]in[pstr_include~loc{include_infoswithpincl_attributes}](* decide what to wrap a structure in, then call above [wrap_str] *)letwrap_str~loc~hide~unused_code_warningsst=letloc={locwithloc_ghost=true}inletunused_code_warnings=allow_unused_code_warnings~ppx_allows_unused_code_warnings:unused_code_warningsinletwarnings,st=ifkeep_w32_impl()||unused_code_warningsthen([],st)elseifnot!do_insert_unused_warning_attributethen([],Ignore_unused_warning.add_dummy_user_for_values#structurest)else([32],st)inletwarnings,st=ifkeep_w60_impl()||unused_code_warnings||not(Ignore_unused_warning.binds_module_names#structurestfalse)then(warnings,st)else(60::warnings,st)inletwrap,st=ifList.is_emptywarningsthen(hide,st)else(true,pstr_attribute~loc(disable_warnings_attributewarnings)::st)inifwrapthenwrap_str~loc~hidestelsest(* wrap blocks that share [unused_code_warnings], using above [wrap_str] above *)letwrap_str~loc~hidelist=List.concat_maplist~f:(fun{items;unused_code_warnings}->ifList.is_emptyitemsthen[]elsewrap_str~loc~hide~unused_code_warningsitems)(* wrap a signature in extra attributes *)letwrap_sig~loc~hidest=letinclude_infos=include_infos~loc(pmty_signature~locst)inletpincl_attributes=ifhidethen[inline_doc_attr;Merlin_helpers.hide_attribute]else[inline_doc_attr]in[psig_include~loc{include_infoswithpincl_attributes}](* decide what to wrap a signature in, then call above [wrap_sig] *)letwrap_sig~loc~hide~unused_code_warningssg=letloc={locwithloc_ghost=true}inletunused_code_warnings=allow_unused_code_warnings~ppx_allows_unused_code_warnings:unused_code_warningsinletwarnings=ifkeep_w32_intf()||unused_code_warningsthen[]else[32]inletwarnings=ifkeep_w60_intf()||(not(Ignore_unused_warning.binds_module_names#signaturesgfalse))||unused_code_warningsthenwarningselse60::warningsinletwrap,sg=ifList.is_emptywarningsthen(hide,sg)else(true,psig_attribute~loc(disable_warnings_attributewarnings)::sg)inifwrapthenwrap_sig~loc~hidesgelsesg(* wrap blocks that share [unused_code_warnings], using above [wrap_sig] above *)letwrap_sig~loc~hidelist=List.concat_maplist~f:(fun{items;unused_code_warnings}->ifList.is_emptyitemsthen[]elsewrap_sig~loc~hide~unused_code_warningsitems)(* +-----------------------------------------------------------------+
| Main expansion |
+-----------------------------------------------------------------+ *)lettypes_used_by_deriving(tds:type_declarationlist)~unused_code_warnings:ppx_allows_unused_code_warnings:structure_itemlist=letunused_code_warnings=allow_unused_code_warnings~ppx_allows_unused_code_warningsinletunused_type_warnings=allow_unused_type_warnings~ppx_allows_unused_code_warningsinifkeep_w32_impl()||unused_code_warnings||unused_type_warningsthen[]elseList.maptds~f:(funtd->lettyp=Common.core_type_of_type_declarationtdinletloc=td.ptype_locinpstr_value~locNonrecursive[value_binding~loc~pat:(ppat_any~loc)~expr:(pexp_fun~locNolabelNone(ppat_constraint~loc(ppat_any~loc)typ)(eunit~loc));])letmerge_generatorsfieldl=List.filter_mapl~f:(funx->x)|>List.concat|>Deriver.resolve_allfield(* This function merges ['a derived] if they have the same [unused_code_warnings]. This
reduces the number of times we add [include struct ... end] to disable warnings. *)letmerge_derivedlists=List.fold_rightlists~init:[]~f:(funderivedacc->matchaccwith|other::otherswhenBool.equalderived.unused_code_warningsother.unused_code_warnings->{otherwithitems=derived.items@other.items}::others|_->derived::acc)letexpand_str_type_decls~ctxtrec_flagtdsvalues=letgenerators,l_err=merge_generatorsDeriver.Field.str_type_declvaluesinletl_err=List.map~f:(funerr->Ast_builder.Default.pstr_extension~loc:Location.noneerr[])l_errinletunused_code_warnings=List.for_allgenerators~f:(fun(_,generators,_)->List.for_allgenerators~f:(fun(Generator.Tt)->t.unused_code_warnings))in(* TODO: instead of disabling the unused warning for types themselves, we
should add a tag [@@unused]. *)letgenerated={items=types_used_by_derivingtds~unused_code_warnings@l_err;unused_code_warnings=false;}::Generator.apply_all~ctxt(rec_flag,tds)generatorsAst_builder.Default.pstr_extension|>merge_derivedinwrap_str~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_sig_type_decls~ctxtrec_flagtdsvalues=letgenerators,l_err=merge_generatorsDeriver.Field.sig_type_declvaluesinletl_err=List.map~f:(funerr->Ast_builder.Default.psig_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxt(rec_flag,tds)generatorsAst_builder.Default.psig_extension|>merge_derivedinwrap_sig~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_str_module_type_decl~ctxtmtdgenerators=letgenerators,l_err=Deriver.resolve_allDeriver.Field.str_module_type_declgeneratorsinletl_err=List.map~f:(funerr->Ast_builder.Default.pstr_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxtmtdgeneratorsAst_builder.Default.pstr_extension|>merge_derivedinwrap_str~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_str_module_binding~ctxtmtdgenerators=letgenerators,l_err=Deriver.resolve_allDeriver.Field.str_module_bindinggeneratorsinletl_err=List.map~f:(funerr->Ast_builder.Default.pstr_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxtmtdgeneratorsAst_builder.Default.pstr_extension|>merge_derivedinwrap_str~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_sig_module_type_decl~ctxtmtdgenerators=letgenerators,l_err=Deriver.resolve_allDeriver.Field.sig_module_type_declgeneratorsinletl_err=List.map~f:(funerr->Ast_builder.Default.psig_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxtmtdgeneratorsAst_builder.Default.psig_extension|>merge_derivedinwrap_sig~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_sig_module_decl~ctxtmtdgenerators=letgenerators,l_err=Deriver.resolve_allDeriver.Field.sig_module_declgeneratorsinletl_err=List.map~f:(funerr->Ast_builder.Default.psig_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxtmtdgeneratorsAst_builder.Default.psig_extension|>merge_derivedinwrap_sig~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_str_exception~ctxtecgenerators=letgenerators,l_err=Deriver.resolve_allDeriver.Field.str_exceptiongeneratorsinletl_err=List.map~f:(funerr->Ast_builder.Default.pstr_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxtecgeneratorsAst_builder.Default.pstr_extension|>merge_derivedinwrap_str~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_sig_exception~ctxtecgenerators=letgenerators,l_err=Deriver.resolve_allDeriver.Field.sig_exceptiongeneratorsinletl_err=List.map~f:(funerr->Ast_builder.Default.psig_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxtecgeneratorsAst_builder.Default.psig_extension|>merge_derivedinwrap_sig~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_str_type_ext~ctxttegenerators=letgenerators,l_err=Deriver.resolve_allDeriver.Field.str_type_extgeneratorsinletl_err=List.map~f:(funerr->Ast_builder.Default.pstr_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxttegeneratorsAst_builder.Default.pstr_extension|>merge_derivedinwrap_str~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_sig_type_ext~ctxttegenerators=letgenerators,l_err=Deriver.resolve_allDeriver.Field.sig_type_extgeneratorsinletl_err=List.map~f:(funerr->Ast_builder.Default.psig_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxttegeneratorsAst_builder.Default.psig_extension|>merge_derivedinwrap_sig~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_str_class_type_decls~ctxt_rec_flagcdsvalues=letgenerators,l_err=merge_generatorsDeriver.Field.str_class_type_declvaluesinletl_err=List.map~f:(funerr->Ast_builder.Default.pstr_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxtcdsgeneratorsAst_builder.Default.pstr_extension|>merge_derivedinwrap_str~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletexpand_sig_class_decls~ctxt_rec_flagcdsvalues=letgenerators,l_err=merge_generatorsDeriver.Field.sig_class_type_declvaluesinletl_err=List.map~f:(funerr->Ast_builder.Default.psig_extension~loc:Location.noneerr[])l_errinletgenerated={items=l_err;unused_code_warnings=false}::Generator.apply_all~ctxtcdsgeneratorsAst_builder.Default.psig_extension|>merge_derivedinwrap_sig~loc:(Expansion_context.Deriver.derived_item_locctxt)~hide:(not@@Expansion_context.Deriver.inlinectxt)generatedletppxlib_prefix="ppxlib."letrules_str~typ~expand_str~rule_str~rule_str_expect=letderiving_attr=mk_deriving_attr~suffix:""~prefix:ppxlib_prefixtypinletderiving_attr_expect=mk_deriving_attr~suffix:"_inline"~prefix:ppxlib_prefixtypin[rule_strderiving_attrexpand_str;rule_str_expectderiving_attr_expectexpand_str;]letrules_sig~typ~expand_sig~rule_sig~rule_sig_expect=letderiving_attr=mk_deriving_attr~suffix:""~prefix:ppxlib_prefixtypinletderiving_attr_expect=mk_deriving_attr~suffix:"_inline"~prefix:ppxlib_prefixtypin[rule_sigderiving_attrexpand_sig;rule_sig_expectderiving_attr_expectexpand_sig;]letrules~typ~expand_sig~expand_str~rule_str~rule_sig~rule_str_expect~rule_sig_expect=letprefix="ppxlib."inletderiving_attr=mk_deriving_attr~suffix:""~prefixtypinletderiving_attr_expect=mk_deriving_attr~suffix:"_inline"~prefixtypin[rule_sigderiving_attrexpand_sig;rule_strderiving_attrexpand_str;rule_str_expectderiving_attr_expectexpand_str;rule_sig_expectderiving_attr_expectexpand_sig;]letrules_type_decl=rules~typ:Type_declaration~expand_str:expand_str_type_decls~expand_sig:expand_sig_type_decls~rule_str:Context_free.Rule.attr_str_type_decl~rule_sig:Context_free.Rule.attr_sig_type_decl~rule_str_expect:Context_free.Rule.attr_str_type_decl_expect~rule_sig_expect:Context_free.Rule.attr_sig_type_decl_expectletrules_type_ext=rules~typ:Type_extension~expand_str:expand_str_type_ext~expand_sig:expand_sig_type_ext~rule_str:Context_free.Rule.attr_str_type_ext~rule_sig:Context_free.Rule.attr_sig_type_ext~rule_str_expect:Context_free.Rule.attr_str_type_ext_expect~rule_sig_expect:Context_free.Rule.attr_sig_type_ext_expectletrules_exception=rules~typ:Type_exception~expand_str:expand_str_exception~expand_sig:expand_sig_exception~rule_str:Context_free.Rule.attr_str_exception~rule_sig:Context_free.Rule.attr_sig_exception~rule_str_expect:Context_free.Rule.attr_str_exception_expect~rule_sig_expect:Context_free.Rule.attr_sig_exception_expectletrules_module_type_decl=rules~typ:Module_type_declaration~expand_str:expand_str_module_type_decl~expand_sig:expand_sig_module_type_decl~rule_str:Context_free.Rule.attr_str_module_type_decl~rule_sig:Context_free.Rule.attr_sig_module_type_decl~rule_str_expect:Context_free.Rule.attr_str_module_type_decl_expect~rule_sig_expect:Context_free.Rule.attr_sig_module_type_decl_expectletrules_module_binding=rules_str~typ:Module_binding~expand_str:expand_str_module_binding~rule_str:Context_free.Rule.attr_str_module_binding~rule_str_expect:Context_free.Rule.attr_str_module_binding_expectletrules_module_decl=rules_sig~typ:Module_declaration~expand_sig:expand_sig_module_decl~rule_sig:Context_free.Rule.attr_sig_module_declaration~rule_sig_expect:Context_free.Rule.attr_sig_module_declaration_expectletrules_class_type_decl=rules~typ:Class_type_decl~expand_str:expand_str_class_type_decls~expand_sig:expand_sig_class_decls~rule_str:Context_free.Rule.attr_str_class_type_decl~rule_sig:Context_free.Rule.attr_sig_class_type_decl~rule_str_expect:Context_free.Rule.attr_str_class_type_decl_expect~rule_sig_expect:Context_free.Rule.attr_sig_class_type_decl_expectlet()=letrules=[rules_type_decl;rules_type_ext;rules_module_binding;rules_module_decl;rules_exception;rules_module_type_decl;rules_class_type_decl;]|>List.concatinDriver.register_transformation"deriving"~aliases:["type_conv"]~rules