123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334(* Js_of_ocaml compiler
* http://www.ocsigen.org/js_of_ocaml/
* Copyright (C) 2010 Jérôme Vouillon
* Laboratoire PPS - CNRS Université Paris Diderot
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, with linking exception;
* either version 2.1 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*)open!StdlibmoduleNum:sigtypet(** Conversions *)valof_string_unsafe:string->tvalof_int32:int32->tvalof_float:float->tvalto_string:t->stringvalto_int32:t->int32(** Predicates *)valis_zero:t->boolvalis_one:t->boolvalis_neg:t->bool(** Arithmetic *)valadd:t->t->tvalneg:t->tend=structtypet=stringletof_string_unsafes=sletto_strings=sletto_int32s=ifString.is_prefixs~prefix:"0"&&String.lengths>1&&String.for_alls~f:(function|'0'..'7'->true|_->false)then(* octal notation *)Int32.of_string("0o"^s)elseInt32.of_stringsletof_int32=Int32.to_stringletof_floatv=matchFloat.classify_floatvwith|FP_nan->"NaN"|FP_zero->(* [1/-0] < 0. seems to be the only way to detect -0 in JavaScript *)ifFloat.(1./.v<0.)then"-0."else"0."|FP_infinite->ifFloat.(v<0.)then"-Infinity"else"Infinity"|FP_normal|FP_subnormal->letvint=int_of_floatvinifFloat.equal(float_of_intvint)vthenPrintf.sprintf"%d."vintelselets1=Printf.sprintf"%.12g"vinifFloat.equalv(float_of_strings1)thens1elselets2=Printf.sprintf"%.15g"vinifFloat.equalv(float_of_strings2)thens2elsePrintf.sprintf"%.18g"vletis_zeros=String.equals"0"letis_ones=String.equals"1"letis_negs=Char.equals.[0]'-'letnegs=matchString.drop_prefixs~prefix:"-"with|None->"-"^s|Somes->sletaddab=of_int32(Int32.add(to_int32a)(to_int32b))endmoduleLabel=structtypet=|Lofint|Sofstringletprinter=VarPrinter.createVarPrinter.Alphabet.javascriptletzero=L0letsucc=function|Lt->L(succt)|S_->assertfalseletto_string=function|Lt->VarPrinter.to_stringprintert|Ss->sletof_strings=Ssendtypelocation=|PiofParse_info.t|N|Utypeidentifier=stringtypeident_string={name:identifier;var:Code.Var.toption;loc:location}typeident=|Sofident_string|VofCode.Var.t(* A.3 Expressions *)andarray_litteral=element_listandelement_list=expressionoptionlistandbinop=|Eq|StarEq|SlashEq|ModEq|PlusEq|MinusEq|LslEq|AsrEq|LsrEq|BandEq|BxorEq|BorEq|Or|And|Bor|Bxor|Band|EqEq|NotEq|EqEqEq|NotEqEq|Lt|Le|Gt|Ge|InstanceOf|In|Lsl|Lsr|Asr|Plus|Minus|Mul|Div|Modandunop=|Not|Neg|Pl|Typeof|Void|Delete|Bnot|IncrA|DecrA|IncrB|DecrBandarguments=expressionlistandproperty_name_and_value_list=(property_name*expression)listandproperty_name=|PNIofidentifier|PNSofstring|PNNofNum.tandexpression=|ESeqofexpression*expression|ECondofexpression*expression*expression|EBinofbinop*expression*expression|EUnofunop*expression|ECallofexpression*arguments*location|EAccessofexpression*expression|EDotofexpression*identifier|ENewofexpression*argumentsoption|EVarofident|EFunoffunction_expression|EStrofstring*[`Bytes|`Utf8]|EArrofarray_litteral|EBoolofbool|ENumofNum.t|EObjofproperty_name_and_value_list|EQuoteofstring|ERegexpofstring*stringoption(****)(* A.4 Statements *)andstatement=|Blockofblock|Variable_statementofvariable_declarationlist|Empty_statement|Expression_statementofexpression|If_statementofexpression*(statement*location)*(statement*location)option|Do_while_statementof(statement*location)*expression|While_statementofexpression*(statement*location)|For_statementof(expressionoption,variable_declarationlist)either*expressionoption*expressionoption*(statement*location)|ForIn_statementof(expression,variable_declaration)either*expression*(statement*location)|Continue_statementofLabel.toption|Break_statementofLabel.toption|Return_statementofexpressionoption(* | With_statement of expression * statement *)|Labelled_statementofLabel.t*(statement*location)|Switch_statementofexpression*case_clauselist*statement_listoption*case_clauselist|Throw_statementofexpression|Try_statementofblock*(ident*block)option*blockoption|Debugger_statementand('left,'right)either=|Leftof'left|Rightof'rightandblock=statement_listandstatement_list=(statement*location)listandvariable_declaration=ident*initialiseroptionandcase_clause=expression*statement_listandinitialiser=expression*location(****)(* A.5 Functions and programs *)andfunction_declaration=ident*formal_parameter_list*function_body*locationandfunction_expression=identoption*formal_parameter_list*function_body*locationandformal_parameter_list=identlistandfunction_body=source_elementsandprogram=source_elementsandsource_elements=(source_element*location)listandsource_element=|Statementofstatement|Function_declarationoffunction_declarationletcompare_identt1t2=matcht1,t2with|Vv1,Vv2->Code.Var.comparev1v2|S{name=s1;var=v1;loc=l1},S{name=s2;var=v2;loc=l2}->(matchString.compares1s2with|0->(matchOption.compareCode.Var.comparev1v2with|0->Poly.comparel1l2|n->n)|n->n)|S_,V_->-1|V_,S_->1exceptionNot_an_identletis_ident=letl=Array.init256~f:(funi->letc=Char.chriinmatchcwith|'a'..'z'|'A'..'Z'|'_'|'$'->1|'0'..'9'->2|_->0)infuns->(not(StringSet.memsReserved.keyword))&&tryfori=0toString.lengths-1doletcode=l.(Char.codes.[i])inifi=0then(ifcode<>1thenraiseNot_an_ident)elseifcode<1thenraiseNot_an_identdone;truewithNot_an_ident->falseletident?(loc=N)?varname=S{name;var;loc}moduleIdentSet=Set.Make(structtypet=identletcompare=compare_identend)moduleIdentMap=Map.Make(structtypet=identletcompare=compare_identend)