Legend:
Page
Library
Module
Module type
Parameter
Class
Class type
Source
Source file parsing_hacks_lib.ml
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286(* Yoann Padioleau
*
* Copyright (C) 2002-2008 Yoann Padioleau
* Copyright (C) 2011 Facebook
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License (GPL)
* version 2 as published by the Free Software Foundation.
*
* 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
* file license.txt for more details.
*)openCommonmoduleFlag=Flag_parsingmoduleFlag_cpp=Flag_parsing_cppmodulePI=Parse_infomoduleTH=Token_helpers_cppopenParser_cppopenToken_views_cpp(*****************************************************************************)(* Wrappers *)(*****************************************************************************)letpr2,_pr2_once=Common2.mk_pr2_wrappersFlag.verbose_parsing(*****************************************************************************)(* Helpers *)(*****************************************************************************)(*
* In the following, there are some harcoded names of types or macros
* but they are not used by our heuristics! They are just here to
* enable to detect false positive by printing only the typedef/macros
* that we don't know yet. If we print everything, then we can easily
* get lost with too much verbose tracing information. So those
* functions "filter" some messages. So our heuristics are still good,
* there is no more (or not that much) hardcoded linux stuff.
*)letmsg_genis_knownprinters=ifnot(!Flag_cpp.filter_msg)thenprinterselseifnot(is_knowns)thenprintersletposii=Parse_info.string_of_infoii(*****************************************************************************)(* Some debugging functions *)(*****************************************************************************)letpr2_pps=if!Flag_cpp.debug_ppthenCommon.pr2("PP-"^s)letpr2_cpluspluss=if!Flag_cpp.debug_cplusplusthenCommon.pr2("C++-"^s)letpr2_typedefs=if!Flag_cpp.debug_typedefthenCommon.pr2("TYPEDEF-"^s)letmsg_change_toktok=matchtokwith(* mostly in parsing_hacks_define.ml *)|TIdent_Define(_s,_ii)->()|TOPar_Define(_ii)->()|TCommentNewline_DefineEndOfMacro_->()(* mostly in parsing_hacks.ml *)|TIdent_Typedef(s,ii)->(* todo? also do LP.add_typedef_root s ??? *)s+>msg_gen(funs->matchswith|"u_char"|"u_short"|"u_int"|"u_long"|"u8"|"u16"|"u32"|"u64"|"s8"|"s16"|"s32"|"s64"|"__u8"|"__u16"|"__u32"|"__u64"->true|"acpi_handle"|"acpi_status"->true|"FILE"|"DIR"->true|swhens=~".*_t$"->true|_->false)(funs->pr2_typedef(spf"promoting %s at %s "s(posii)))(* mostly in parsing_hacks_pp.ml *)(* cppext: *)|TComment_Pp(directive,ii)->lets=PI.str_of_infoiiin(matchdirective,swith|Token_cpp.CppMacro,_->pr2_pp(spf"MACRO: commented at %s"(posii))|Token_cpp.CppDirective,_whens=~"#define.*"->pr2_pp(spf"DEFINE: commented at %s"(posii));|Token_cpp.CppDirective,_whens=~"#include.*"->pr2_pp(spf"INCLUDE: commented at %s"(posii));|Token_cpp.CppDirective,_whens=~"#if.*"->pr2_pp(spf"IFDEF: commented at %s"(posii));|Token_cpp.CppDirective,_whens=~"#undef.*"->pr2_pp(spf"UNDEF: commented at %s"(posii));|Token_cpp.CppDirective,_->pr2_pp(spf"OTHER: commented directive at %s"(posii));|_->(* todo? *)())|TOBrace_DefineInitii->pr2_pp(spf"DEFINE: initializer at %s"(posii))|TIdent_MacroStringii->lets=PI.str_of_infoiiins+>msg_gen(funs->matchswith|"REVISION"|"UTS_RELEASE"|"SIZE_STR"|"DMA_STR"->true(* s when s =~ ".*STR.*" -> true *)|_->false)(funs->pr2_pp(spf"MACRO: string-macro %s at %s "s(posii)))|TIdent_MacroStmtii->pr2_pp(spf"MACRO: stmt-macro at %s"(posii));|TIdent_MacroDecl(s,ii)->s+>msg_gen(funs->matchswith|"DECLARE_MUTEX"|"DECLARE_COMPLETION"|"DECLARE_RWSEM"|"DECLARE_WAITQUEUE"|"DECLARE_WAIT_QUEUE_HEAD"|"DEFINE_SPINLOCK"|"DEFINE_TIMER"|"DEVICE_ATTR"|"CLASS_DEVICE_ATTR"|"DRIVER_ATTR"|"SENSOR_DEVICE_ATTR"|"LIST_HEAD"|"DECLARE_WORK"|"DECLARE_TASKLET"|"PORT_ATTR_RO"|"PORT_PMA_ATTR"|"DECLARE_BITMAP"->true(*
| s when s =~ "^DECLARE_.*" -> true
| s when s =~ ".*_ATTR$" -> true
| s when s =~ "^DEFINE_.*" -> true
| s when s =~ "NS_DECL.*" -> true
*)|_->false)(fun_s->pr2_pp(spf"MACRO: macro-declare at %s"(posii)))|Tconst_MacroDeclConstii->pr2_pp(spf"MACRO: retag const at %s"(posii))|TAny_Actionii->pr2_pp(spf"ACTION: retag at %s"(posii))|TCPar_EOLii->pr2_pp(spf"MISC: retagging ) %s"(posii))(* mostly in parsing_hacks_cpp.ml *)(* c++ext: *)|TComment_Cpp(directive,ii)->lets=PI.str_of_infoiiin(matchdirective,swith|Token_cpp.CplusplusTemplate,_->pr2_cplusplus(spf"COM-TEMPLATE: commented at %s"(posii))|Token_cpp.CplusplusQualifier,_->pr2_cplusplus(spf"COM-QUALIFIER: commented at %s"(posii)))|TOPar_CplusplusInitii->pr2_cplusplus(spf"constructor initializer at %s"(posii))|TOCro_newii|TCCro_newii->pr2_cplusplus(spf"new [] at %s"(posii))|TInf_Templateii|TSup_Templateii->pr2_cplusplus(spf"template <> at %s"(posii))|Tchar_Constrii|Tint_Constrii|Tfloat_Constrii|Tdouble_Constrii|Tshort_Constrii|Tlong_Constrii|Tbool_Constrii|Tunsigned_Constrii|Tsigned_Constrii->pr2_cplusplus(spf"constructed object builtin at %s"(posii));|TIdent_TypedefConstr(s,ii)->pr2_cplusplus(spf"constructed object %s at %s"s(posii))|TIdent_ClassnameInQualifier(s,ii)->pr2_cplusplus(spf"CLASSNAME: in qualifier context %s at %s "s(posii))|TIdent_Constructor(s,ii)->pr2_cplusplus(spf"CONSTRUCTOR: found %s at %s "s(posii))|TIdent_Templatename(s,ii)->pr2_cplusplus(spf"TEMPLATENAME: found %s at %s"s(posii))|TColCol_BeforeTypedefii->pr2_typedef(spf"RECLASSIF colcol to colcol2 at %s"(posii))|TIdent_ClassnameInQualifier_BeforeTypedef(s,ii)->pr2_typedef(spf"RECLASSIF class in qualifier %s at %s"s(posii))|TIdent_TemplatenameInQualifier_BeforeTypedef(s,ii)->pr2_typedef(spf"RECLASSIF template in qualifier %s at %s"s(posii))|_->raiseTodoletmsg_contexttctx=letctx_str=matchctxwith|InParameter->"InParameter"|InArgument->"InArgument"|_->raiseImpossibleinpr2_cplusplus(spf"CONTEXT: %s at %s"ctx_str(pos(TH.info_of_tokt)))letchange_tokextended_toktok=msg_change_toktok;(* otherwise parse_c will be lost if don't find a EOF token
* why? because paren detection had a pb because of
* some ifdef-exp?
*)ifTH.is_eofextended_tok.tthenpr2"PB: wierd, I try to tag an EOF token as something else"elseextended_tok.t<-tokletfresh_toktok=msg_change_toktok;tok(* normally the caller have first filtered the set of tokens to have
* a clearer "view" to work on
*)letset_as_commentcppkindx=assert(not(TH.is_real_commentx.t));change_tokx(TComment_Pp(cppkind,TH.info_of_tokx.t))(*****************************************************************************)(* The regexp and basic view definitions *)(*****************************************************************************)(*
val regexp_macro: Str.regexp
val regexp_annot: Str.regexp
val regexp_declare: Str.regexp
val regexp_foreach: Str.regexp
val regexp_typedef: Str.regexp
*)(* opti: better to built then once and for all, especially regexp_foreach *)letregexp_macro=Str.regexp"^[A-Z_][A-Z_0-9]*$"(* linuxext: *)letregexp_declare=Str.regexp".*DECLARE.*"(* firefoxext: *)letregexp_ns_decl_like=Str.regexp("\\("^"NS_DECL_\\|NS_DECLARE_\\|NS_IMPL_\\|"^"NS_IMPLEMENT_\\|NS_INTERFACE_\\|NS_FORWARD_\\|NS_HTML_\\|"^"NS_DISPLAY_\\|NS_IMPL_\\|"^"TX_DECL_\\|DOM_CLASSINFO_\\|NS_CLASSINFO_\\|IMPL_INTERNAL_\\|"^"ON_\\|EVT_\\|NS_UCONV_\\|NS_GENERIC_\\|NS_COM_"^"\\).*")