[anjuta/cxxparser] cxxparser: Added grammar files.
- From: Massimo Cora' <mcora src gnome org>
- To: svn-commits-list gnome org
- Subject: [anjuta/cxxparser] cxxparser: Added grammar files.
- Date: Sun, 26 Jul 2009 20:07:51 +0000 (UTC)
commit 4e9f9acafb8c0b0bf92ea59b39977c0346651870
Author: Massimo Corà <mcora src gnome org>
Date: Sun Jul 26 21:57:40 2009 +0200
cxxparser: Added grammar files.
These won't be used to actually compile the code. But it's useful to have them with us.
plugins/symbol-db/cxxparser/grammars/README | 5 +
plugins/symbol-db/cxxparser/grammars/cpp.l | 424 ++++++++++++++
.../symbol-db/cxxparser/grammars/cpp_func_parser.y | 404 ++++++++++++++
.../cxxparser/grammars/cpp_scope_grammar.y | 576 ++++++++++++++++++++
.../cxxparser/grammars/cpp_variables_grammar.y | 530 ++++++++++++++++++
.../symbol-db/cxxparser/grammars/expr_grammar.y | 388 +++++++++++++
plugins/symbol-db/cxxparser/grammars/expr_lexer.l | 318 +++++++++++
7 files changed, 2645 insertions(+), 0 deletions(-)
---
diff --git a/plugins/symbol-db/cxxparser/grammars/README b/plugins/symbol-db/cxxparser/grammars/README
new file mode 100644
index 0000000..3870908
--- /dev/null
+++ b/plugins/symbol-db/cxxparser/grammars/README
@@ -0,0 +1,5 @@
+These grammars have been used to generate the parsers/lexers using yacc/flex.
+I put them here but they won't be used in generation of the parsers at compile time.
+
+Grammars took from CodeLite CxxParser
+
diff --git a/plugins/symbol-db/cxxparser/grammars/cpp.l b/plugins/symbol-db/cxxparser/grammars/cpp.l
new file mode 100644
index 0000000..0be45f0
--- /dev/null
+++ b/plugins/symbol-db/cxxparser/grammars/cpp.l
@@ -0,0 +1,424 @@
+%{
+/* Included code before lex code */
+/*************** Includes and Defines *****************************/
+
+
+#include "map"
+#include "cpp_lexer.h" // YACC generated definitions based on C++ grammar
+#include "errno.h"
+
+#define YYSTYPE std::string
+
+#include "string"
+#include <stdlib.h>
+#include <string.h>
+#include <vector>
+
+extern std::string cl_scope_lval;
+extern std::string cl_var_lval;
+extern std::string cl_func_lval;
+
+std::vector<std::string> currentScope;
+
+bool setLexerInput(const std::string &in, const std::map<std::string, std::string> &ignoreTokens);
+void setUseIgnoreMacros(bool ignore);
+
+std::string getCurrentScope();
+void printScopeName();
+void cl_scope_lex_clean();
+void cl_scope_less(int count);
+
+//we keep a very primitive map with only symbol name
+//that we encountered so far
+std::map<std::string, std::string> g_symbols;
+std::map<std::string, std::string> g_macros;
+
+static std::map<std::string, std::string> g_ignoreList;
+static bool gs_useMacroIgnore = true;
+
+bool isaTYPE(char *string);
+bool isaMACRO(char *string);
+bool isignoredToken(char *string);
+
+static bool defineFound = false;
+
+/* Prototypes */
+#define WHITE_RETURN(x) /* do nothing */
+
+#define PA_KEYWORD_RETURN(x) RETURN_VAL(x) /* standard C PArser Keyword */
+#define CPP_KEYWORD_RETURN(x) PA_KEYWORD_RETURN(x) /* C++ keyword */
+#define PPPA_KEYWORD_RETURN(x) RETURN_VAL(x) /* both PreProcessor and PArser keyword */
+#define PP_KEYWORD_RETURN(x) IDENTIFIER_RETURN()
+
+#define IDENTIFIER_RETURN(){\
+ if(isaTYPE(yytext)){\
+ RETURN_VAL(LE_TYPEDEFname);\
+ }else if(isaMACRO(yytext)){\
+ RETURN_VAL(LE_MACRO);\
+ }else if(isignoredToken(yytext)){\
+ }else{ RETURN_VAL(LE_IDENTIFIER);}\
+ }
+
+
+#define PPOP_RETURN(x) RETURN_VAL((int)*yytext) /* PreProcess and Parser operator */
+#define NAMED_PPOP_RETURN(x) RETURN_VAL(x)
+#define ASCIIOP_RETURN(x) RETURN_VAL((int)*yytext) /* a single character operator */
+#define NAMEDOP_RETURN(x) RETURN_VAL(x) /* a multichar operator, with a name */
+
+#define NUMERICAL_RETURN(x) RETURN_VAL(x) /* some sort of constant */
+#define LITERAL_RETURN(x) RETURN_VAL(x) /* a string literal */
+#define C_COMMENT_RETURN(x) RETURN_VAL(x) /* C Style comment */
+#define RETURN_VAL(x) {\
+ cl_scope_lval = yytext;\
+ cl_var_lval = yytext;\
+ cl_func_lval = yytext;\
+ return(x);}
+
+%}
+
+%option yylineno
+
+identifier [a-zA-Z_][0-9a-zA-Z_]*
+
+exponent_part [eE][-+]?[0-9]+
+fractional_constant ([0-9]*"."[0-9]+)|([0-9]+".")
+floating_constant (({fractional_constant}{exponent_part}?)|([0-9]+{exponent_part}))[FfLl]?
+
+integer_suffix_opt ([uU]?[lL]?)|([lL][uU])
+decimal_constant [1-9][0-9]*{integer_suffix_opt}
+octal_constant "0"[0-7]*{integer_suffix_opt}
+hex_constant "0"[xX][0-9a-fA-F]+{integer_suffix_opt}
+
+simple_escape [abfnrtv'"?\\]
+octal_escape [0-7]{1,3}
+hex_escape "x"[0-9a-fA-F]+
+
+escape_sequence [\\]({simple_escape}|{octal_escape}|{hex_escape})
+c_char [^'\\\n]|{escape_sequence}
+s_char [^"\\\n]|{escape_sequence}
+
+h_tab [\011]
+form_feed [\014]
+v_tab [\013]
+c_return [\015]
+
+horizontal_white [ ]|{h_tab}
+
+%x PREPR
+%x WRAP_PREP
+%x CPP_COMMENT
+%x C_COMMENT
+
+%%
+
+"/*" {
+ BEGIN C_COMMENT;
+ }
+
+"//" {
+ BEGIN CPP_COMMENT;
+ }
+
+{horizontal_white}+ {
+ WHITE_RETURN(' ');
+ }
+
+({v_tab}|{c_return}|{form_feed})+ {
+ WHITE_RETURN(' ');
+ }
+
+
+({horizontal_white}|{v_tab}|{c_return}|{form_feed})*"\n" {
+ WHITE_RETURN('\n');
+ }
+
+auto {PA_KEYWORD_RETURN(LE_AUTO);}
+break {PA_KEYWORD_RETURN(LE_BREAK);}
+case {PA_KEYWORD_RETURN(LE_CASE);}
+char {PA_KEYWORD_RETURN(LE_CHAR);}
+const {PA_KEYWORD_RETURN(LE_CONST);}
+continue {PA_KEYWORD_RETURN(LE_CONTINUE);}
+default {PA_KEYWORD_RETURN(LE_DEFAULT);}
+define {PP_KEYWORD_RETURN(LE_DEFINE);}
+defined {PP_KEYWORD_RETURN(LE_OPDEFINED);}
+do {PA_KEYWORD_RETURN(LE_DO);}
+double {PA_KEYWORD_RETURN(LE_DOUBLE);}
+elif {PP_KEYWORD_RETURN(LE_ELIF);}
+else {PPPA_KEYWORD_RETURN(LE_ELSE);}
+endif {PP_KEYWORD_RETURN(LE_ENDIF);}
+enum {PA_KEYWORD_RETURN(LE_ENUM);}
+error {PP_KEYWORD_RETURN(LE_ERROR);}
+extern {PA_KEYWORD_RETURN(LE_EXTERN);}
+float {PA_KEYWORD_RETURN(LE_FLOAT);}
+for {PA_KEYWORD_RETURN(LE_FOR);}
+goto {PA_KEYWORD_RETURN(LE_GOTO);}
+if {PPPA_KEYWORD_RETURN(LE_IF);}
+ifdef {PP_KEYWORD_RETURN(LE_IFDEF);}
+ifndef {PP_KEYWORD_RETURN(LE_IFNDEF);}
+include {PP_KEYWORD_RETURN(LE_INCLUDE); }
+int {PA_KEYWORD_RETURN(LE_INT);}
+line {PP_KEYWORD_RETURN(LE_LINE);}
+long {PA_KEYWORD_RETURN(LE_LONG);}
+pragma {PP_KEYWORD_RETURN(LE_PRAGMA);}
+register {PA_KEYWORD_RETURN(LE_REGISTER);}
+return {PA_KEYWORD_RETURN(LE_RETURN);}
+short {PA_KEYWORD_RETURN(LE_SHORT);}
+signed {PA_KEYWORD_RETURN(LE_SIGNED);}
+sizeof {PA_KEYWORD_RETURN(LE_SIZEOF);}
+static {PA_KEYWORD_RETURN(LE_STATIC);}
+struct {PA_KEYWORD_RETURN(LE_STRUCT);}
+switch {PA_KEYWORD_RETURN(LE_SWITCH);}
+typedef {PA_KEYWORD_RETURN(LE_TYPEDEF);}
+undef {PP_KEYWORD_RETURN(LE_UNDEF);}
+union {PA_KEYWORD_RETURN(LE_UNION);}
+unsigned {PA_KEYWORD_RETURN(LE_UNSIGNED);}
+void {PA_KEYWORD_RETURN(LE_VOID);}
+volatile {PA_KEYWORD_RETURN(LE_VOLATILE);}
+while {PA_KEYWORD_RETURN(LE_WHILE);}
+
+
+class {CPP_KEYWORD_RETURN(LE_CLASS);}
+namespace {CPP_KEYWORD_RETURN(LE_NAMESPACE);}
+delete {CPP_KEYWORD_RETURN(LE_DELETE);}
+friend {CPP_KEYWORD_RETURN(LE_FRIEND);}
+inline {CPP_KEYWORD_RETURN(LE_INLINE);}
+new {CPP_KEYWORD_RETURN(LE_NEW);}
+operator {CPP_KEYWORD_RETURN(LE_OPERATOR);}
+overload {CPP_KEYWORD_RETURN(LE_OVERLOAD);}
+protected {CPP_KEYWORD_RETURN(LE_PROTECTED);}
+private {CPP_KEYWORD_RETURN(LE_PRIVATE);}
+public {CPP_KEYWORD_RETURN(LE_PUBLIC);}
+this {CPP_KEYWORD_RETURN(LE_THIS);}
+virtual {CPP_KEYWORD_RETURN(LE_VIRTUAL);}
+template {CPP_KEYWORD_RETURN(LE_TEMPLATE);}
+typename {CPP_KEYWORD_RETURN(LE_TYPENAME);}
+dynamic_cast {CPP_KEYWORD_RETURN(LE_DYNAMIC_CAST);}
+static_cast {CPP_KEYWORD_RETURN(LE_STATIC_CAST);}
+const_cast {CPP_KEYWORD_RETURN(LE_CONST_CAST);}
+reinterpret_cast {CPP_KEYWORD_RETURN(LE_REINTERPRET_CAST);}
+using {CPP_KEYWORD_RETURN(LE_USING);}
+throw {CPP_KEYWORD_RETURN(LE_THROW);}
+catch {CPP_KEYWORD_RETURN(LE_CATCH);}
+{identifier} {IDENTIFIER_RETURN();}
+{decimal_constant} {NUMERICAL_RETURN(LE_INTEGERconstant);}
+{octal_constant} {NUMERICAL_RETURN(LE_OCTALconstant);}
+{hex_constant} {NUMERICAL_RETURN(LE_HEXconstant);}
+{floating_constant} {NUMERICAL_RETURN(LE_FLOATINGconstant);}
+
+
+"L"?[']{c_char}+['] {
+ NUMERICAL_RETURN(LE_CHARACTERconstant);
+ }
+
+
+"L"?["]{s_char}*["] {
+ LITERAL_RETURN(LE_STRINGliteral);}
+
+
+
+
+"(" {PPOP_RETURN(LE_LP);}
+")" {PPOP_RETURN(LE_RP);}
+"," {PPOP_RETURN(LE_COMMA);}
+^({horizontal_white})*"#" {BEGIN PREPR;}
+"{" {ASCIIOP_RETURN(LE_LC);}
+"}" {ASCIIOP_RETURN(LE_RC);}
+"[" {ASCIIOP_RETURN(LE_LB);}
+"]" {ASCIIOP_RETURN(LE_RB);}
+"." {ASCIIOP_RETURN(LE_DOT);}
+"&" {ASCIIOP_RETURN(LE_AND);}
+"*" {ASCIIOP_RETURN(LE_STAR);}
+"+" {ASCIIOP_RETURN(LE_PLUS);}
+"-" {ASCIIOP_RETURN(LE_MINUS);}
+"~" {ASCIIOP_RETURN(LE_NEGATE);}
+"!" {ASCIIOP_RETURN(LE_NOT);}
+"/" {ASCIIOP_RETURN(LE_DIV);}
+"%" {ASCIIOP_RETURN(LE_MOD);}
+"<" {ASCIIOP_RETURN(LE_LT);}
+">" {ASCIIOP_RETURN(LE_GT);}
+"^" {ASCIIOP_RETURN(LE_XOR);}
+"|" {ASCIIOP_RETURN(LE_PIPE);}
+"?" {ASCIIOP_RETURN(LE_QUESTION);}
+":" {ASCIIOP_RETURN(LE_COLON);}
+";" {ASCIIOP_RETURN(LE_SEMICOLON);}
+"=" {ASCIIOP_RETURN(LE_ASSIGN);}
+
+".*" {NAMEDOP_RETURN(LE_DOTstar);}
+"::" {NAMEDOP_RETURN(LE_CLCL);}
+"->" {NAMEDOP_RETURN(LE_ARROW);}
+"->*" {NAMEDOP_RETURN(LE_ARROWstar);}
+"++" {NAMEDOP_RETURN(LE_ICR);}
+"--" {NAMEDOP_RETURN(LE_DECR);}
+"<<" {NAMEDOP_RETURN(LE_LS);}
+">>" {NAMEDOP_RETURN(LE_RS);}
+"<=" {NAMEDOP_RETURN(LE_LE);}
+">=" {NAMEDOP_RETURN(LE_GE);}
+"==" {NAMEDOP_RETURN(LE_EQ);}
+"!=" {NAMEDOP_RETURN(LE_NE);}
+"&&" {NAMEDOP_RETURN(LE_ANDAND);}
+"||" {NAMEDOP_RETURN(LE_OROR);}
+"*=" {NAMEDOP_RETURN(LE_MULTassign);}
+"/=" {NAMEDOP_RETURN(LE_DIVassign);}
+"%=" {NAMEDOP_RETURN(LE_MODassign);}
+"+=" {NAMEDOP_RETURN(LE_PLUSassign);}
+"-=" {NAMEDOP_RETURN(LE_MINUSassign);}
+"<<=" {NAMEDOP_RETURN(LE_LSassign);}
+">>=" {NAMEDOP_RETURN(LE_RSassign);}
+"&=" {NAMEDOP_RETURN(LE_ANDassign);}
+"^=" {NAMEDOP_RETURN(LE_ERassign);}
+"|=" {NAMEDOP_RETURN(LE_ORassign);}
+"..." {NAMEDOP_RETURN(LE_ELLIPSIS);}
+<<EOF>> {
+ //reset lexer
+ yyterminate();
+ }
+. {return yytext[0];}
+<PREPR>\n {
+ defineFound = false;
+ cl_scope_lineno++;
+ BEGIN INITIAL;
+ }
+<PREPR>\\ {
+ BEGIN WRAP_PREP;
+ }
+<PREPR>define {
+ defineFound = true;
+ }
+<WRAP_PREP>\n {
+ cl_scope_lineno++;
+ BEGIN PREPR;
+ }
+<WRAP_PREP>{identifier} {
+ if(defineFound)
+ {
+ defineFound = false;
+ g_macros[yytext] = true;
+ }
+ }
+<PREPR>{identifier} {
+ if(defineFound)
+ {
+ defineFound = false;
+ g_macros[yytext] = true;
+ }
+ }
+<WRAP_PREP>. {}
+<PREPR>. {}
+<CPP_COMMENT>\n {BEGIN INITIAL;}
+<CPP_COMMENT>. {}
+<C_COMMENT>"*/" {BEGIN INITIAL;}
+<C_COMMENT>. {}
+%%
+
+bool isaTYPE(char *string)
+{
+ return g_symbols.find(string) != g_symbols.end();
+}
+
+bool isignoredToken(char *string)
+{
+ std::map<std::string, std::string>::iterator iter = g_ignoreList.find(string);
+ if(iter == g_ignoreList.end()){
+ /* this string is not in the ignore macro list */
+ return false;
+ } else {
+ /* it exist, but maybe it has a replacement */
+ return iter->second.empty();
+ }
+}
+
+bool isaMACRO(char *string)
+{
+ if(gs_useMacroIgnore) {
+ return g_macros.find(string) != g_macros.end();
+ }else{
+ return false;
+ }
+}
+
+void cl_scope_lex_clean()
+{
+ yy_flush_buffer(YY_CURRENT_BUFFER);
+ yy_delete_buffer(YY_CURRENT_BUFFER);
+ cl_scope_lineno = 1;
+ currentScope.clear();
+ g_symbols.clear();
+ g_macros.clear();
+}
+
+/**
+ * scope util functions
+ */
+void printScopeName()
+{
+ /*
+ if(currentScope.empty())
+ {
+ printf("%d: current scope is global scope\n", cl_scope_lineno );
+ }
+ else
+ {
+ printf("%d: current scope is %s\n", cl_scope_lineno, getCurrentScope().c_str());
+ }
+ */
+}
+
+void increaseScope()
+{
+ static int value = 0;
+ std::string scopeName("__anon_");
+
+ char buf[100];
+ sprintf(buf, "%d", value++);
+ scopeName += buf;
+ currentScope.push_back(scopeName);
+}
+
+std::string getCurrentScope()
+{
+ //format scope name
+ std::string scope;
+ if(currentScope.empty()){
+ return "";
+ }
+
+ std::vector<std::string> tmpscope(currentScope);
+
+ while( tmpscope.empty() == false ){
+ std::string _scope = tmpscope.front();
+ tmpscope.erase(tmpscope.begin());
+
+ if(_scope.find("__anon_") == (size_t)-1 && _scope.empty() == false){
+ scope += _scope;
+ scope += "::";
+ }
+ }
+
+ //remove the trailing '::'
+ scope.erase(scope.find_last_not_of(":")+1);
+ return scope;
+}
+
+/*******************************************************************/
+bool setLexerInput(const std::string &in, const std::map<std::string, std::string> &ignoreTokens)
+{
+ BEGIN INITIAL;
+ yy_scan_string(in.c_str());
+
+ g_ignoreList = ignoreTokens;
+
+ //update the working file name
+ return true;
+}
+
+void setUseIgnoreMacros(bool ignore) {
+ gs_useMacroIgnore = ignore;
+}
+
+int yywrap(){
+ return 1;
+}
+
+void cl_scope_less(int count){
+ yyless(count);
+}
diff --git a/plugins/symbol-db/cxxparser/grammars/cpp_func_parser.y b/plugins/symbol-db/cxxparser/grammars/cpp_func_parser.y
new file mode 100644
index 0000000..6e66b7c
--- /dev/null
+++ b/plugins/symbol-db/cxxparser/grammars/cpp_func_parser.y
@@ -0,0 +1,404 @@
+%{
+// Copyright Eran Ifrah(c)
+%}
+
+%{
+/*************** Includes and Defines *****************************/
+#include "string"
+#include "vector"
+#include "stdio.h"
+#include "map"
+#include "function.h"
+
+#define YYDEBUG_LEXER_TEXT (cl_func_lval)
+#define YYSTYPE std::string
+#define YYDEBUG 0 /* get the pretty debugging code to compile*/
+
+#ifdef yylex
+#undef yylex
+#define yylex cl_scope_lex
+#endif
+
+int cl_func_parse();
+void cl_func_error(char *string);
+
+static FunctionList *g_funcs = NULL;
+static clFunction curr_func;
+
+//---------------------------------------------
+// externs defined in the lexer
+//---------------------------------------------
+extern char *cl_func_text;
+extern int cl_scope_lex();
+extern bool setLexerInput(const std::string &in, const std::map<std::string, std::string> &ignoreTokens);
+extern int cl_scope_lineno;
+extern void cl_scope_lex_clean();
+
+
+/*************** Standard ytab.c continues here *********************/
+%}
+
+/*************************************************************************/
+
+/* This group is used by the C/C++ language parser */
+%token LE_AUTO LE_DOUBLE LE_INT LE_STRUCT
+%token LE_BREAK LE_ELSE LE_LONG LE_SWITCH
+%token LE_CASE LE_ENUM LE_REGISTER LE_TYPEDEF
+%token LE_CHAR LE_EXTERN LE_RETURN LE_UNION
+%token LE_CONST LE_FLOAT LE_SHORT LE_UNSIGNED
+%token LE_CONTINUE LE_FOR LE_SIGNED LE_VOID
+%token LE_DEFAULT LE_GOTO LE_SIZEOF LE_VOLATILE
+%token LE_DO LE_IF LE_STATIC LE_WHILE
+
+/* The following are used in C++ only. ANSI C would call these IDENTIFIERs */
+%token LE_NEW LE_DELETE
+%token LE_THIS
+%token LE_OPERATOR
+%token LE_CLASS
+%token LE_PUBLIC LE_PROTECTED LE_PRIVATE
+%token LE_VIRTUAL LE_FRIEND
+%token LE_INLINE LE_OVERLOAD
+%token LE_TEMPLATE LE_TYPENAME
+%token LE_THROW LE_CATCH
+
+/* ANSI C Grammar suggestions */
+%token LE_IDENTIFIER LE_STRINGliteral
+%token LE_FLOATINGconstant LE_INTEGERconstant LE_CHARACTERconstant
+%token LE_OCTALconstant LE_HEXconstant
+%token LE_POUNDPOUND LE_CComment LE_CPPComment LE_NAMESPACE LE_USING
+
+/* New Lexical element, whereas ANSI C suggested non-terminal */
+%token LE_TYPEDEFname
+
+/* Multi-Character operators */
+%token LE_ARROW /* -> */
+%token LE_ICR LE_DECR /* ++ -- */
+%token LE_LS LE_RS /* << >> */
+%token LE_LE LE_GE LE_EQ LE_NE /* <= >= == != */
+%token LE_ANDAND LE_OROR /* && || */
+%token LE_ELLIPSIS /* ... */
+ /* Following are used in C++, not ANSI C */
+%token LE_CLCL /* :: */
+%token LE_DOTstar LE_ARROWstar /* .* ->* */
+
+/* modifying assignment operators */
+%token LE_MULTassign LE_DIVassign LE_MODassign /* *= /= %= */
+%token LE_PLUSassign LE_MINUSassign /* += -= */
+%token LE_LSassign LE_RSassign /* <<= >>= */
+%token LE_ANDassign LE_ERassign LE_ORassign /* &= ^= |= */
+%token LE_MACRO
+%token LE_DYNAMIC_CAST
+%token LE_STATIC_CAST
+%token LE_CONST_CAST
+%token LE_REINTERPRET_CAST
+
+%start translation_unit
+
+%%
+/* Costants */
+basic_type_name_inter: LE_INT { $$ = $1; }
+ | LE_CHAR { $$ = $1; }
+ | LE_SHORT { $$ = $1; }
+ | LE_LONG { $$ = $1; }
+ | LE_FLOAT { $$ = $1; }
+ | LE_DOUBLE { $$ = $1; }
+ | LE_SIGNED { $$ = $1; }
+ | LE_UNSIGNED { $$ = $1; }
+ | LE_VOID { $$ = $1; }
+ ;
+
+basic_type_name: LE_UNSIGNED basic_type_name_inter { $$ = $1 + " " + $2; }
+ | LE_SIGNED basic_type_name_inter { $$ = $1 + " " + $2; }
+ | LE_LONG LE_LONG { $$ = $1 + " " + $2; }
+ | LE_LONG LE_INT { $$ = $1 + " " + $2; }
+ | basic_type_name_inter { $$ = $1; }
+ ;
+
+
+/* ========================================================================*/
+/* find declarations */
+/* ========================================================================*/
+
+translation_unit : /*empty*/
+ | translation_unit external_decl
+ ;
+
+external_decl : {curr_func.Reset();} function_decl
+ | error {
+ //printf("CodeLite: syntax error, unexpected token '%s' found\n", cl_func_lval.c_str());
+ }
+ ;
+
+/*templates*/
+template_arg : /* empty */ { $$ = "";}
+ | template_specifiter LE_IDENTIFIER {$$ = $1 + " " + $2;}
+ ;
+
+template_arg_list : template_arg { $$ = $1; }
+ | template_arg_list ',' template_arg { $$ = $1 + " " + $2 + " " + $3; }
+ ;
+
+template_specifiter : LE_CLASS { $$ = $1; }
+ | LE_TYPENAME { $$ = $1; }
+ ;
+
+opt_template_qualifier : /*empty*/
+ | LE_TEMPLATE '<' template_arg_list '>' { $$ = $1 + $2 + $3 + $4;}
+ ;
+
+/* the following rules are for template parameters no declarations! */
+template_parameter_list : /* empty */ {$$ = "";}
+ | template_parameter {$$ = $1;}
+ | template_parameter_list ',' template_parameter {$$ = $1 + $2 + $3;}
+ ;
+
+template_parameter : const_spec nested_scope_specifier LE_IDENTIFIER special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4;
+ }
+ | const_spec nested_scope_specifier basic_type_name special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4;
+ }
+ | const_spec nested_scope_specifier LE_IDENTIFIER '<' template_parameter_list '>' special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4 + $5 + $6 + $7 + " " ;
+ }
+ ;
+
+func_name: LE_IDENTIFIER {$$ = $1;}
+ | '~' LE_IDENTIFIER {$$ = $1 + $2;}
+ | LE_OPERATOR any_operator {$$ = $1 + $2;}
+ ;
+
+any_operator:
+ '+'
+ | '-'
+ | '*'
+ | '/'
+ | '%'
+ | '^'
+ | '&'
+ | '|'
+ | '~'
+ | '!'
+ | '<'
+ | '>'
+ | LE_LS
+ | LE_RS
+ | LE_ANDAND
+ | LE_OROR
+ | LE_ARROW
+ | LE_ARROWstar
+ | '.'
+ | LE_DOTstar
+ | LE_ICR
+ | LE_DECR
+ | LE_LE
+ | LE_GE
+ | LE_EQ
+ | LE_NE
+ | '(' ')'
+ | '[' ']'
+ | LE_NEW
+ | LE_DELETE
+ | ','
+ ;
+
+/* functions */
+function_decl : stmnt_starter opt_template_qualifier virtual_spec const_spec variable_decl nested_scope_specifier func_name '(' {func_consumeFuncArgList();} const_spec declare_throw opt_pure_virtual func_postfix
+ {
+ //trim down trailing '::' from scope name
+ $6.erase($6.find_last_not_of(":")+1);
+ curr_func.m_isVirtual = $3.find("virtual") != std::string::npos;
+ curr_func.m_isPureVirtual = $12.find("=") != std::string::npos;
+ curr_func.m_isConst = $10.find("const") != std::string::npos;
+ curr_func.m_name = $7;
+ curr_func.m_scope = $6;
+ curr_func.m_retrunValusConst = $4;
+ curr_func.m_lineno = cl_scope_lineno;
+ if(g_funcs)
+ {
+ g_funcs->push_back(curr_func);
+ }
+ curr_func.Reset();
+ }
+ ;
+
+declare_throw: /*empty*/ {$$ = "";}
+ | LE_THROW '(' template_parameter_list ')' {$$ = $3;}
+ ;
+
+func_postfix: '{'
+ | ';'
+ ;
+
+nested_scope_specifier : /*empty*/ {$$ = "";}
+ | nested_scope_specifier scope_specifier { $$ = $1 + $2;}
+ ;
+
+opt_pure_virtual : /*empty*/ {$$ = "";}
+ | '=' LE_OCTALconstant {$$ = $1 + $2;}
+ ;
+
+scope_specifier : LE_IDENTIFIER LE_CLCL {$$ = $1+ $2;}
+ | LE_IDENTIFIER '<' {func_consumeTemplateDecl();} LE_CLCL {$$ = $1 + $4;}
+ ;
+
+virtual_spec : /* empty */ {$$ = ""; }
+ | LE_VIRTUAL { $$ = $1; }
+ ;
+
+const_spec : /* empty */ {$$ = ""; }
+ | LE_CONST { $$ = $1; }
+ ;
+
+amp_item : /*empty*/ {$$ = ""; }
+ | '&' { $$ = $1; }
+ ;
+
+star_list : /*empty*/ {$$ = ""; }
+ | star_list '*' {$$ = $1 + $2;}
+ ;
+
+special_star_amp : star_list amp_item { $$ = $1 + $2; }
+ ;
+
+stmnt_starter : /*empty*/ {$$ = "";}
+ | ';' { $$ = ";";}
+ | ':' { $$ = ":";} //e.g. private: std::string m_name;
+ ;
+
+/** Variables **/
+variable_decl : nested_scope_specifier basic_type_name special_star_amp
+ {
+ $1.erase($1.find_last_not_of(":")+1);
+ curr_func.m_returnValue.m_type = $2;
+ curr_func.m_returnValue.m_typeScope = $1;
+ curr_func.m_returnValue.m_starAmp = $3;
+ curr_func.m_returnValue.m_isPtr = ($3.find("*") != (size_t)-1);
+ $$ = $1 + $2 + $3;
+ }
+ | nested_scope_specifier LE_IDENTIFIER special_star_amp
+ {
+ $1.erase($1.find_last_not_of(":")+1);
+ curr_func.m_returnValue.m_type = $2;
+ curr_func.m_returnValue.m_typeScope = $1;
+ curr_func.m_returnValue.m_starAmp = $3;
+ curr_func.m_returnValue.m_isPtr = ($3.find("*") != (size_t)-1);
+ $$ = $1 + $2 + $3 ;
+ }
+ | nested_scope_specifier LE_IDENTIFIER '<' template_parameter_list '>' special_star_amp
+ {
+ $1.erase($1.find_last_not_of(":")+1);
+ curr_func.m_returnValue.m_type = $2;
+ curr_func.m_returnValue.m_typeScope = $1;
+ curr_func.m_returnValue.m_starAmp = $6;
+ curr_func.m_returnValue.m_isPtr = ($6.find("*") != (size_t)-1);
+ curr_func.m_returnValue.m_isTemplate = true;
+ curr_func.m_returnValue.m_templateDecl = $4;
+ $$ = $1 + $2 + $3 + $4 + $5 + $6 ;
+ }
+ ;
+%%
+void yyerror(char *s) {}
+
+void func_consumeFuncArgList()
+{
+ curr_func.m_signature = "(";
+
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_scope_lex();
+ if(ch == 0)
+ {
+ break;
+ }
+
+ curr_func.m_signature += cl_func_lval;
+ curr_func.m_signature += " ";
+ if(ch == ')')
+ {
+ depth--;
+ continue;
+ }
+ else if(ch == '(')
+ {
+ depth ++ ;
+ continue;
+ }
+ }
+}
+
+/**
+ * consume all token until matching closing brace is found
+ */
+void func_consumeDecl()
+{
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_scope_lex();
+ //printf("ch=%d\n", ch);
+ //fflush(stdout);
+ if(ch ==0)
+ {
+ break;
+ }
+ if(ch == '}')
+ {
+ depth--;
+ continue;
+ }
+ else if(ch == '{')
+ {
+ depth ++ ;
+ continue;
+ }
+ }
+
+}
+
+void func_consumeTemplateDecl()
+{
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_scope_lex();
+ //printf("ch=%d\n", ch);
+ //fflush(stdout);
+ if(ch ==0){
+ break;
+ }
+
+ if(ch == '>')
+ {
+ depth--;
+ continue;
+ }
+ else if(ch == '<')
+ {
+ depth ++ ;
+ continue;
+ }
+ }
+}
+
+// return the scope name at the end of the input string
+void get_functions(const std::string &in, FunctionList &li, const std::map<std::string, std::string> &ignoreTokens)
+{
+ if( !setLexerInput(in, ignoreTokens) )
+ {
+ return;
+ }
+
+ g_funcs = &li;
+
+ //call tghe main parsing routine
+ cl_func_parse();
+ g_funcs = NULL;
+
+ //do the lexer cleanup
+ cl_scope_lex_clean();
+}
diff --git a/plugins/symbol-db/cxxparser/grammars/cpp_scope_grammar.y b/plugins/symbol-db/cxxparser/grammars/cpp_scope_grammar.y
new file mode 100644
index 0000000..fcc93fe
--- /dev/null
+++ b/plugins/symbol-db/cxxparser/grammars/cpp_scope_grammar.y
@@ -0,0 +1,576 @@
+ %{
+// Copyright Eran Ifrah(c)
+%}
+
+%{
+/*************** Includes and Defines *****************************/
+#include "string"
+#include "vector"
+#include "stdio.h"
+#include "map"
+
+#define YYDEBUG_LEXER_TEXT (cl_scope_lval)
+#define YYSTYPE std::string
+#define YYDEBUG 0 /* get the pretty debugging code to compile*/
+
+int cl_scope_parse();
+void cl_scope_error(char *string);
+void syncParser();
+
+static std::vector<std::string> gs_additionlNS;
+
+//---------------------------------------------
+// externs defined in the lexer
+//---------------------------------------------
+extern char *cl_scope_text;
+extern int cl_scope_lex();
+extern bool setLexerInput(const std::string &in, const std::map<std::string, std::string> &ignoreTokens);
+extern int cl_scope_lineno;
+extern std::vector<std::string> currentScope;
+extern void printScopeName(); //print the current scope name
+extern void increaseScope(); //increase scope with anonymouse value
+extern std::string getCurrentScope();
+extern void cl_scope_lex_clean();
+extern void cl_scope_less(int count);
+
+/*************** Standard ytab.c continues here *********************/
+%}
+
+/*************************************************************************/
+
+/* This group is used by the C/C++ language parser */
+%token LE_AUTO LE_DOUBLE LE_INT LE_STRUCT
+%token LE_BREAK LE_ELSE LE_LONG LE_SWITCH
+%token LE_CASE LE_ENUM LE_REGISTER LE_TYPEDEF
+%token LE_CHAR LE_EXTERN LE_RETURN LE_UNION
+%token LE_CONST LE_FLOAT LE_SHORT LE_UNSIGNED
+%token LE_CONTINUE LE_FOR LE_SIGNED LE_VOID
+%token LE_DEFAULT LE_GOTO LE_SIZEOF LE_VOLATILE
+%token LE_DO LE_IF LE_STATIC LE_WHILE
+
+/* The following are used in C++ only. ANSI C would call these IDENTIFIERs */
+%token LE_NEW LE_DELETE
+%token LE_THIS
+%token LE_OPERATOR
+%token LE_CLASS
+%token LE_PUBLIC LE_PROTECTED LE_PRIVATE
+%token LE_VIRTUAL LE_FRIEND
+%token LE_INLINE LE_OVERLOAD
+%token LE_TEMPLATE LE_TYPENAME
+%token LE_THROW LE_CATCH
+/* ANSI C Grammar suggestions */
+%token LE_IDENTIFIER LE_STRINGliteral
+%token LE_FLOATINGconstant LE_INTEGERconstant LE_CHARACTERconstant
+%token LE_OCTALconstant LE_HEXconstant
+%token LE_POUNDPOUND LE_CComment LE_CPPComment LE_NAMESPACE LE_USING
+
+/* New Lexical element, whereas ANSI C suggested non-terminal */
+%token LE_TYPEDEFname
+
+/* Multi-Character operators */
+%token LE_ARROW /* -> */
+%token LE_ICR LE_DECR /* ++ -- */
+%token LE_LS LE_RS /* << >> */
+%token LE_LE LE_GE LE_EQ LE_NE /* <= >= == != */
+%token LE_ANDAND LE_OROR /* && || */
+%token LE_ELLIPSIS /* ... */
+ /* Following are used in C++, not ANSI C */
+%token LE_CLCL /* :: */
+%token LE_DOTstar LE_ARROWstar /* .* ->* */
+
+/* modifying assignment operators */
+%token LE_MULTassign LE_DIVassign LE_MODassign /* *= /= %= */
+%token LE_PLUSassign LE_MINUSassign /* += -= */
+%token LE_LSassign LE_RSassign /* <<= >>= */
+%token LE_ANDassign LE_ERassign LE_ORassign /* &= ^= |= */
+%token LE_MACRO
+%token LE_DYNAMIC_CAST
+%token LE_STATIC_CAST
+%token LE_CONST_CAST
+%token LE_REINTERPRET_CAST
+
+%start translation_unit
+
+%%
+/* Costants */
+basic_type_name:
+ LE_INT { $$ = $1; }
+ | LE_CHAR { $$ = $1; }
+ | LE_SHORT { $$ = $1; }
+ | LE_LONG { $$ = $1; }
+ | LE_FLOAT { $$ = $1; }
+ | LE_DOUBLE { $$ = $1; }
+ | LE_SIGNED { $$ = $1; }
+ | LE_UNSIGNED { $$ = $1; }
+ | LE_VOID { $$ = $1; }
+ ;
+
+
+/* ========================================================================*/
+/* find declarations */
+/* ========================================================================*/
+
+translation_unit : /*empty*/
+ | translation_unit external_decl
+ ;
+
+external_decl : class_decl
+ | enum_decl
+ | union_decl
+ | function_decl
+ | namespace_decl
+ | using_namespace
+ | scope_reducer
+ | scope_increaer
+ | question_expression
+ | error {
+// printf("CodeLite: syntax error, unexpected token '%s' found at line %d \n", cl_scope_text, cl_scope_lineno);
+// syncParser();
+ }
+ ;
+
+
+/*templates*/
+template_arg : /* empty */ { $$ = "";}
+ | template_specifiter LE_IDENTIFIER {$$ = $1 + " " + $2;}
+ ;
+
+template_arg_list : template_arg { $$ = $1; }
+ | template_arg_list ',' template_arg { $$ = $1 + " " + $2 + " " + $3; }
+ ;
+
+template_specifiter : LE_CLASS { $$ = $1; }
+ | LE_TYPENAME { $$ = $1; }
+ ;
+
+opt_template_qualifier : /*empty*/
+ | LE_TEMPLATE '<' template_arg_list '>' { $$ = $1 + $2 + $3 + $4;}
+ ;
+/*inheritance*/
+derivation_list : /*empty*/ {$$ = "";}
+ | parent_class {$$ = $1;}
+ | derivation_list ',' parent_class {$$ = $1 + $2 + $3;}
+ ;
+
+parent_class : access_specifier LE_IDENTIFIER opt_template_specifier {$$ = $1 + " " + $2 + $3;}
+ ;
+
+opt_template_specifier : /*empty*/ {$$ = "";}
+ | '<' template_parameter_list '>' {$$ = $1 + $2 + $3;}
+ ;
+
+access_specifier : /*empty*/ {$$ = "";}
+ | LE_PUBLIC {$$ = $1;}
+ | LE_PRIVATE {$$ = $1;}
+ | LE_PROTECTED {$$ = $1;}
+ ;
+
+/* the following rules are for template parameters no declarations! */
+template_parameter_list : /* empty */ {$$ = "";}
+ | template_parameter {$$ = $1;}
+ | template_parameter_list ',' template_parameter {$$ = $1 + $2 + $3;}
+ ;
+
+/*template_parameter : const_spec nested_scope_specifier LE_IDENTIFIER special_star_amp {$$ = $1 + $2 + $3 +$4;}
+ ;*/
+template_parameter : const_spec nested_scope_specifier LE_IDENTIFIER special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4;
+ }
+ | const_spec nested_scope_specifier basic_type_name special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4;
+ }
+ | const_spec nested_scope_specifier LE_IDENTIFIER '<' template_parameter_list '>' special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4 + $5 + $6 + $7 + " " ;
+ }
+ ;
+
+using_namespace: LE_USING LE_NAMESPACE nested_scope_specifier LE_IDENTIFIER ';'
+ {
+ //printf("Found using namespace %s\n", $3.c_str());
+ gs_additionlNS.push_back($3+$4);
+ }
+ ;
+
+/* namespace */
+namespace_decl : stmnt_starter LE_NAMESPACE LE_IDENTIFIER '{'
+ {
+ currentScope.push_back($3);
+ printScopeName();
+ }
+ | stmnt_starter LE_NAMESPACE '{'
+ {
+ //anonymouse namespace
+ increaseScope();
+ printScopeName();
+ }
+ ;
+opt_class_qualifier : /*empty*/{$$ = "";}
+ | LE_MACRO {$$ = $1;}
+ ;
+
+/* the class rule itself */
+class_decl : stmnt_starter opt_template_qualifier class_keyword opt_class_qualifier LE_IDENTIFIER '{'
+ {
+ //increase the scope level
+ currentScope.push_back($5);
+ printScopeName();
+ }
+
+ | stmnt_starter opt_template_qualifier class_keyword opt_class_qualifier LE_IDENTIFIER ':' derivation_list '{'
+ {
+ //increase the scope level
+ currentScope.push_back($5);
+ printScopeName();
+ }
+ ;
+
+scope_reducer : '}' {
+ if(currentScope.empty())
+ {
+ //fatal error!
+ //printf("CodeLite: fatal error - cant go beyond global scope!\n");
+ }
+ else
+ {
+ currentScope.pop_back();
+ printScopeName();
+ }
+ }
+ ;
+scope_increaer : '{' {
+ //increase random scope
+ increaseScope();
+ printScopeName();
+ }
+
+question_expression : '?'
+ {
+ consumeNotIncluding(';');
+ }
+
+class_keyword: LE_CLASS {$$ = $1;}
+ | LE_STRUCT {$$ = $1;}
+ ;
+
+func_name: LE_IDENTIFIER {$$ = $1;}
+ | LE_OPERATOR any_operator {$$ = $1;}
+ ;
+
+any_operator:
+ '+'
+ | '='
+ | '*'
+ | '/'
+ | '%'
+ | '^'
+ | '&'
+ | '|'
+ | '~'
+ | '!'
+ | '<'
+ | '>'
+ | LE_LS
+ | LE_RS
+ | LE_ANDAND
+ | LE_OROR
+ | LE_ARROW
+ | LE_ARROWstar
+ | '.'
+ | LE_DOTstar
+ | LE_ICR
+ | LE_DECR
+ | LE_LE
+ | LE_GE
+ | LE_EQ
+ | LE_NE
+ | '(' ')'
+ | '[' ']'
+ | LE_NEW
+ | LE_DELETE
+ | ','
+ | LE_MULTassign
+ | LE_DIVassign
+ | LE_MODassign
+ | LE_PLUSassign
+ | LE_MINUSassign
+ | LE_LSassign
+ | LE_RSassign
+ | LE_ANDassign
+ | LE_ERassign
+ | LE_ORassign
+ ;
+
+optional_initialization_list: '{' {$$ = '{';}/* empty */
+ | ':' {consumeInitializationList() /*eat everything including the open brace*/;}
+ ;
+
+declare_throw: /*empty*/ {$$ = "";}
+ | LE_THROW '(' template_parameter_list ')' {$$ = $3;}
+ ;
+
+/* functions */
+function_decl : stmnt_starter opt_template_qualifier virtual_spec const_spec variable_decl nested_scope_specifier func_name '(' {consumeFuncArgList();} const_spec declare_throw '{'
+ {
+ //trim down trailing '::' from scope name
+ if($6.find_last_not_of(":") != std::string::npos){
+ $6.erase($6.find_last_not_of(":")+1);
+ }
+ currentScope.push_back($6);
+ printScopeName();
+ }
+ | stmnt_starter opt_template_qualifier virtual_spec const_spec nested_scope_specifier func_name '(' {consumeFuncArgList();} optional_initialization_list
+ {
+
+ //trim down trailing '::' from scope name
+ if($5.find_last_not_of(":") != std::string::npos){
+ $5.erase($5.find_last_not_of(":")+1);
+ }
+ currentScope.push_back($5);
+ printScopeName();
+ }
+ | stmnt_starter opt_template_qualifier virtual_spec const_spec nested_scope_specifier '~' func_name '(' {consumeFuncArgList();} const_spec '{'
+ {
+
+ //trim down trailing '::' from scope name
+ if($5.find_last_not_of(":") != std::string::npos){
+ $5.erase($5.find_last_not_of(":")+1);
+ }
+ currentScope.push_back($5);
+ printScopeName();
+ }
+ ;
+
+/*
+applicable for C++, for cases where a function is declared as
+void scope::foo(){ ... }
+*/
+nested_scope_specifier : /*empty*/ {$$ = "";}
+ | nested_scope_specifier scope_specifier { $$ = $1 + $2;}
+ ;
+
+scope_specifier : LE_IDENTIFIER LE_CLCL {$$ = $1+ $2;}
+ | LE_IDENTIFIER '<' {consumeTemplateDecl();} LE_CLCL {$$ = $1 + $4;}
+ ;
+
+virtual_spec : /* empty */ {$$ = ""; }
+ | LE_VIRTUAL { $$ = $1; }
+ ;
+
+const_spec : /* empty */ {$$ = ""; }
+ | LE_CONST { $$ = $1; }
+ ;
+
+amp_item : /*empty*/ {$$ = ""; }
+ | '&' { $$ = $1; }
+ ;
+
+star_list : /*empty*/ {$$ = ""; }
+ | star_list '*' {$$ = $1 + $2;}
+ ;
+
+special_star_amp : star_list amp_item { $$ = $1 + $2; }
+ ;
+
+stmnt_starter : /*empty*/ {$$ = "";}
+ | ';' { $$ = ";";}
+ | ':' { $$ = ":";} //e.g. private: std::string m_name;
+ ;
+
+/** Variables **/
+variable_decl : nested_scope_specifier basic_type_name special_star_amp
+ {$$ = $1 + $2 + $3 ;}
+ | nested_scope_specifier LE_IDENTIFIER special_star_amp
+ {$$ = $1 + $2 + $3 ;}
+ | nested_scope_specifier LE_IDENTIFIER '<' template_parameter_list '>' special_star_amp
+ {$$ = $1 + $2 + $3 + $4 + $5 + $6 ;}
+ ;
+
+enum_decl : stmnt_starter LE_ENUM LE_IDENTIFIER '{' {currentScope.push_back($3); printScopeName();} enum_arg_list '}'
+ {
+ currentScope.pop_back();//reduce the scope
+ printScopeName();
+ //printf("found enum: %s, args are: %s\n", $2.c_str(), $5.c_str());
+ }
+ ;
+
+enum_optional_assign : /*empty*/ {$$ = "";}
+ | '=' LE_HEXconstant {$$ = $1 + $2;}
+ | '=' LE_OCTALconstant {$$ = $1 + $2;}
+ | '=' LE_INTEGERconstant {$$ = $1 + $2;}
+ ;
+
+enum_argument : LE_IDENTIFIER enum_optional_assign {$$ = $1 + $2;}
+ ;
+enum_arg_list : /*empty*/ {$$ = "";}
+ | enum_argument {$$ = $1;}
+ | enum_arg_list ',' enum_argument {$$ = $1 + $2 + $3;}
+ ;
+
+union_decl : stmnt_starter LE_UNION LE_IDENTIFIER '{'
+ {
+ currentScope.push_back($3);
+ printScopeName();
+ consumeDecl();
+ printScopeName();
+ }
+ ;
+%%
+void yyerror(char *s) {}
+
+void syncParser(){
+ //move lexer to the next ';' line or scope opening '{'
+ //int ch = cl_scope_lex();
+}
+
+//swallow all tokens up to the first '{'
+void consumeInitializationList(){
+ while( true ){
+ int ch = cl_scope_lex();
+ if(ch == 0){
+ break;
+ }
+
+ if(ch == '{'){
+ break;
+ }
+ }
+}
+
+//swallow all tokens up to the first '{'
+void consumeBody (){
+ std::string cs = "{";
+ int depth = 1;
+ while( true ) {
+ int ch = cl_scope_lex();
+ if(ch == 0){
+ break;
+ }
+
+ cs += cl_scope_text;
+ cs += " ";
+
+ if(ch == '{'){
+ depth++;
+ }else if(ch == '}'){
+ depth--;
+ if(depth == 0){
+ cl_scope_less(0);
+ break;
+ }
+ }
+ }
+ printf("Consumed body: [%s]\n", cs.c_str());
+}
+
+void consumeFuncArgList(){
+ int depth = 1;
+ while(depth > 0){
+ int ch = cl_scope_lex();
+ if(ch == 0){
+ break;
+ }
+
+ if(ch == ')'){
+ depth--;
+ continue;
+ }
+ else if(ch == '('){
+ depth ++ ;
+ continue;
+ }
+ }
+}
+
+/**
+ * consume all token until matching closing brace is found
+ */
+void consumeDecl()
+{
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_scope_lex();
+ if(ch ==0)
+ {
+ break;
+ }
+ if(ch == '}')
+ {
+ depth--;
+ if(depth == 0) currentScope.pop_back();//reduce the scope
+ continue;
+ }
+ else if(ch == '{')
+ {
+ depth ++ ;
+ continue;
+ }
+ }
+
+}
+
+void consumeTemplateDecl()
+{
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_scope_lex();
+ //printf("ch=%d\n", ch);
+ fflush(stdout);
+ if(ch ==0){
+ break;
+ }
+
+ if(ch == '>')
+ {
+ depth--;
+ continue;
+ }
+ else if(ch == '<')
+ {
+ depth ++ ;
+ continue;
+ }
+ }
+}
+
+//swallow all tokens up to the first '{'
+void consumeNotIncluding(int ch){
+ while( true ){
+ int c = cl_scope_lex();
+ if(c == 0){ // EOF?
+ break;
+ }
+
+ //keep the function signature
+ if(c == ch){
+ cl_scope_less(0);
+ break;
+ }
+ }
+}
+
+// return the scope name at the end of the input string
+std::string get_scope_name( const std::string &in,
+ std::vector<std::string> &additionalNS,
+ const std::map<std::string, std::string> &ignoreTokens)
+{
+ if( !setLexerInput(in, ignoreTokens) ){
+ return "";
+ }
+
+ //call tghe main parsing routine
+ cl_scope_parse();
+ std::string scope = getCurrentScope();
+ //do the lexer cleanup
+ cl_scope_lex_clean();
+
+ for(size_t i=0; i<gs_additionlNS.size(); i++){
+ additionalNS.push_back(gs_additionlNS.at(i));
+ }
+ gs_additionlNS.clear();
+ return scope;
+}
diff --git a/plugins/symbol-db/cxxparser/grammars/cpp_variables_grammar.y b/plugins/symbol-db/cxxparser/grammars/cpp_variables_grammar.y
new file mode 100644
index 0000000..2777a11
--- /dev/null
+++ b/plugins/symbol-db/cxxparser/grammars/cpp_variables_grammar.y
@@ -0,0 +1,530 @@
+%{
+// Copyright Eran Ifrah(c)
+%}
+
+%{
+/*************** Includes and Defines *****************************/
+#include "string"
+#include "vector"
+#include "stdio.h"
+#include "map"
+#include "variable.h"
+
+#ifdef yylex
+#undef yylex
+#define yylex cl_scope_lex
+#endif
+
+#define YYSTYPE std::string
+#define YYDEBUG 0 /* get the pretty debugging code to compile*/
+
+void cl_scope_error(char *string);
+int cl_var_parse();
+void syncParser();
+void var_consumeDefaultValue(char c1, char c2);
+
+static VariableList *gs_vars = NULL;
+static std::vector<std::string> gs_names;
+static bool g_isUsedWithinFunc = false;
+Variable curr_var;
+static std::string s_tmpString;
+
+//---------------------------------------------
+// externs defined in the lexer
+//---------------------------------------------
+extern char *cl_scope_text;
+extern int cl_scope_lex();
+extern void cl_scope_less(int count);
+
+extern int cl_scope_lineno;
+extern std::vector<std::string> currentScope;
+extern bool setLexerInput(const std::string &in, const std::map<std::string, std::string> &ignoreMap);
+extern void setUseIgnoreMacros(bool ignore);
+extern void cl_scope_lex_clean();
+
+/*************** Standard ytab.c continues here *********************/
+%}
+
+/*************************************************************************/
+
+/* This group is used by the C/C++ language parser */
+%token LE_AUTO LE_DOUBLE LE_INT LE_STRUCT
+%token LE_BREAK LE_ELSE LE_LONG LE_SWITCH
+%token LE_CASE LE_ENUM LE_REGISTER LE_TYPEDEF
+%token LE_CHAR LE_EXTERN LE_RETURN LE_UNION
+%token LE_CONST LE_FLOAT LE_SHORT LE_UNSIGNED
+%token LE_CONTINUE LE_FOR LE_SIGNED LE_VOID
+%token LE_DEFAULT LE_GOTO LE_SIZEOF LE_VOLATILE
+%token LE_DO LE_IF LE_STATIC LE_WHILE
+
+/* The following are used in C++ only. ANSI C would call these IDENTIFIERs */
+%token LE_NEW LE_DELETE
+%token LE_THIS
+%token LE_OPERATOR
+%token LE_CLASS
+%token LE_PUBLIC LE_PROTECTED LE_PRIVATE
+%token LE_VIRTUAL LE_FRIEND
+%token LE_INLINE LE_OVERLOAD
+%token LE_TEMPLATE LE_TYPENAME
+%token LE_THROW LE_CATCH
+/* ANSI C Grammar suggestions */
+%token LE_IDENTIFIER LE_STRINGliteral
+%token LE_FLOATINGconstant LE_INTEGERconstant LE_CHARACTERconstant
+%token LE_OCTALconstant LE_HEXconstant
+%token LE_POUNDPOUND LE_CComment LE_CPPComment LE_NAMESPACE LE_USING
+
+/* New Lexical element, whereas ANSI C suggested non-terminal */
+%token LE_TYPEDEFname
+
+/* Multi-Character operators */
+%token LE_ARROW /* -> */
+%token LE_ICR LE_DECR /* ++ -- */
+%token LE_LS LE_RS /* << >> */
+%token LE_LE LE_GE LE_EQ LE_NE /* <= >= == != */
+%token LE_ANDAND LE_OROR /* && || */
+%token LE_ELLIPSIS /* ... */
+ /* Following are used in C++, not ANSI C */
+%token LE_CLCL /* :: */
+%token LE_DOTstar LE_ARROWstar /* .* ->* */
+
+/* modifying assignment operators */
+%token LE_MULTassign LE_DIVassign LE_MODassign /* *= /= %= */
+%token LE_PLUSassign LE_MINUSassign /* += -= */
+%token LE_LSassign LE_RSassign /* <<= >>= */
+%token LE_ANDassign LE_ERassign LE_ORassign /* &= ^= |= */
+%token LE_MACRO
+%token LE_DYNAMIC_CAST
+%token LE_STATIC_CAST
+%token LE_CONST_CAST
+%token LE_REINTERPRET_CAST
+
+%start translation_unit
+
+%%
+/* Costants */
+basic_type_name_inter: LE_INT { $$ = $1; }
+ | LE_CHAR { $$ = $1; }
+ | LE_SHORT { $$ = $1; }
+ | LE_LONG { $$ = $1; }
+ | LE_FLOAT { $$ = $1; }
+ | LE_DOUBLE { $$ = $1; }
+ | LE_SIGNED { $$ = $1; }
+ | LE_UNSIGNED { $$ = $1; }
+ | LE_VOID { $$ = $1; }
+ ;
+
+basic_type_name: LE_UNSIGNED basic_type_name_inter { $$ = $1 + " " + $2; }
+ | LE_SIGNED basic_type_name_inter { $$ = $1 + " " + $2; }
+ | LE_LONG LE_LONG { $$ = $1 + " " + $2; }
+ | LE_LONG LE_INT { $$ = $1 + " " + $2; }
+ | basic_type_name_inter { $$ = $1; }
+ ;
+
+/* ========================================================================*/
+/* find declarations */
+/* ========================================================================*/
+
+translation_unit : /*empty*/
+ | translation_unit external_decl
+ ;
+
+external_decl : {curr_var.Reset(); gs_names.clear(); s_tmpString.clear();} variables
+ | error {
+ yyclearin; //clear lookahead token
+ yyerrok;
+ //printf("CodeLite: syntax error, unexpected token '%s' found at line %d \n", cl_var_lval.c_str(), cl_scope_lineno);
+ var_syncParser();
+ }
+ ;
+
+/* the following rules are for template parameters no declarations! */
+parameter_list : /* empty */ {$$ = "";}
+ | template_parameter {$$ = $1;}
+ | parameter_list ',' template_parameter {$$ = $1 + $2 + " " + $3;}
+ ;
+
+template_parameter : const_spec nested_scope_specifier LE_IDENTIFIER special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4;
+ }
+ | const_spec nested_scope_specifier basic_type_name special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4;
+ }
+ | const_spec nested_scope_specifier LE_IDENTIFIER '<' parameter_list '>' special_star_amp
+ {
+ $$ = $1 + $2 + $3 +$4 + $5 + $6 + $7 + " " ;
+ }
+ ;
+
+//the main rule for finding variables
+//in the code. if this rule succeeded, the variables
+//is added to the gs_vars vriable
+variables : stmnt_starter variable_decl special_star_amp variable_name_list postfix
+ {
+ if(gs_vars)
+ {
+ Variable var;
+ std::string pattern;
+ curr_var.m_isPtr = ($3.find("*") != (size_t)-1);
+ curr_var.m_starAmp = $3;
+ curr_var.m_lineno = cl_scope_lineno;
+ for(size_t i=0; i< gs_names.size(); i++)
+ {
+ //create new variable for every variable name found
+ var = curr_var;
+ var.m_pattern = "/^" + $1 + " " + $2 + " " + $3 + gs_names.at(i) + " $/";
+ var.m_name = gs_names.at(i);
+ gs_vars->push_back(var);
+ }
+ curr_var.Reset();
+ gs_names.clear();
+ }
+ }
+ //
+ // Functions arguments:
+ //
+ | '(' variable_decl special_star_amp LE_IDENTIFIER postfix2
+ {
+ if(gs_vars)
+ {
+ Variable var;
+ std::string pattern;
+ curr_var.m_pattern = "/^";
+ curr_var.m_pattern += $1 + " " + $2 + " " + $3 + " " + $4 + $5 + "$/";
+ curr_var.m_isPtr = ($3.find("*") != (size_t)-1);
+ curr_var.m_starAmp = $3;
+ curr_var.m_arrayBrackets = $5;
+ curr_var.m_lineno = cl_scope_lineno;
+ //create new variable for every variable name found
+ var = curr_var;
+ var.m_name = $4;;
+ gs_vars->push_back(var);
+ curr_var.Reset();
+ gs_names.clear();
+ }
+ }
+ | ',' variable_decl special_star_amp LE_IDENTIFIER postfix2
+ {
+ if(gs_vars && g_isUsedWithinFunc)
+ {
+ Variable var;
+ std::string pattern;
+ curr_var.m_pattern = "/^";
+ curr_var.m_pattern += $1 + " " + $2 + " " + $3 + " " + $4 + $5 + "$/";
+ curr_var.m_isPtr = ($3.find("*") != (size_t)-1);
+ curr_var.m_starAmp = $3;
+ curr_var.m_arrayBrackets = $5;
+ curr_var.m_lineno = cl_scope_lineno;
+
+ //create new variable for every variable name found
+ var = curr_var;
+ var.m_name = $4;
+ gs_vars->push_back(var);
+
+ curr_var.Reset();
+ gs_names.clear();
+ }
+ }
+ | '(' variable_decl special_star_amp postfix3
+ {
+ if(gs_vars && g_isUsedWithinFunc)
+ {
+ Variable var;
+ std::string pattern;
+ curr_var.m_pattern = "/^";
+ curr_var.m_pattern += $1 + " " + $2 + " " + $3 + " " + "$/";
+ curr_var.m_isPtr = ($3.find("*") != (size_t)-1);
+ curr_var.m_starAmp = $3;
+ curr_var.m_lineno = cl_scope_lineno;
+
+ //create new variable for every variable name found
+ var = curr_var;
+ var.m_name = "";
+ gs_vars->push_back(var);
+
+ curr_var.Reset();
+ gs_names.clear();
+ }
+ if($4 == ",") {
+ cl_scope_less(0);
+ }
+ }
+ | ',' variable_decl special_star_amp postfix3
+ {
+ if(gs_vars && g_isUsedWithinFunc)
+ {
+ Variable var;
+ std::string pattern;
+ curr_var.m_pattern = "/^";
+ curr_var.m_pattern += $1 + " " + $2 + " " + $3 + " " + "$/";
+ curr_var.m_isPtr = ($3.find("*") != (size_t)-1);
+ curr_var.m_starAmp = $3;
+ curr_var.m_lineno = cl_scope_lineno;
+
+ //create new variable for every variable name found
+ var = curr_var;
+ var.m_name = "";
+ gs_vars->push_back(var);
+
+ curr_var.Reset();
+ gs_names.clear();
+ }
+ if($4 == ",") {
+ cl_scope_less(0);
+ }
+ };
+
+
+variable_name_list: LE_IDENTIFIER
+ {
+ gs_names.push_back($1);
+ $$ = $1;
+ }
+ | variable_name_list ',' special_star_amp LE_IDENTIFIER
+ {
+ //collect all the names
+ gs_names.push_back($4);
+ $$ = $1 + $2 + " " + $3 + $4;
+ }
+ ;
+
+postfix3: ','
+ | ')'
+ ;
+
+postfix2: /*empty*/ {$$ = "";}
+ | '=' {var_consumeDefaultValue(',', ')'); $$ = ""; }
+ | ')' { $$ = ""; }
+ | '[' { $$ = $1 + var_consumBracketsContent('[');}
+ ;
+
+postfix: ';'
+ | '='
+ | ')'
+ | '(' { $$ = $1 + var_consumBracketsContent('(');}
+ | '[' { $$ = $1 + var_consumBracketsContent('[');}
+ ;
+/*
+applicable for C++, for cases where a function is declared as
+void scope::foo(){ ... }
+*/
+scope_specifier : LE_IDENTIFIER LE_CLCL {$$ = $1+ $2; }
+ | LE_IDENTIFIER '<' parameter_list '>' LE_CLCL {$$ = $1 + $2 + $3 + $4 + $5;}
+ ;
+
+nested_scope_specifier: /*empty*/ {$$ = "";}
+ | nested_scope_specifier scope_specifier { $$ = $1 + $2;}
+ ;
+
+const_spec : /* empty */ {$$ = ""; }
+ | LE_CONST { $$ = $1; }
+ ;
+
+amp_item : /*empty*/ {$$ = ""; }
+ | '&' { $$ = $1; }
+ ;
+
+star_list : /*empty*/ {$$ = ""; }
+ | star_list '*' {$$ = $1 + $2;}
+ ;
+
+special_star_amp : star_list amp_item { $$ = $1 + $2; }
+ ;
+
+stmnt_starter : /*empty*/ {$$ = "";}
+ | ';' { $$ = ";";}
+ | '{' { $$ = "{";}
+// | '(' { $$ = "(";}
+ | '}' { $$ = "}";}
+ | ':' { $$ = ":";} //e.g. private: std::string m_name;
+// | '=' { $$ = "=";}
+ ;
+
+/** Variables **/
+variable_decl : const_spec basic_type_name
+ {
+ $$ = $1 + " " + $2;
+ $2.erase($2.find_last_not_of(":")+1);
+ curr_var.m_type = $2;
+ curr_var.m_isConst = !$1.empty();
+ }
+ | const_spec nested_scope_specifier LE_IDENTIFIER
+ {
+ $$ = $1 + " " + $2 + $3;
+ $2.erase($2.find_last_not_of(":")+1);
+ curr_var.m_typeScope = $2;
+ curr_var.m_type = $3;
+ curr_var.m_isConst = !$1.empty();
+ s_tmpString.clear();
+ }
+ | const_spec nested_scope_specifier LE_IDENTIFIER '<' parameter_list '>'
+ {
+ $$ = $1 + " " + $2 + $3 + " " + $4 + $5 + $6;
+ $2.erase($2.find_last_not_of(":")+1);
+ curr_var.m_typeScope = $2;
+ curr_var.m_type = $3;
+ curr_var.m_isTemplate = true;
+ curr_var.m_templateDecl = $4 +$5 +$6;
+ curr_var.m_isConst = !$1.empty();
+ s_tmpString.clear();
+ }
+ | const_spec LE_STRUCT nested_scope_specifier LE_IDENTIFIER '{' {s_tmpString = var_consumBracketsContent('{');}
+ {
+ $$ = $1 + " " + $2 + " " + $3 + " " + $4 + $5 + $6 + s_tmpString;
+ $3.erase($3.find_last_not_of(":")+1);
+ curr_var.m_typeScope = $3;
+ curr_var.m_type = $4;
+ curr_var.m_isTemplate = false;
+ curr_var.m_isConst = !$1.empty();
+ s_tmpString.clear();
+ }
+ | const_spec LE_STRUCT nested_scope_specifier LE_IDENTIFIER
+ {
+ $$ = $0;
+ $3.erase($3.find_last_not_of(":")+1);
+ curr_var.m_typeScope = $3;
+ curr_var.m_type = $4;
+ curr_var.m_isTemplate = false;
+ curr_var.m_isConst = !$1.empty();
+ s_tmpString.clear();
+ }
+ ;
+
+%%
+void yyerror(char *s) {}
+
+
+std::string var_consumBracketsContent(char openBrace)
+{
+ char closeBrace;
+
+ switch(openBrace) {
+ case '(': closeBrace = ')'; break;
+ case '[': closeBrace = ']'; break;
+ case '<': closeBrace = '>'; break;
+ case '{': closeBrace = '}'; break;
+ default:
+ openBrace = '(';
+ closeBrace = ')';
+ break;
+ }
+
+ std::string consumedData;
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_scope_lex();
+ if(ch == 0){
+ break;
+ }
+
+
+ if(ch == closeBrace)
+ {
+ consumedData.erase(0, consumedData.find_first_not_of(" "));
+ consumedData.erase(consumedData.find_last_not_of(" ")+1);
+ consumedData += cl_scope_text;
+
+ depth--;
+ continue;
+ }
+ else if(ch == openBrace)
+ {
+ consumedData.erase(0, consumedData.find_first_not_of(" "));
+ consumedData.erase(consumedData.find_last_not_of(" ")+1);
+ consumedData += cl_scope_text;
+
+ depth ++ ;
+ continue;
+ }
+
+ consumedData += cl_scope_text;
+ consumedData += " ";
+ }
+
+ return consumedData;
+}
+
+void var_consumeDefaultValue(char c1, char c2)
+{
+ int depth = 0;
+ bool cont(true);
+
+ while (depth >= 0) {
+ int ch = cl_scope_lex();
+ if(ch == 0) { break;}
+
+ if(ch == c1 && depth == 0) {
+ cl_scope_less(0);
+ break;
+ }
+
+ if(ch == c2 && depth == 0) {
+ cl_scope_less(0);
+ break;
+ }
+
+ curr_var.m_defaultValue += cl_scope_text;
+ if(ch == ')' || ch == '}'){
+ depth--;
+ continue;
+ } else if(ch == '(' || ch == '{') {
+ depth ++ ;
+ continue;
+ }
+ }
+}
+
+void var_syncParser(){
+// int depth = 1;
+// bool cont(true);
+//
+// while (depth > 0 && cont) {
+// int ch = cl_scope_lex();
+// if(ch == 0) { break;}
+// if(ch == ',' && depth == 0) { break;}
+// if(ch == ';' && depth == 0) { break;}
+// if(ch == ')' && depth == 0) { break;}
+//
+// if(ch == ')'){
+// depth--;
+// continue;
+// }
+// else if(ch == '('){
+// depth ++ ;
+// continue;
+// }
+// printf("%d ", ch);
+// }
+// printf("\n");
+}
+
+// return the scope name at the end of the input string
+void get_variables(const std::string &in, VariableList &li, const std::map<std::string, std::string> &ignoreMap, bool isUsedWithinFunc)
+{
+ //provide the lexer with new input
+ if( !setLexerInput(in, ignoreMap) ){
+ return;
+ }
+
+ //set the parser local output to our variable list
+ gs_vars = &li;
+ setUseIgnoreMacros(false);
+
+ // the 'g_isUsedWithinFunc' allows us to parse variabels without name
+ // this is typical when used as function declaration (e.g. void setValue(bool);)
+ g_isUsedWithinFunc = isUsedWithinFunc;
+
+ //call tghe main parsing routine
+ cl_var_parse();
+ gs_vars = NULL;
+
+ // restore settings
+ setUseIgnoreMacros(true);
+ g_isUsedWithinFunc = false;
+
+ //do the lexer cleanup
+ cl_scope_lex_clean();
+}
+
diff --git a/plugins/symbol-db/cxxparser/grammars/expr_grammar.y b/plugins/symbol-db/cxxparser/grammars/expr_grammar.y
new file mode 100644
index 0000000..7b3b516
--- /dev/null
+++ b/plugins/symbol-db/cxxparser/grammars/expr_grammar.y
@@ -0,0 +1,388 @@
+%{
+// Copyright Eran Ifrah(c)
+%}
+
+%{
+/*************** Includes and Defines *****************************/
+#include "string"
+#include "vector"
+#include "stdio.h"
+#include "map"
+#include "expression_result.h"
+
+#define YYSTYPE std::string
+#define YYDEBUG 0 /* get the pretty debugging code to compile*/
+
+void cl_expr_error(char *string);
+
+static ExpressionResult result;
+
+//---------------------------------------------
+// externs defined in the lexer
+//---------------------------------------------
+extern char *cl_expr_text;
+extern int cl_expr_lex();
+extern int cl_expr_parse();
+extern int cl_expr_lineno;
+extern std::vector<std::string> currentScope;
+extern bool setExprLexerInput(const std::string &in);
+extern void cl_expr_lex_clean();
+
+/*************** Standard ytab.c continues here *********************/
+%}
+
+/*************************************************************************/
+
+/* This group is used by the C/C++ language parser */
+%token LE_AUTO LE_DOUBLE LE_INT LE_STRUCT
+%token LE_BREAK LE_ELSE LE_LONG LE_SWITCH
+%token LE_CASE LE_ENUM LE_REGISTER LE_TYPEDEF
+%token LE_CHAR LE_EXTERN LE_RETURN LE_UNION
+%token LE_CONST LE_FLOAT LE_SHORT LE_UNSIGNED
+%token LE_CONTINUE LE_FOR LE_SIGNED LE_VOID
+%token LE_DEFAULT LE_GOTO LE_SIZEOF LE_VOLATILE
+%token LE_DO LE_IF LE_STATIC LE_WHILE
+
+/* The following are used in C++ only. ANSI C would call these IDENTIFIERs */
+%token LE_NEW LE_DELETE
+%token LE_THIS
+%token LE_OPERATOR
+%token LE_CLASS
+%token LE_PUBLIC LE_PROTECTED LE_PRIVATE
+%token LE_VIRTUAL LE_FRIEND
+%token LE_INLINE LE_OVERLOAD
+%token LE_TEMPLATE LE_TYPENAME
+%token LE_THROW LE_CATCH
+/* ANSI C Grammar suggestions */
+%token LE_IDENTIFIER LE_STRINGliteral
+%token LE_FLOATINGconstant LE_INTEGERconstant LE_CHARACTERconstant
+%token LE_OCTALconstant LE_HEXconstant
+%token LE_POUNDPOUND LE_CComment LE_CPPComment LE_NAMESPACE LE_USING
+
+/* New Lexical element, whereas ANSI C suggested non-terminal */
+%token LE_TYPEDEFname
+
+/* Multi-Character operators */
+%token LE_ARROW /* -> */
+%token LE_ICR LE_DECR /* ++ -- */
+%token LE_LS LE_RS /* << >> */
+%token LE_LE LE_GE LE_EQ LE_NE /* <= >= == != */
+%token LE_ANDAND LE_OROR /* && || */
+%token LE_ELLIPSIS /* ... */
+ /* Following are used in C++, not ANSI C */
+%token LE_CLCL /* :: */
+%token LE_DOTstar LE_ARROWstar /* .* ->* */
+
+/* modifying assignment operators */
+%token LE_MULTassign LE_DIVassign LE_MODassign /* *= /= %= */
+%token LE_PLUSassign LE_MINUSassign /* += -= */
+%token LE_LSassign LE_RSassign /* <<= >>= */
+%token LE_ANDassign LE_ERassign LE_ORassign /* &= ^= |= */
+%token LE_MACRO
+%token LE_DYNAMIC_CAST
+%token LE_STATIC_CAST
+%token LE_CONST_CAST
+%token LE_REINTERPRET_CAST
+
+%start translation_unit
+
+%%
+/* ========================================================================*/
+/* find declarations */
+/* ========================================================================*/
+
+translation_unit : /*empty*/
+ | translation_unit primary_expr
+ ;
+
+primary_expr : {result.Reset();} simple_expr
+ | error {
+ yyclearin; //clear lookahead token
+ yyerrok;
+ //fprintf(stderr, "CodeLite: syntax error, unexpected token '%s' found at line %d \n", cl_expr_text, cl_expr_lineno);
+ //fflush(stderr);
+ expr_syncParser();
+ }
+ ;
+
+const_spec : /* empty */ {$$ = ""; }
+ | LE_CONST { $$ = $1; }
+ ;
+
+basic_type_name:
+ LE_INT { $$ = $1; }
+ | LE_CHAR { $$ = $1; }
+ | LE_SHORT { $$ = $1; }
+ | LE_LONG { $$ = $1; }
+ | LE_FLOAT { $$ = $1; }
+ | LE_DOUBLE { $$ = $1; }
+ | LE_SIGNED { $$ = $1; }
+ | LE_UNSIGNED { $$ = $1; }
+ | LE_VOID { $$ = $1; }
+ ;
+
+parameter_list : /* empty */ {$$ = "";}
+ | template_parameter {$$ = $1;}
+ | parameter_list ',' template_parameter {$$ = $1 + $2 + $3;}
+ ;
+
+
+template_parameter : const_spec nested_scope_specifier LE_IDENTIFIER special_star_amp
+ {$$ = $1 + " " + $2 + " " + $3 +$4;}
+ | const_spec nested_scope_specifier basic_type_name special_star_amp
+ {$$ = $1 + " " + $2 + " " + $3 +$4;}
+ | const_spec nested_scope_specifier LE_IDENTIFIER '<' parameter_list '>' special_star_amp
+ {$$ = $1 + " " + $2 + " " + $3 +$4 + $5 + $6;}
+ ;
+
+simple_expr : stmnt_starter special_cast '<' cast_type '>' '('
+ {
+ expr_FuncArgList();
+ $$ = $4;
+ result.m_isaType = true;
+ result.m_name = $4;
+ result.m_isFunc = false;
+ printf("Rule 1\n");
+ //result.Print();
+ }
+ | stmnt_starter LE_THIS
+ {
+ $$ = $2;
+ result.m_isaType = false;
+ result.m_name = $$;
+ result.m_isFunc = false;
+ result.m_isThis = true;
+ result.m_isPtr = true;
+ //result.Print();
+ }
+ | stmnt_starter '*' LE_THIS
+ {
+ $$ = $3;
+ result.m_isaType = false;
+ result.m_name = $$;
+ result.m_isFunc = false;
+ result.m_isThis = true;
+ //result.Print();
+ }
+ | stmnt_starter '*' identifier_name
+ {
+ $$ = $3;
+ result.m_isaType = false;
+ result.m_name = $$;
+ result.m_isFunc = false;
+ result.m_isThis = false;
+ result.m_isPtr = false;
+ //result.Print();
+ }
+ | stmnt_starter '(' cast_type ')' special_star_amp identifier_name
+ {
+ $$ = $3;
+ result.m_isaType = true;
+ result.m_name = $$;
+ result.m_isFunc = false;
+ result.m_isThis = false;
+ //result.Print();
+ }
+ | stmnt_starter nested_scope_specifier identifier_name optional_template_init_list optinal_postifx
+ {
+ result.m_isaType = false;
+ result.m_name = $3;
+ result.m_isThis = false;
+ $2.erase($2.find_last_not_of(":")+1);
+ result.m_scope = $2;
+ result.m_isTemplate = $4.empty() ? false : true;
+ result.m_templateInitList = $4;
+ //result.Print();
+ }
+
+ | stmnt_starter '(' '(' cast_type ')' special_star_amp identifier_name ')'
+ {
+ $$ = $4;
+ result.m_isaType = true;
+ result.m_name = $$;
+ result.m_isFunc = false;
+ result.m_isThis = false;
+ //result.Print();
+ }
+
+ ;
+
+identifier_name : LE_IDENTIFIER array_brackets {$$ = $1;}
+ ;
+optional_template_init_list: /*empty*/ {$$ = "";}
+ | '<' parameter_list '>' {$$ = $1 + $2 + $3;}
+ ;
+
+optinal_postifx: /*empty*/ {$$ = "";}
+ | '('
+ {
+ $$ = $1;
+ expr_FuncArgList();
+ result.m_isFunc = true;
+ }
+ ;
+
+special_cast : LE_DYNAMIC_CAST {$$ = $1;}
+ | LE_STATIC_CAST {$$ = $1;}
+ | LE_CONST_CAST {$$ = $1;}
+ | LE_REINTERPRET_CAST {$$ = $1;}
+ ;
+
+amp_item : /*empty*/ {$$ = ""; }
+ | '&' { $$ = $1; }
+ ;
+
+star_list : /*empty*/ {$$ = ""; }
+ | star_list '*' {$$ = $1 + $2;}
+ ;
+
+special_star_amp : star_list amp_item { $$ = $1 + $2; }
+ ;
+
+stmnt_starter : /*empty*/ {$$ = "";}
+ | ';' { $$ = ";";}
+ | ':' { $$ = ":";} //e.g. private: std::string m_name;
+ ;
+
+cast_type: nested_scope_specifier LE_IDENTIFIER '<' parameter_list '>' special_star_amp
+ {
+ $$ = $1 + $2;
+ $1.erase($1.find_last_not_of(":")+1);
+ result.m_scope = $1;
+ result.m_name = $2;
+ result.m_isPtr = ($6.find("*") != (size_t)-1);;
+ result.m_isTemplate = true;
+ result.m_templateInitList = $3 + $4 + $5;
+ }
+ | nested_scope_specifier LE_IDENTIFIER special_star_amp
+ {
+ $$ = $1 + $2;
+ $1.erase($1.find_last_not_of(":")+1);
+ result.m_scope = $1;
+ result.m_name = $2;
+ result.m_isPtr = ($3.find("*") != (size_t)-1);;
+ }
+ ;
+
+nested_scope_specifier : /*empty*/ {$$ = "";}
+ | nested_scope_specifier scope_specifier { $$ = $1 + $2;}
+ ;
+
+scope_specifier : LE_IDENTIFIER LE_CLCL {$$ = $1+ $2;}
+ ;
+
+array_brackets : /* empty */ { $$ = ""; }
+ | '[' { expr_consumBracketsContent('['); $$ = "[]";}
+ ;
+%%
+void yyerror(char *s) {}
+
+void expr_consumBracketsContent(char openBrace)
+{
+ char closeBrace;
+
+ switch(openBrace) {
+ case '(': closeBrace = ')'; break;
+ case '[': closeBrace = ']'; break;
+ case '<': closeBrace = '>'; break;
+ case '{': closeBrace = '}'; break;
+ default:
+ openBrace = '(';
+ closeBrace = ')';
+ break;
+ }
+
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_expr_lex();
+ //printf("ch=%d\n", ch);
+ //fflush(stdout);
+ if(ch == 0){
+ break;
+ }
+
+ if(ch == closeBrace)
+ {
+ depth--;
+ continue;
+ }
+ else if(ch == openBrace)
+ {
+ depth ++ ;
+ continue;
+ }
+ }
+}
+
+void expr_FuncArgList()
+{
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_expr_lex();
+ //printf("ch=%d\n", ch);
+ //fflush(stdout);
+ if(ch ==0){
+ break;
+ }
+
+ if(ch == ')')
+ {
+ depth--;
+ continue;
+ }
+ else if(ch == '(')
+ {
+ depth ++ ;
+ continue;
+ }
+ }
+}
+
+void expr_consumeTemplateDecl()
+{
+ int depth = 1;
+ while(depth > 0)
+ {
+ int ch = cl_expr_lex();
+ //printf("ch=%d\n", ch);
+ fflush(stdout);
+ if(ch ==0){
+ break;
+ }
+
+ if(ch == '>')
+ {
+ depth--;
+ continue;
+ }
+ else if(ch == '<')
+ {
+ depth ++ ;
+ continue;
+ }
+ }
+}
+
+void expr_syncParser(){
+ //dont do anything, a hook to allow us to implement some
+ //nice error recovery if needed
+}
+
+// return the scope name at the end of the input string
+ExpressionResult &parse_expression(const std::string &in)
+{
+ result.Reset();
+ //provide the lexer with new input
+ if( !setExprLexerInput(in) ){
+ return result;
+ }
+
+ //printf("parsing...\n");
+ cl_expr_parse();
+ //do the lexer cleanup
+ cl_expr_lex_clean();
+
+ return result;
+}
diff --git a/plugins/symbol-db/cxxparser/grammars/expr_lexer.l b/plugins/symbol-db/cxxparser/grammars/expr_lexer.l
new file mode 100644
index 0000000..a8fcf99
--- /dev/null
+++ b/plugins/symbol-db/cxxparser/grammars/expr_lexer.l
@@ -0,0 +1,318 @@
+%{
+/* Included code before lex code */
+/*************** Includes and Defines *****************************/
+
+
+#include "map"
+#include "cpp_lexer.h" // YACC generated definitions based on C++ grammar
+#include "errno.h"
+
+#define YYSTYPE std::string
+
+#include "string"
+#include <stdlib.h>
+#include <string.h>
+#include <vector>
+
+extern std::string cl_expr_lval;
+extern std::string cl_var_lval;
+
+bool setExprLexerInput(const std::string &in);
+void cl_expr_lex_clean();
+
+bool exprIsaTYPE(char *string);
+bool exprIsaMACRO(char *string);
+static bool defineFound = false;
+
+/* Prototypes */
+#define WHITE_RETURN(x) /* do nothing */
+
+#define PA_KEYWORD_RETURN(x) RETURN_VAL(x) /* standard C PArser Keyword */
+#define CPP_KEYWORD_RETURN(x) PA_KEYWORD_RETURN(x) /* C++ keyword */
+#define PPPA_KEYWORD_RETURN(x) RETURN_VAL(x) /* both PreProcessor and PArser keyword */
+#define PP_KEYWORD_RETURN(x) IDENTIFIER_RETURN()
+
+#define IDENTIFIER_RETURN(){\
+ if(exprIsaTYPE(yytext)){\
+ RETURN_VAL(LE_TYPEDEFname);\
+ }else if(exprIsaMACRO(yytext)){\
+ RETURN_VAL(LE_MACRO);\
+ }else{ RETURN_VAL(LE_IDENTIFIER);}\
+ }
+
+
+#define PPOP_RETURN(x) RETURN_VAL((int)*yytext) /* PreProcess and Parser operator */
+#define NAMED_PPOP_RETURN(x) RETURN_VAL(x)
+#define ASCIIOP_RETURN(x) RETURN_VAL((int)*yytext) /* a single character operator */
+#define NAMEDOP_RETURN(x) RETURN_VAL(x) /* a multichar operator, with a name */
+
+#define NUMERICAL_RETURN(x) RETURN_VAL(x) /* some sort of constant */
+#define LITERAL_RETURN(x) RETURN_VAL(x) /* a string literal */
+#define C_COMMENT_RETURN(x) RETURN_VAL(x) /* C Style comment */
+#define RETURN_VAL(x) {\
+ cl_expr_lval = yytext;\
+ return(x);}
+%}
+
+%option yylineno
+
+identifier [a-zA-Z_][0-9a-zA-Z_]*
+
+exponent_part [eE][-+]?[0-9]+
+fractional_constant ([0-9]*"."[0-9]+)|([0-9]+".")
+floating_constant (({fractional_constant}{exponent_part}?)|([0-9]+{exponent_part}))[FfLl]?
+
+integer_suffix_opt ([uU]?[lL]?)|([lL][uU])
+decimal_constant [1-9][0-9]*{integer_suffix_opt}
+octal_constant "0"[0-7]*{integer_suffix_opt}
+hex_constant "0"[xX][0-9a-fA-F]+{integer_suffix_opt}
+
+simple_escape [abfnrtv'"?\\]
+octal_escape [0-7]{1,3}
+hex_escape "x"[0-9a-fA-F]+
+
+escape_sequence [\\]({simple_escape}|{octal_escape}|{hex_escape})
+c_char [^'\\\n]|{escape_sequence}
+s_char [^"\\\n]|{escape_sequence}
+
+h_tab [\011]
+form_feed [\014]
+v_tab [\013]
+c_return [\015]
+
+horizontal_white [ ]|{h_tab}
+
+%x PREPR
+%x WRAP_PREP
+%x CPP_COMMENT
+%x C_COMMENT
+
+%%
+
+"/*" {
+ BEGIN C_COMMENT;
+ }
+
+"//" {
+ BEGIN CPP_COMMENT;
+ }
+
+{horizontal_white}+ {
+ WHITE_RETURN(' ');
+ }
+
+({v_tab}|{c_return}|{form_feed})+ {
+ WHITE_RETURN(' ');
+ }
+
+
+({horizontal_white}|{v_tab}|{c_return}|{form_feed})*"\n" {
+ WHITE_RETURN('\n');
+ }
+
+auto {PA_KEYWORD_RETURN(LE_AUTO);}
+break {PA_KEYWORD_RETURN(LE_BREAK);}
+case {PA_KEYWORD_RETURN(LE_CASE);}
+char {PA_KEYWORD_RETURN(LE_CHAR);}
+const {PA_KEYWORD_RETURN(LE_CONST);}
+continue {PA_KEYWORD_RETURN(LE_CONTINUE);}
+default {PA_KEYWORD_RETURN(LE_DEFAULT);}
+define {PP_KEYWORD_RETURN(LE_DEFINE);}
+defined {PP_KEYWORD_RETURN(LE_OPDEFINED);}
+do {PA_KEYWORD_RETURN(LE_DO);}
+double {PA_KEYWORD_RETURN(LE_DOUBLE);}
+elif {PP_KEYWORD_RETURN(LE_ELIF);}
+else {PPPA_KEYWORD_RETURN(LE_ELSE);}
+endif {PP_KEYWORD_RETURN(LE_ENDIF);}
+enum {PA_KEYWORD_RETURN(LE_ENUM);}
+error {PP_KEYWORD_RETURN(LE_ERROR);}
+extern {PA_KEYWORD_RETURN(LE_EXTERN);}
+float {PA_KEYWORD_RETURN(LE_FLOAT);}
+for {PA_KEYWORD_RETURN(LE_FOR);}
+goto {PA_KEYWORD_RETURN(LE_GOTO);}
+if {PPPA_KEYWORD_RETURN(LE_IF);}
+ifdef {PP_KEYWORD_RETURN(LE_IFDEF);}
+ifndef {PP_KEYWORD_RETURN(LE_IFNDEF);}
+include {PP_KEYWORD_RETURN(LE_INCLUDE); }
+int {PA_KEYWORD_RETURN(LE_INT);}
+line {PP_KEYWORD_RETURN(LE_LINE);}
+long {PA_KEYWORD_RETURN(LE_LONG);}
+pragma {PP_KEYWORD_RETURN(LE_PRAGMA);}
+register {PA_KEYWORD_RETURN(LE_REGISTER);}
+return {PA_KEYWORD_RETURN(LE_RETURN);}
+short {PA_KEYWORD_RETURN(LE_SHORT);}
+signed {PA_KEYWORD_RETURN(LE_SIGNED);}
+sizeof {PA_KEYWORD_RETURN(LE_SIZEOF);}
+static {PA_KEYWORD_RETURN(LE_STATIC);}
+struct {PA_KEYWORD_RETURN(LE_STRUCT);}
+switch {PA_KEYWORD_RETURN(LE_SWITCH);}
+typedef {PA_KEYWORD_RETURN(LE_TYPEDEF);}
+undef {PP_KEYWORD_RETURN(LE_UNDEF);}
+union {PA_KEYWORD_RETURN(LE_UNION);}
+unsigned {PA_KEYWORD_RETURN(LE_UNSIGNED);}
+void {PA_KEYWORD_RETURN(LE_VOID);}
+volatile {PA_KEYWORD_RETURN(LE_VOLATILE);}
+while {PA_KEYWORD_RETURN(LE_WHILE);}
+
+
+class {CPP_KEYWORD_RETURN(LE_CLASS);}
+namespace {CPP_KEYWORD_RETURN(LE_NAMESPACE);}
+delete {CPP_KEYWORD_RETURN(LE_DELETE);}
+friend {CPP_KEYWORD_RETURN(LE_FRIEND);}
+inline {CPP_KEYWORD_RETURN(LE_INLINE);}
+new {CPP_KEYWORD_RETURN(LE_NEW);}
+operator {CPP_KEYWORD_RETURN(LE_OPERATOR);}
+overload {CPP_KEYWORD_RETURN(LE_OVERLOAD);}
+protected {CPP_KEYWORD_RETURN(LE_PROTECTED);}
+private {CPP_KEYWORD_RETURN(LE_PRIVATE);}
+public {CPP_KEYWORD_RETURN(LE_PUBLIC);}
+this {CPP_KEYWORD_RETURN(LE_THIS);}
+virtual {CPP_KEYWORD_RETURN(LE_VIRTUAL);}
+template {CPP_KEYWORD_RETURN(LE_TEMPLATE);}
+typename {CPP_KEYWORD_RETURN(LE_TYPENAME);}
+dynamic_cast {CPP_KEYWORD_RETURN(LE_DYNAMIC_CAST);}
+static_cast {CPP_KEYWORD_RETURN(LE_STATIC_CAST);}
+const_cast {CPP_KEYWORD_RETURN(LE_CONST_CAST);}
+reinterpret_cast {CPP_KEYWORD_RETURN(LE_REINTERPRET_CAST);}
+using {CPP_KEYWORD_RETURN(LE_USING);}
+throw {CPP_KEYWORD_RETURN(LE_THROW);}
+catch {CPP_KEYWORD_RETURN(LE_CATCH);}
+{identifier} {IDENTIFIER_RETURN();}
+
+{decimal_constant} {NUMERICAL_RETURN(LE_INTEGERconstant);}
+{octal_constant} {NUMERICAL_RETURN(LE_OCTALconstant);}
+{hex_constant} {NUMERICAL_RETURN(LE_HEXconstant);}
+{floating_constant} {NUMERICAL_RETURN(LE_FLOATINGconstant);}
+
+
+"L"?[']{c_char}+['] {
+ NUMERICAL_RETURN(LE_CHARACTERconstant);
+ }
+
+
+"L"?["]{s_char}*["] {
+ LITERAL_RETURN(LE_STRINGliteral);}
+
+
+
+
+"(" {PPOP_RETURN(LE_LP);}
+")" {PPOP_RETURN(LE_RP);}
+"," {PPOP_RETURN(LE_COMMA);}
+^"#" {BEGIN PREPR;}
+"{" {ASCIIOP_RETURN(LE_LC);}
+"}" {ASCIIOP_RETURN(LE_RC);}
+"[" {ASCIIOP_RETURN(LE_LB);}
+"]" {ASCIIOP_RETURN(LE_RB);}
+"." {ASCIIOP_RETURN(LE_DOT);}
+"&" {ASCIIOP_RETURN(LE_AND);}
+"*" {ASCIIOP_RETURN(LE_STAR);}
+"+" {ASCIIOP_RETURN(LE_PLUS);}
+"-" {ASCIIOP_RETURN(LE_MINUS);}
+"~" {ASCIIOP_RETURN(LE_NEGATE);}
+"!" {ASCIIOP_RETURN(LE_NOT);}
+"/" {ASCIIOP_RETURN(LE_DIV);}
+"%" {ASCIIOP_RETURN(LE_MOD);}
+"<" {ASCIIOP_RETURN(LE_LT);}
+">" {ASCIIOP_RETURN(LE_GT);}
+"^" {ASCIIOP_RETURN(LE_XOR);}
+"|" {ASCIIOP_RETURN(LE_PIPE);}
+"?" {ASCIIOP_RETURN(LE_QUESTION);}
+":" {ASCIIOP_RETURN(LE_COLON);}
+";" {ASCIIOP_RETURN(LE_SEMICOLON);}
+"=" {ASCIIOP_RETURN(LE_ASSIGN);}
+
+".*" {NAMEDOP_RETURN(LE_DOTstar);}
+"::" {NAMEDOP_RETURN(LE_CLCL);}
+"->" {NAMEDOP_RETURN(LE_ARROW);}
+"->*" {NAMEDOP_RETURN(LE_ARROWstar);}
+"++" {NAMEDOP_RETURN(LE_ICR);}
+"--" {NAMEDOP_RETURN(LE_DECR);}
+"<<" {NAMEDOP_RETURN(LE_LS);}
+">>" {NAMEDOP_RETURN(LE_RS);}
+"<=" {NAMEDOP_RETURN(LE_LE);}
+">=" {NAMEDOP_RETURN(LE_GE);}
+"==" {NAMEDOP_RETURN(LE_EQ);}
+"!=" {NAMEDOP_RETURN(LE_NE);}
+"&&" {NAMEDOP_RETURN(LE_ANDAND);}
+"||" {NAMEDOP_RETURN(LE_OROR);}
+"*=" {NAMEDOP_RETURN(LE_MULTassign);}
+"/=" {NAMEDOP_RETURN(LE_DIVassign);}
+"%=" {NAMEDOP_RETURN(LE_MODassign);}
+"+=" {NAMEDOP_RETURN(LE_PLUSassign);}
+"-=" {NAMEDOP_RETURN(LE_MINUSassign);}
+"<<=" {NAMEDOP_RETURN(LE_LSassign);}
+">>=" {NAMEDOP_RETURN(LE_RSassign);}
+"&=" {NAMEDOP_RETURN(LE_ANDassign);}
+"^=" {NAMEDOP_RETURN(LE_ERassign);}
+"|=" {NAMEDOP_RETURN(LE_ORassign);}
+"..." {NAMEDOP_RETURN(LE_ELLIPSIS);}
+<<EOF>> {
+ //reset lexer
+ yyterminate();
+ }
+. {return yytext[0];}
+<PREPR>\n {
+ defineFound = false;
+ BEGIN INITIAL;
+ }
+<PREPR>\\ {
+ BEGIN WRAP_PREP;
+ }
+<PREPR>define {
+ defineFound = true;
+ }
+<WRAP_PREP>\n {
+ BEGIN PREPR;
+ }
+<WRAP_PREP>{identifier} {
+ if(defineFound)
+ {
+ defineFound = false;
+ }
+ }
+<PREPR>{identifier} {
+ if(defineFound)
+ {
+ defineFound = false;
+ }
+ }
+<WRAP_PREP>. {}
+<PREPR>. {}
+<CPP_COMMENT>\n {BEGIN INITIAL;}
+<CPP_COMMENT>. {}
+<C_COMMENT>"*/" {BEGIN INITIAL;}
+<C_COMMENT>. {}
+%%
+
+bool exprIsaTYPE(char *string)
+{
+ return false;
+}
+
+bool exprIsaMACRO(char *string)
+{
+ return false;
+}
+
+void cl_expr_lex_clean()
+{
+ yy_flush_buffer(YY_CURRENT_BUFFER);
+ yy_delete_buffer(YY_CURRENT_BUFFER);
+ cl_expr_lineno = 1;
+}
+
+/*******************************************************************/
+bool setExprLexerInput(const std::string &in)
+{
+ BEGIN INITIAL;
+ yy_scan_string(in.c_str());
+
+ //update the working file name
+ return true;
+}
+
+int yywrap()
+{
+ return 1;
+}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]