📄 parser.y
字号:
;char_type: TOK_CHAR { $$ = IDL_type_char_new (); } ;wide_char_type: TOK_WCHAR { $$ = IDL_type_wide_char_new (); } ;boolean_type: TOK_BOOLEAN { $$ = IDL_type_boolean_new (); } ;octet_type: TOK_OCTET { $$ = IDL_type_octet_new (); } ;any_type: TOK_ANY { $$ = IDL_type_any_new (); } ;object_type: TOK_OBJECT { $$ = IDL_type_object_new (); } ;typecode_type: TOK_TYPECODE { $$ = IDL_type_typecode_new (); } ;string_type: TOK_STRING '<' positive_int_const '>' { $$ = IDL_type_string_new ($3); }| TOK_STRING { $$ = IDL_type_string_new (NULL); } ;wide_string_type: TOK_WSTRING '<' positive_int_const '>' { $$ = IDL_type_wide_string_new ($3); }| TOK_WSTRING { $$ = IDL_type_wide_string_new (NULL); } ;declarator_list: declarator { $$ = list_start ($1, TRUE); }| declarator_list check_comma declarator { $$ = list_chain ($1, $3, TRUE); } ;declarator: simple_declarator| complex_declarator ;simple_declarator: new_ident ;complex_declarator: array_declarator ;simple_declarator_list: simple_declarator { $$ = list_start ($1, TRUE); }| simple_declarator_list check_comma simple_declarator { $$ = list_chain ($1, $3, TRUE); } ;array_declarator: new_ident fixed_array_size_list { IDL_tree p; int i; $$ = IDL_type_array_new ($1, $2); for (i = 1, p = $2; p; ++i, p = IDL_LIST (p).next) if (!IDL_LIST (p).data) { char *s = IDL_ns_ident_to_qstring ($1, "::", 0); yyerrorv ("Missing value in dimension %d of array `%s'", i, s); g_free (s); }} ;fixed_array_size_list: fixed_array_size { $$ = list_start ($1, FALSE); }| fixed_array_size_list fixed_array_size { $$ = list_chain ($1, $2, FALSE); } ;fixed_array_size: '[' positive_int_const ']' { $$ = $2; }| '[' ']' { $$ = NULL; } ;prop_hash: TOK_PROP_KEY TOK_PROP_VALUE { $$ = g_hash_table_new (IDL_strcase_hash, IDL_strcase_equal); g_hash_table_insert ($$, $1, $2);}| prop_hash ',' TOK_PROP_KEY TOK_PROP_VALUE { $$ = $1; g_hash_table_insert ($$, $3, $4);}| TOK_PROP_KEY { $$ = g_hash_table_new (IDL_strcase_hash, IDL_strcase_equal); g_hash_table_insert ($$, $1, g_strdup (""));}| prop_hash ',' TOK_PROP_KEY { $$ = $1; g_hash_table_insert ($$, $3, g_strdup (""));} ;ident: TOK_IDENT { $$ = IDL_ident_new ($1); } ;new_ident: ns_new_ident { assert ($1 != NULL); assert (IDL_NODE_TYPE ($1) == IDLN_GENTREE); assert (IDL_NODE_TYPE (IDL_GENTREE ($1).data) == IDLN_IDENT); $$ = IDL_GENTREE ($1).data;} ;new_scope: ns_new_ident { IDL_ns_push_scope (__IDL_root_ns, $1);#ifdef YYDEBUG if (yydebug) printf ("entering new/prev scope of %s\n", IDL_IDENT (IDL_GENTREE (IDL_NS (__IDL_root_ns).current).data).str);#endif assert (IDL_NODE_TYPE (IDL_GENTREE ($1).data) == IDLN_IDENT); $$ = IDL_GENTREE ($1).data;} ;new_or_prev_scope: cur_ns_new_or_prev_ident { IDL_ns_push_scope (__IDL_root_ns, $1); assert (IDL_NS (__IDL_root_ns).current != NULL); assert (IDL_NODE_TYPE (IDL_NS (__IDL_root_ns).current) == IDLN_GENTREE); assert (IDL_GENTREE (IDL_NS (__IDL_root_ns).current).data != NULL); assert (IDL_NODE_TYPE (IDL_GENTREE (IDL_NS (__IDL_root_ns).current).data) == IDLN_IDENT);#ifdef YYDEBUG if (yydebug) printf ("entering new/prev scope of %s\n", IDL_IDENT (IDL_GENTREE (IDL_NS (__IDL_root_ns).current).data).str);#endif assert (IDL_NODE_TYPE (IDL_GENTREE ($1).data) == IDLN_IDENT); $$ = IDL_GENTREE ($1).data;} ;pop_scope: /* empty */ {#ifdef YYDEBUG if (yydebug) printf ("scope to parent of %s\n", IDL_IDENT (IDL_GENTREE (IDL_NS (__IDL_root_ns).current).data).str);#endif IDL_ns_pop_scope (__IDL_root_ns);} ;ns_new_ident: ident { IDL_tree p; if ((p = IDL_ns_place_new (__IDL_root_ns, $1)) == NULL) { IDL_tree q; int i; p = IDL_ns_lookup_cur_scope (__IDL_root_ns, $1, NULL); for (i = 0, q = IDL_GENTREE (p).data; q && (IDL_NODE_TYPE (q) == IDLN_IDENT || IDL_NODE_TYPE (q) == IDLN_LIST) && i < 4; ++i) if (IDL_NODE_UP (q)) q = IDL_NODE_UP (q); if (q) { IDL_tree_error ($1, "`%s' conflicts", IDL_IDENT ($1).str); do_token_error (q, "with", FALSE); } else yyerrorv ("`%s' duplicate identifier", IDL_IDENT ($1).str); IDL_tree_free ($1); YYABORT; } assert (IDL_IDENT ($1)._ns_ref == p);#ifdef REF_IDENTS ++IDL_NODE_REFS (IDL_GENTREE (p).data);#endif if (__IDL_new_ident_comments != NULL) { assert (IDL_IDENT ($1).comments == NULL); IDL_IDENT ($1).comments = __IDL_new_ident_comments; __IDL_new_ident_comments = NULL; } $$ = p;} ;ns_prev_ident: ident { IDL_tree p; if ((p = IDL_ns_resolve_ident (__IDL_root_ns, $1)) == NULL) { yyerrorv ("`%s' undeclared identifier", IDL_IDENT ($1).str); IDL_tree_free ($1); YYABORT; } IDL_tree_free ($1); assert (IDL_GENTREE (p).data != NULL); assert (IDL_IDENT (IDL_GENTREE (p).data)._ns_ref == p);#ifdef REF_IDENTS ++IDL_NODE_REFS (IDL_GENTREE (p).data);#endif $$ = p;} ;cur_ns_new_or_prev_ident: ident { IDL_tree p; if ((p = IDL_ns_lookup_cur_scope (__IDL_root_ns, $1, NULL)) == NULL) { p = IDL_ns_place_new (__IDL_root_ns, $1); assert (p != NULL); assert (IDL_IDENT ($1)._ns_ref == p); if (__IDL_new_ident_comments != NULL) { assert (IDL_IDENT ($1).comments == NULL); IDL_IDENT ($1).comments = __IDL_new_ident_comments; __IDL_new_ident_comments = NULL; } } else { IDL_tree_free ($1); assert (IDL_GENTREE (p).data != NULL); assert (IDL_IDENT (IDL_GENTREE (p).data)._ns_ref == p); }#ifdef REF_IDENTS ++IDL_NODE_REFS (IDL_GENTREE (p).data);#endif $$ = p;} ;ns_global_ident: ident { IDL_tree p; if ((p = IDL_ns_lookup_this_scope ( __IDL_root_ns,IDL_NS (__IDL_root_ns).file, $1, NULL)) == NULL) { yyerrorv ("`%s' undeclared identifier", IDL_IDENT ($1).str); IDL_tree_free ($1); YYABORT; } IDL_tree_free ($1); assert (IDL_GENTREE (p).data != NULL); assert (IDL_IDENT (IDL_GENTREE (p).data)._ns_ref == p);#ifdef REF_IDENTS ++IDL_NODE_REFS (IDL_GENTREE (p).data);#endif $$ = p;} ;string_lit_list: string_lit { $$ = list_start ($1, TRUE); }| string_lit_list check_comma string_lit { $$ = list_chain ($1, $3, TRUE); } ;positive_int_const: const_exp { IDL_tree literal, ident = NULL; IDL_longlong_t value = 0; if ((literal = IDL_resolve_const_exp ($1, IDLN_INTEGER))) { assert (IDL_NODE_TYPE (literal) == IDLN_INTEGER); value = IDL_INTEGER (literal).value; IDL_tree_free ($1); } if (literal && IDL_NODE_UP (literal) && IDL_NODE_TYPE (IDL_NODE_UP (literal)) == IDLN_CONST_DCL) ident = IDL_CONST_DCL (IDL_NODE_UP (literal)).ident; if (literal == NULL) { if (!(__IDL_flags & IDLF_NO_EVAL_CONST)) yyerror ("Could not resolve constant expression"); $$ = $1; } else if (value == 0) { yyerror ("Zero array size is illegal"); if (ident) IDL_tree_error (ident, "From constant declared here"); $$ = NULL; } else if (value < 0) { yywarningv (IDL_WARNING1, "Cannot use negative value %" IDL_LL "d, using %" IDL_LL "d", value, -value); if (ident) IDL_tree_warning (ident, IDL_WARNING1, "From constant declared here"); $$ = IDL_integer_new (-value); } else $$ = IDL_integer_new (value);} ;z_declspec: /* empty */ { $$ = 0; }| TOK_DECLSPEC { $$ = IDL_parse_declspec ($1); g_free ($1);} ;z_props: /* empty */ { $$ = NULL; }| '[' { /* Enable property scanning */ if (__IDL_flags & IDLF_PROPERTIES) __IDL_flagsi |= IDLFP_PROPERTIES; else { yyerror ("Property syntax not enabled"); YYABORT; }} prop_hash ']' { $$ = $3; } ;integer_lit: TOK_INTEGER { $$ = IDL_integer_new ($1); } ;string_lit: dqstring_cat { $$ = IDL_string_new ($1); } ;char_lit: sqstring { $$ = IDL_char_new ($1); } ;fixed_pt_lit: TOK_FIXEDP { $$ = IDL_fixed_new ($1); } ;floating_pt_lit: TOK_FLOATP { $$ = IDL_float_new ($1); } ;boolean_lit: TOK_TRUE { $$ = IDL_boolean_new (TRUE); }| TOK_FALSE { $$ = IDL_boolean_new (FALSE); } ;codefrag: z_declspec TOK_CODEFRAG { $$ = $2; assign_declspec ($$, $1);} ;dqstring_cat: dqstring| dqstring_cat dqstring { char *catstr = g_malloc (strlen ($1) + strlen ($2) + 1); strcpy (catstr, $1); g_free ($1); strcat (catstr, $2); g_free ($2); $$ = catstr;} ;dqstring: TOK_DQSTRING { char *s = IDL_do_escapes ($1); g_free ($1); $$ = s;} ;sqstring: TOK_SQSTRING { char *s = IDL_do_escapes ($1); g_free ($1); $$ = s;} ;%%void __IDL_parser_reset (void){ yyclearin;}static const char *IDL_ns_get_cur_prefix (IDL_ns ns){ IDL_tree p; p = IDL_NS (ns).current; assert (p != NULL); while (p && !IDL_GENTREE (p)._cur_prefix) p = IDL_NODE_UP (p); return p ? IDL_GENTREE (p)._cur_prefix : NULL;}gchar *IDL_ns_ident_make_repo_id (IDL_ns ns, IDL_tree p, const char *p_prefix, int *major, int *minor){ GString *s = g_string_new (NULL); const char *prefix; char *q; assert (p != NULL); if (IDL_NODE_TYPE (p) == IDLN_IDENT) p = IDL_IDENT_TO_NS (p); assert (p != NULL); prefix = p_prefix ? p_prefix : IDL_ns_get_cur_prefix (ns); q = IDL_ns_ident_to_qstring (p, "/", 0); g_string_sprintf (s, "IDL:%s%s%s:%d.%d", prefix ? prefix : "", prefix && *prefix ? "/" : "", q, major ? *major : 1, minor ? *minor : 0); g_free (q); q = s->str; g_string_free (s, FALSE); return q;}static const char *get_name_token (const char *s, char **tok){ const char *begin = s; int state = 0; if (!s) return NULL; while (isspace (*s)) ++s; while (1) switch (state) { case 0: /* Unknown */ if (*s == ':') state = 1; else if (isalnum (*s) || *s == '_') { begin = s; state = 2; } else return NULL; break; case 1: /* Scope */ if (strncmp (s, "::", 2) == 0) { char *r = g_malloc (3); strcpy (r, "::"); *tok = r; return s + 2; } else /* Invalid */ return NULL; break; case 2: if (isalnum (*s) || *s == '_') ++s; else { char *r = g_malloc (s - begin + 1); strncpy (r, begin, s - begin + 1); r[s - begin] = 0; *tok = r; return s; } break; }}static IDL_tree IDL_ns_pragma_parse_name (IDL_ns ns, const char *s){ IDL_tree p = IDL_NS (ns).current; int start = 1; char *tok; while (p && *s && (s = get_name_token (s, &tok))) { if (tok == NULL) return NULL; if (strcmp (tok, "::") == 0) { if (start) { /* Globally scoped */ p = IDL_NS (ns).file; } g_free (tok); } else { IDL_tree ident = IDL_ident_new (tok); p = IDL_ns_lookup_this_scope (__IDL_root_ns, p, ident, NULL); IDL_tree_free (ident); } start = 0; } return p;}void IDL_ns_ID (IDL_ns ns, const char *s){ char name[1024], id[1024]; IDL_tree p, ident; int n; n = sscanf (s, "%1023s \"%1023s\"", name, id); if (n < 2 && __IDL_is_parsing) { yywarning (IDL_WARNING1, "Malformed pragma ID"); return; } if (id[strlen (id) - 1] == '"') id[strlen (id) - 1] = 0; p = IDL_ns_pragma_parse_name (__IDL_root_ns, name); if (!p && __IDL_is_parsing) { yywarningv (IDL_WARNING1, "Unknown identifier `%s' in pragma ID", name); return; } /* We have resolved the identifier, so assign the repo id */ assert (IDL_NODE_TYPE (p) == IDLN_GENTREE); assert (IDL_GENTREE (p).data != NULL); assert (IDL_NODE_TYPE (IDL_GENTREE (p).data) == IDLN_IDENT); ident = IDL_GENTREE (p).data; if (IDL_IDENT_REPO_ID (ident) != NULL) g_free (IDL_IDENT_REPO_ID (ident)); IDL_IDENT_REPO_ID (ident) = g_strdup (id);}void IDL_ns_version (IDL_ns ns, const char *s){ char name[1024]; int n, major, minor; IDL_tree p, ident; n = sscanf (s, "%1023s %u %u", name, &major, &minor); if (n < 3 && __IDL_is_parsing) { yywarning (IDL_WARNING1, "Malformed pragma version"); return; } p = IDL_ns_pragma_parse_name (__IDL_root_ns, name);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -