summaryrefslogtreecommitdiff
path: root/vala
diff options
context:
space:
mode:
Diffstat (limited to 'vala')
-rw-r--r--vala/Makefile.am16
-rw-r--r--vala/parser.y644
-rw-r--r--vala/scanner.l1
-rw-r--r--vala/vala.h3
-rw-r--r--vala/valaarray.vala2
-rw-r--r--vala/valaarraylengthfield.vala2
-rw-r--r--vala/valaarrayresizemethod.vala2
-rw-r--r--vala/valaattributeprocessor.vala8
-rw-r--r--vala/valablock.vala5
-rw-r--r--vala/valabreakstatement.vala4
-rw-r--r--vala/valacallback.vala9
-rw-r--r--vala/valaclass.vala63
-rw-r--r--vala/valacodecontext.vala44
-rw-r--r--vala/valacodenode.vala7
-rw-r--r--vala/valacodevisitor.vala16
-rw-r--r--vala/valaconstant.vala19
-rw-r--r--vala/valaconstructor.vala9
-rw-r--r--vala/valacontinuestatement.vala4
-rw-r--r--vala/valacreationmethod.vala2
-rw-r--r--vala/valadatatype.vala52
-rw-r--r--vala/valadeclarationstatement.vala4
-rw-r--r--vala/valadestructor.vala19
-rw-r--r--vala/valadostatement.vala11
-rw-r--r--vala/valaemptystatement.vala4
-rw-r--r--vala/valaenum.vala24
-rw-r--r--vala/valaenumvalue.vala16
-rw-r--r--vala/valaexpressionstatement.vala24
-rw-r--r--vala/valafield.vala24
-rw-r--r--vala/valaflags.vala150
-rw-r--r--vala/valaflagsvalue.vala80
-rw-r--r--vala/valaforeachstatement.vala11
-rw-r--r--vala/valaformalparameter.vala7
-rw-r--r--vala/valaforstatement.vala9
-rw-r--r--vala/valaifstatement.vala4
-rw-r--r--vala/valainterface.vala28
-rw-r--r--vala/valainterfacewriter.vala96
-rw-r--r--vala/valalockstatement.vala11
-rw-r--r--vala/valamember.vala4
-rw-r--r--vala/valamemorymanager.vala36
-rw-r--r--vala/valamethod.vala29
-rw-r--r--vala/valanamespace.vala153
-rw-r--r--vala/valaproperty.vala7
-rw-r--r--vala/valapropertyaccessor.vala14
-rw-r--r--vala/valareturnstatement.vala4
-rw-r--r--vala/valascope.vala89
-rw-r--r--vala/valasemanticanalyzer.vala457
-rw-r--r--vala/valasignal.vala13
-rw-r--r--vala/valasourcefile.vala35
-rw-r--r--vala/valastatement.vala14
-rw-r--r--vala/valastruct.vala33
-rw-r--r--vala/valaswitchstatement.vala2
-rw-r--r--vala/valasymbol.vala144
-rw-r--r--vala/valasymbolbuilder.vala427
-rw-r--r--vala/valasymbolresolver.vala62
-rw-r--r--vala/valathrowstatement.vala2
-rw-r--r--vala/valatrystatement.vala2
-rw-r--r--vala/valatypeparameter.vala15
-rw-r--r--vala/valatypereference.vala2
-rw-r--r--vala/valavariabledeclarator.vala12
-rw-r--r--vala/valawhilestatement.vala11
60 files changed, 1156 insertions, 1845 deletions
diff --git a/vala/Makefile.am b/vala/Makefile.am
index 7ce1baee1..fe04e51bf 100644
--- a/vala/Makefile.am
+++ b/vala/Makefile.am
@@ -127,12 +127,6 @@ libvalacore_la_SOURCES = \
valafield.c \
valafield.h \
valafield.vala \
- valaflags.c \
- valaflags.h \
- valaflags.vala \
- valaflagsvalue.c \
- valaflagsvalue.h \
- valaflagsvalue.vala \
valaforeachstatement.c \
valaforeachstatement.h \
valaforeachstatement.vala \
@@ -247,6 +241,9 @@ libvalacore_la_SOURCES = \
valareturnstatement.c \
valareturnstatement.h \
valareturnstatement.vala \
+ valascope.c \
+ valascope.h \
+ valascope.vala \
valasemanticanalyzer.c \
valasemanticanalyzer.h \
valasemanticanalyzer.vala \
@@ -283,9 +280,6 @@ libvalacore_la_SOURCES = \
valaswitchstatement.c \
valaswitchstatement.h \
valaswitchstatement.vala \
- valasymbolbuilder.c \
- valasymbolbuilder.h \
- valasymbolbuilder.vala \
valasymbol.c \
valasymbol.h \
valasymbol.vala \
@@ -360,8 +354,6 @@ valainclude_HEADERS = \
valaexpression.h \
valaexpressionstatement.h \
valafield.h \
- valaflags.h \
- valaflagsvalue.h \
valaforeachstatement.h \
valaformalparameter.h \
valaforstatement.h \
@@ -400,6 +392,7 @@ valainclude_HEADERS = \
valareferencetransferexpression.h \
valareport.h \
valareturnstatement.h \
+ valascope.h \
valasemanticanalyzer.h \
valasignal.h \
valasizeofexpression.h \
@@ -412,7 +405,6 @@ valainclude_HEADERS = \
valaswitchlabel.h \
valaswitchsection.h \
valaswitchstatement.h \
- valasymbolbuilder.h \
valasymbol.h \
valasymbolresolver.h \
valathrowstatement.h \
diff --git a/vala/parser.y b/vala/parser.y
index 79042d6ea..58a6c5f43 100644
--- a/vala/parser.y
+++ b/vala/parser.y
@@ -36,12 +36,8 @@
#define src_com(l,c) (vala_source_reference_new_with_comment (current_source_file, l.first_line, l.first_column, l.last_line, l.last_column, c))
static ValaSourceFile *current_source_file;
-static ValaNamespace *current_namespace;
-static gboolean current_namespace_implicit;
-static ValaClass *current_class;
-static ValaStruct *current_struct;
-static ValaInterface *current_interface;
-static ValaEnum *current_enum;
+static GList *symbol_stack;
+static GList *scope_stack;
typedef enum {
VALA_MODIFIER_NONE,
@@ -53,6 +49,12 @@ typedef enum {
int yylex (YYSTYPE *yylval_param, YYLTYPE *yylloc_param, ValaParser *parser);
static void yyerror (YYLTYPE *locp, ValaParser *parser, const char *msg);
+
+static void push_symbol (ValaSymbol *symbol);
+static ValaSymbol *pop_symbol (void);
+
+static gboolean check_is_namespace (ValaSymbol *symbol, ValaSourceReference *src);
+static gboolean check_is_class (ValaSymbol *symbol, ValaSourceReference *src);
%}
%defines
@@ -69,15 +71,10 @@ static void yyerror (YYLTYPE *locp, ValaParser *parser, const char *msg);
ValaTypeReference *type_reference;
ValaExpression *expression;
ValaStatement *statement;
- ValaNamespace *namespace;
- ValaClass *class;
+ ValaBlock *block;
ValaStruct *struct_;
ValaInterface *interface;
- ValaEnum *enum_;
ValaEnumValue *enum_value;
- ValaFlags *flags;
- ValaFlagsValue *flags_value;
- ValaCallback *callback;
ValaConstant *constant;
ValaField *field;
ValaMethod *method;
@@ -167,7 +164,6 @@ static void yyerror (YYLTYPE *locp, ValaParser *parser, const char *msg);
%token ENUM "enum"
%token VALA_FALSE "false"
%token FINALLY "finally"
-%token FLAGS "flags"
%token FOR "for"
%token FOREACH "foreach"
%token GET "get"
@@ -269,8 +265,8 @@ static void yyerror (YYLTYPE *locp, ValaParser *parser, const char *msg);
%type <expression> opt_expression
%type <expression> expression
%type <statement> statement
-%type <statement> embedded_statement
-%type <statement> block
+%type <block> embedded_statement
+%type <block> block
%type <list> opt_statement_list
%type <list> statement_list
%type <statement> empty_statement
@@ -307,13 +303,11 @@ static void yyerror (YYLTYPE *locp, ValaParser *parser, const char *msg);
%type <catch_clause> specific_catch_clause
%type <catch_clause> opt_general_catch_clause
%type <catch_clause> general_catch_clause
-%type <statement> opt_finally_clause
-%type <statement> finally_clause
+%type <block> opt_finally_clause
+%type <block> finally_clause
%type <statement> lock_statement
-%type <namespace> namespace_declaration
%type <str> opt_name_specifier
%type <str> name_specifier
-%type <class> class_declaration
%type <num> opt_access_modifier
%type <num> access_modifier
%type <num> opt_modifiers
@@ -326,16 +320,7 @@ static void yyerror (YYLTYPE *locp, ValaParser *parser, const char *msg);
%type <property_accessor> get_accessor_declaration
%type <property_accessor> opt_set_accessor_declaration
%type <property_accessor> set_accessor_declaration
-%type <struct_> struct_declaration
%type <struct_> struct_header
-%type <interface> interface_declaration
-%type <enum_> enum_declaration
-%type <flags> flags_declaration
-%type <list> flags_body
-%type <list> opt_flags_member_declarations
-%type <list> flags_member_declarations
-%type <flags_value> flags_member_declaration
-%type <callback> callback_declaration
%type <constant> constant_declaration
%type <field> field_declaration
%type <list> variable_declarators
@@ -346,7 +331,7 @@ static void yyerror (YYLTYPE *locp, ValaParser *parser, const char *msg);
%type <expression> variable_initializer
%type <method> method_declaration
%type <method> method_header
-%type <statement> method_body
+%type <block> method_body
%type <list> opt_formal_parameter_list
%type <list> formal_parameter_list
%type <num> opt_construct
@@ -1051,7 +1036,7 @@ shift_expression
g_object_unref ($1);
g_object_unref ($3);
}
- /* don't use two OP_GT due to resolve parse conflicts
+ /* don't use two OP_GT to resolve parse conflicts
* stacked generics won't be that common in vala */
| shift_expression OP_SHIFT_RIGHT additive_expression
{
@@ -1350,6 +1335,9 @@ expression
statement
: declaration_statement
| block
+ {
+ $$ = VALA_STATEMENT ($1);
+ }
| empty_statement
| expression_statement
| selection_statement
@@ -1364,56 +1352,56 @@ embedded_statement
| empty_statement
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_block_new (src));
- vala_block_add_statement (VALA_BLOCK ($$), $1);
+ $$ = vala_block_new (src);
+ vala_block_add_statement ($$, $1);
g_object_unref ($1);
g_object_unref (src);
}
| expression_statement
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_block_new (src));
- vala_block_add_statement (VALA_BLOCK ($$), $1);
+ $$ = vala_block_new (src);
+ vala_block_add_statement ($$, $1);
g_object_unref ($1);
g_object_unref (src);
}
| selection_statement
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_block_new (src));
- vala_block_add_statement (VALA_BLOCK ($$), $1);
+ $$ = vala_block_new (src);
+ vala_block_add_statement ($$, $1);
g_object_unref ($1);
g_object_unref (src);
}
| iteration_statement
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_block_new (src));
- vala_block_add_statement (VALA_BLOCK ($$), $1);
+ $$ = vala_block_new (src);
+ vala_block_add_statement ($$, $1);
g_object_unref ($1);
g_object_unref (src);
}
| jump_statement
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_block_new (src));
- vala_block_add_statement (VALA_BLOCK ($$), $1);
+ $$ = vala_block_new (src);
+ vala_block_add_statement ($$, $1);
g_object_unref ($1);
g_object_unref (src);
}
| try_statement
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_block_new (src));
- vala_block_add_statement (VALA_BLOCK ($$), $1);
+ $$ = vala_block_new (src);
+ vala_block_add_statement ($$, $1);
g_object_unref ($1);
g_object_unref (src);
}
| lock_statement
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_block_new (src));
- vala_block_add_statement (VALA_BLOCK ($$), $1);
+ $$ = vala_block_new (src);
+ vala_block_add_statement ($$, $1);
g_object_unref ($1);
g_object_unref (src);
}
@@ -1423,11 +1411,11 @@ block
: OPEN_BRACE opt_statement_list CLOSE_BRACE
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_block_new (src));
+ $$ = vala_block_new (src);
if ($2 != NULL) {
GList *l;
for (l = $2; l != NULL; l = l->next) {
- vala_block_add_statement (VALA_BLOCK ($$), l->data);
+ vala_block_add_statement ($$, l->data);
g_object_unref (l->data);
}
g_list_free ($2);
@@ -1580,51 +1568,24 @@ selection_statement
if_statement
: comment IF open_parens expression CLOSE_PARENS embedded_statement
{
- ValaBlock *true_block;
ValaSourceReference *src;
- if (VALA_IS_BLOCK ($6)) {
- true_block = VALA_BLOCK ($6);
- } else {
- true_block = vala_block_new (vala_code_node_get_source_reference (VALA_CODE_NODE ($6)));
- vala_block_add_statement (true_block, $6);
- g_object_unref ($6);
- }
-
src = src_com(@4, $1);
- $$ = VALA_STATEMENT (vala_if_statement_new ($4, true_block, NULL, src));
+ $$ = VALA_STATEMENT (vala_if_statement_new ($4, $6, NULL, src));
g_object_unref (src);
g_object_unref ($4);
- g_object_unref (true_block);
+ g_object_unref ($6);
}
| comment IF open_parens expression CLOSE_PARENS embedded_statement ELSE embedded_statement
{
- ValaBlock *true_block;
- ValaBlock *false_block;
ValaSourceReference *src;
- if (VALA_IS_BLOCK ($6)) {
- true_block = VALA_BLOCK ($6);
- } else {
- true_block = vala_block_new (vala_code_node_get_source_reference (VALA_CODE_NODE ($6)));
- vala_block_add_statement (true_block, $6);
- g_object_unref ($6);
- }
-
- if (VALA_IS_BLOCK ($8)) {
- false_block = VALA_BLOCK ($8);
- } else {
- false_block = vala_block_new (vala_code_node_get_source_reference (VALA_CODE_NODE ($8)));
- vala_block_add_statement (false_block, $8);
- g_object_unref ($8);
- }
-
src = src_com(@4, $1);
- $$ = VALA_STATEMENT (vala_if_statement_new ($4, true_block, false_block, src));
+ $$ = VALA_STATEMENT (vala_if_statement_new ($4, $6, $8, src));
g_object_unref (src);
g_object_unref ($4);
- g_object_unref (true_block);
- g_object_unref (false_block);
+ g_object_unref ($6);
+ g_object_unref ($8);
}
;
@@ -1802,7 +1763,7 @@ for_statement
if (init != NULL) {
ValaSourceReference *decl_src = vala_code_node_get_source_reference (VALA_CODE_NODE (decl));
- ValaMemberAccess *lhs = vala_member_access_new (NULL, vala_variable_declarator_get_name (decl), decl_src);
+ ValaMemberAccess *lhs = vala_member_access_new (NULL, vala_symbol_get_name (VALA_SYMBOL (decl)), decl_src);
ValaAssignment *assign = vala_assignment_new (VALA_EXPRESSION (lhs), init, VALA_ASSIGNMENT_OPERATOR_SIMPLE, decl_src);
g_object_unref (lhs);
vala_for_statement_add_initializer (for_statement, VALA_EXPRESSION (assign));
@@ -1919,7 +1880,7 @@ try_statement
{
GList *l;
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_try_statement_new (VALA_BLOCK ($2), VALA_BLOCK ($4), src));
+ $$ = VALA_STATEMENT (vala_try_statement_new ($2, $4, src));
g_object_unref ($2);
if ($4 != NULL) {
g_object_unref ($4);
@@ -1935,7 +1896,7 @@ try_statement
| TRY block finally_clause
{
ValaSourceReference *src = src(@1);
- $$ = VALA_STATEMENT (vala_try_statement_new (VALA_BLOCK ($2), VALA_BLOCK ($3), src));
+ $$ = VALA_STATEMENT (vala_try_statement_new ($2, $3, src));
g_object_unref ($2);
g_object_unref ($3);
g_object_unref (src);
@@ -2027,15 +1988,29 @@ namespace_declaration
: comment opt_attributes NAMESPACE identifier
{
ValaSourceReference *src = src_com(@4, $1);
- current_namespace = vala_namespace_new ($4, src);
+ ValaSymbol *current_symbol = vala_scope_lookup (scope_stack->data, $4);
+ if (current_symbol != NULL) {
+ if (check_is_namespace (current_symbol, src)) {
+ // merge namespace declarations
+ if (!vala_source_file_get_pkg (current_source_file)) {
+ vala_namespace_set_pkg (VALA_NAMESPACE (current_symbol), FALSE);
+ }
+ VALA_CODE_NODE (current_symbol)->attributes = $2;
+ }
+ } else {
+ current_symbol = VALA_SYMBOL (vala_namespace_new ($4, src));
+ vala_namespace_set_pkg (VALA_NAMESPACE (current_symbol), vala_source_file_get_pkg (current_source_file));
+ VALA_CODE_NODE (current_symbol)->attributes = g_list_concat (VALA_CODE_NODE (current_symbol)->attributes, $2);
+ vala_namespace_add_namespace (VALA_NAMESPACE (symbol_stack->data), VALA_NAMESPACE (current_symbol));
+ }
g_object_unref (src);
- VALA_CODE_NODE(current_namespace)->attributes = $2;
g_free ($4);
+
+ push_symbol (current_symbol);
}
namespace_body
{
- $$ = current_namespace;
- current_namespace = vala_code_context_get_global_namespace (vala_source_file_get_context (current_source_file));
+ g_object_unref (pop_symbol ());
}
;
@@ -2093,10 +2068,6 @@ outer_declarations
outer_declaration
: namespace_declaration
- {
- vala_code_context_add_namespace (vala_source_file_get_context (current_source_file), $1);
- g_object_unref ($1);
- }
| namespace_member_declaration
;
@@ -2112,100 +2083,15 @@ namespace_member_declarations
namespace_member_declaration
: class_declaration
- {
- /* skip declarations with errors */
- if ($1 != NULL) {
- vala_namespace_add_class (current_namespace, $1);
- vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
- g_object_unref ($1);
- }
-
- if (current_namespace_implicit) {
- /* current namespace has been declared implicitly */
- current_namespace = vala_code_context_get_global_namespace (vala_source_file_get_context (current_source_file));
- current_namespace_implicit = FALSE;
- }
- }
| struct_declaration
- {
- /* skip declarations with errors */
- if ($1 != NULL) {
- vala_namespace_add_struct (current_namespace, $1);
- vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
- g_object_unref ($1);
- }
-
- if (current_namespace_implicit) {
- /* current namespace has been declared implicitly */
- current_namespace = vala_code_context_get_global_namespace (vala_source_file_get_context (current_source_file));
- current_namespace_implicit = FALSE;
- }
- }
| interface_declaration
- {
- /* skip declarations with errors */
- if ($1 != NULL) {
- vala_namespace_add_interface (current_namespace, $1);
- vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
- g_object_unref ($1);
- }
-
- if (current_namespace_implicit) {
- /* current namespace has been declared implicitly */
- current_namespace = vala_code_context_get_global_namespace (vala_source_file_get_context (current_source_file));
- current_namespace_implicit = FALSE;
- }
- }
| enum_declaration
- {
- /* skip declarations with errors */
- if ($1 != NULL) {
- vala_namespace_add_enum (current_namespace, $1);
- vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
- g_object_unref ($1);
- }
-
- if (current_namespace_implicit) {
- /* current namespace has been declared implicitly */
- current_namespace = vala_code_context_get_global_namespace (vala_source_file_get_context (current_source_file));
- current_namespace_implicit = FALSE;
- }
- }
- | flags_declaration
- {
- /* skip declarations with errors */
- if ($1 != NULL) {
- vala_namespace_add_flags (current_namespace, $1);
- vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
- g_object_unref ($1);
- }
-
- if (current_namespace_implicit) {
- /* current namespace has been declared implicitly */
- current_namespace = vala_code_context_get_global_namespace (vala_source_file_get_context (current_source_file));
- current_namespace_implicit = FALSE;
- }
- }
| callback_declaration
- {
- /* skip declarations with errors */
- if ($1 != NULL) {
- vala_namespace_add_callback (current_namespace, $1);
- vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
- g_object_unref ($1);
- }
-
- if (current_namespace_implicit) {
- /* current namespace has been declared implicitly */
- current_namespace = vala_code_context_get_global_namespace (vala_source_file_get_context (current_source_file));
- current_namespace_implicit = FALSE;
- }
- }
| constant_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_namespace_add_constant (current_namespace, $1);
+ vala_namespace_add_constant (VALA_NAMESPACE (symbol_stack->data), $1);
vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
g_object_unref ($1);
}
@@ -2218,7 +2104,7 @@ namespace_member_declaration
* to explicitly state it */
vala_field_set_instance ($1, FALSE);
- vala_namespace_add_field (current_namespace, $1);
+ vala_namespace_add_field (VALA_NAMESPACE (symbol_stack->data), $1);
vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
g_object_unref ($1);
}
@@ -2231,7 +2117,7 @@ namespace_member_declaration
* to explicitly state it */
vala_method_set_instance ($1, FALSE);
- vala_namespace_add_method (current_namespace, $1);
+ vala_namespace_add_method (VALA_NAMESPACE (symbol_stack->data), $1);
vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($1));
g_object_unref ($1);
}
@@ -2245,54 +2131,84 @@ class_declaration
ValaSourceReference *src;
char *name = $6;
-
+
+ ValaSymbol *parent_symbol = VALA_SYMBOL (g_object_ref (symbol_stack->data));
+ ValaScope *parent_scope = VALA_SCOPE (scope_stack->data);
+
if ($7 != NULL) {
ValaSourceReference *ns_src = src(@6);
- current_namespace = vala_namespace_new ($6, ns_src);
+ parent_symbol = vala_scope_lookup (parent_scope, $6);
+ if (parent_symbol != NULL) {
+ if (check_is_namespace (parent_symbol, src)) {
+ if (!vala_source_file_get_pkg (current_source_file)) {
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), FALSE);
+ }
+ }
+ } else {
+ parent_symbol = VALA_SYMBOL (vala_namespace_new ($6, ns_src));
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), vala_source_file_get_pkg (current_source_file));
+ vala_namespace_add_namespace (VALA_NAMESPACE (symbol_stack->data), VALA_NAMESPACE (parent_symbol));
+ }
+ parent_scope = vala_symbol_get_scope (parent_symbol);
g_free ($6);
g_object_unref (ns_src);
- current_namespace_implicit = TRUE;
-
- vala_code_context_add_namespace (vala_source_file_get_context (current_source_file), current_namespace);
- g_object_unref (current_namespace);
name = $7;
}
-
+
src = src_com(@6, $1);
- current_class = vala_class_new (name, src);
- g_free (name);
- g_object_unref (src);
-
- VALA_CODE_NODE(current_class)->attributes = $2;
- if ($3 != 0) {
- VALA_DATA_TYPE(current_class)->access = $3;
- }
- if (($4 & VALA_MODIFIER_ABSTRACT) == VALA_MODIFIER_ABSTRACT) {
- vala_class_set_is_abstract (current_class, TRUE);
- }
- if (($4 & VALA_MODIFIER_STATIC) == VALA_MODIFIER_STATIC) {
- vala_class_set_is_static (current_class, TRUE);
- }
- if ($8 != NULL) {
- for (l = $8; l != NULL; l = l->next) {
- vala_class_add_type_parameter (current_class, l->data);
- g_object_unref (l->data);
+ ValaSymbol *current_symbol = vala_scope_lookup (parent_scope, name);
+ if (current_symbol != NULL) {
+ if (check_is_class (current_symbol, src)) {
+ // merge class declarations
}
- g_list_free ($8);
- }
- if ($9 != NULL) {
- for (l = $9; l != NULL; l = l->next) {
- vala_class_add_base_type (current_class, l->data);
- g_object_unref (l->data);
+ } else {
+ current_symbol = VALA_SYMBOL (vala_class_new (name, src));
+ g_free (name);
+ g_object_unref (src);
+
+ if (VALA_IS_CLASS (parent_symbol)) {
+ vala_class_add_class (VALA_CLASS (parent_symbol), VALA_CLASS (current_symbol));
+ } else if (VALA_IS_NAMESPACE (parent_symbol)) {
+ vala_namespace_add_class (VALA_NAMESPACE (parent_symbol), VALA_CLASS (current_symbol));
+ vala_source_file_add_node (current_source_file, VALA_CODE_NODE (current_symbol));
+ } else {
+ g_assert_not_reached ();
+ }
+
+ VALA_CODE_NODE (current_symbol)->attributes = $2;
+ if ($3 != 0) {
+ VALA_DATA_TYPE (current_symbol)->access = $3;
+ }
+ if (($4 & VALA_MODIFIER_ABSTRACT) == VALA_MODIFIER_ABSTRACT) {
+ vala_class_set_is_abstract (VALA_CLASS (current_symbol), TRUE);
+ }
+ if (($4 & VALA_MODIFIER_STATIC) == VALA_MODIFIER_STATIC) {
+ vala_class_set_is_static (VALA_CLASS (current_symbol), TRUE);
+ }
+ if ($8 != NULL) {
+ for (l = $8; l != NULL; l = l->next) {
+ vala_class_add_type_parameter (VALA_CLASS (current_symbol), l->data);
+ g_object_unref (l->data);
+ }
+ g_list_free ($8);
+ }
+ if ($9 != NULL) {
+ for (l = $9; l != NULL; l = l->next) {
+ vala_class_add_base_type (VALA_CLASS (current_symbol), l->data);
+ g_object_unref (l->data);
+ }
+ g_list_free ($9);
}
- g_list_free ($9);
}
+
+ g_object_unref (parent_symbol);
+
+ push_symbol (current_symbol);
}
class_body
{
- $$ = current_class;
- current_class = NULL;
+ g_object_unref (pop_symbol ());
}
;
@@ -2404,7 +2320,7 @@ class_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_class_add_constant (current_class, $1);
+ vala_class_add_constant (VALA_CLASS (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -2412,7 +2328,7 @@ class_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_class_add_field (current_class, $1);
+ vala_class_add_field (VALA_CLASS (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -2420,7 +2336,7 @@ class_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_class_add_method (current_class, $1);
+ vala_class_add_method (VALA_CLASS (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -2428,7 +2344,7 @@ class_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_class_add_property (current_class, $1, FALSE);
+ vala_class_add_property (VALA_CLASS (symbol_stack->data), $1, FALSE);
g_object_unref ($1);
}
}
@@ -2436,7 +2352,7 @@ class_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_class_add_signal (current_class, $1);
+ vala_class_add_signal (VALA_CLASS (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -2444,7 +2360,7 @@ class_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_class_set_constructor (current_class, $1);
+ vala_class_set_constructor (VALA_CLASS (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -2452,17 +2368,19 @@ class_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_class_set_destructor (current_class, $1);
+ vala_class_set_destructor (VALA_CLASS (symbol_stack->data), $1);
g_object_unref ($1);
}
}
+ | class_declaration
+ | struct_declaration
;
constant_declaration
: comment opt_attributes opt_access_modifier CONST type variable_declarator SEMICOLON
{
ValaSourceReference *src = src_com(@5, $1);
- $$ = vala_constant_new (vala_variable_declarator_get_name ($6), $5, vala_variable_declarator_get_initializer ($6), src);
+ $$ = vala_constant_new (vala_symbol_get_name (VALA_SYMBOL ($6)), $5, vala_variable_declarator_get_initializer ($6), src);
g_object_unref (src);
g_object_unref ($5);
g_object_unref ($6);
@@ -2486,7 +2404,7 @@ field_declaration
vala_type_reference_set_takes_ownership ($5, TRUE);
}
- $$ = vala_field_new (vala_variable_declarator_get_name ($6), $5, vala_variable_declarator_get_initializer ($6), src);
+ $$ = vala_field_new (vala_symbol_get_name (VALA_SYMBOL ($6)), $5, vala_variable_declarator_get_initializer ($6), src);
g_object_unref (src);
if ($3 != 0) {
$$->access = $3;
@@ -2581,7 +2499,7 @@ method_declaration
: method_header method_body
{
$$ = $1;
- vala_method_set_body ($$, VALA_BLOCK($2));
+ vala_method_set_body ($$, $2);
if ($2 != NULL) {
g_object_unref ($2);
}
@@ -2944,12 +2862,11 @@ destructor_declaration
struct_declaration
: struct_header
{
- current_struct = $1;
+ push_symbol (VALA_SYMBOL ($1));
}
struct_body
{
- $$ = current_struct;
- current_struct = NULL;
+ g_object_unref (pop_symbol ());
}
;
@@ -2961,15 +2878,26 @@ struct_header
char *name = $5;
+ ValaSymbol *parent_symbol = VALA_SYMBOL (g_object_ref (symbol_stack->data));
+ ValaScope *parent_scope = VALA_SCOPE (scope_stack->data);
+
if ($6 != NULL) {
ValaSourceReference *ns_src = src(@5);
- current_namespace = vala_namespace_new ($5, ns_src);
+ parent_symbol = vala_scope_lookup (parent_scope, $5);
+ if (parent_symbol != NULL) {
+ if (check_is_namespace (parent_symbol, src)) {
+ if (!vala_source_file_get_pkg (current_source_file)) {
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), FALSE);
+ }
+ }
+ } else {
+ parent_symbol = VALA_SYMBOL (vala_namespace_new ($5, ns_src));
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), vala_source_file_get_pkg (current_source_file));
+ vala_namespace_add_namespace (VALA_NAMESPACE (symbol_stack->data), VALA_NAMESPACE (parent_symbol));
+ }
+ parent_scope = vala_symbol_get_scope (parent_symbol);
g_free ($5);
g_object_unref (ns_src);
- current_namespace_implicit = TRUE;
-
- vala_code_context_add_namespace (vala_source_file_get_context (current_source_file), current_namespace);
- g_object_unref (current_namespace);
name = $6;
}
@@ -2978,6 +2906,16 @@ struct_header
$$ = vala_struct_new (name, src);
g_free (name);
g_object_unref (src);
+
+ if (VALA_IS_CLASS (parent_symbol)) {
+ vala_class_add_struct (VALA_CLASS (parent_symbol), $$);
+ } else if (VALA_IS_NAMESPACE (parent_symbol)) {
+ vala_namespace_add_struct (VALA_NAMESPACE (parent_symbol), $$);
+ vala_source_file_add_node (current_source_file, VALA_CODE_NODE ($$));
+ } else {
+ g_assert_not_reached ();
+ }
+
for (l = $7; l != NULL; l = l->next) {
vala_struct_add_type_parameter ($$, l->data);
}
@@ -3014,7 +2952,7 @@ struct_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_struct_add_field (current_struct, $1);
+ vala_struct_add_field (VALA_STRUCT (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -3022,7 +2960,7 @@ struct_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_struct_add_method (current_struct, $1);
+ vala_struct_add_method (VALA_STRUCT (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -3034,35 +2972,50 @@ interface_declaration
ValaSourceReference *src;
char *name = $6;
+ ValaSymbol *parent_symbol = VALA_SYMBOL (g_object_ref (symbol_stack->data));
+ ValaScope *parent_scope = VALA_SCOPE (scope_stack->data);
+
if ($7 != NULL) {
ValaSourceReference *ns_src = src(@6);
- current_namespace = vala_namespace_new ($6, ns_src);
+ parent_symbol = vala_scope_lookup (parent_scope, $6);
+ if (parent_symbol != NULL) {
+ if (check_is_namespace (parent_symbol, src)) {
+ if (!vala_source_file_get_pkg (current_source_file)) {
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), FALSE);
+ }
+ }
+ } else {
+ parent_symbol = VALA_SYMBOL (vala_namespace_new ($6, ns_src));
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), vala_source_file_get_pkg (current_source_file));
+ vala_namespace_add_namespace (VALA_NAMESPACE (symbol_stack->data), VALA_NAMESPACE (parent_symbol));
+ }
+ parent_scope = vala_symbol_get_scope (parent_symbol);
g_free ($6);
g_object_unref (ns_src);
- current_namespace_implicit = TRUE;
-
- vala_code_context_add_namespace (vala_source_file_get_context (current_source_file), current_namespace);
- g_object_unref (current_namespace);
name = $7;
}
src = src_com(@6, $1);
- current_interface = vala_interface_new (name, src);
+ ValaInterface *iface = vala_interface_new (name, src);
g_free (name);
g_object_unref (src);
- VALA_CODE_NODE(current_interface)->attributes = $2;
+ vala_namespace_add_interface (VALA_NAMESPACE (parent_symbol), iface);
+ vala_source_file_add_node (current_source_file, VALA_CODE_NODE (iface));
+ g_object_unref (parent_symbol);
+
+ VALA_CODE_NODE (iface)->attributes = $2;
if ($3 != 0) {
- VALA_DATA_TYPE(current_interface)->access = $3;
+ VALA_DATA_TYPE (iface)->access = $3;
}
if (($4 & VALA_MODIFIER_STATIC) == VALA_MODIFIER_STATIC) {
- vala_interface_set_is_static (current_interface, TRUE);
+ vala_interface_set_is_static (iface, TRUE);
}
if ($8 != NULL) {
GList *l;
for (l = $8; l != NULL; l = l->next) {
- vala_interface_add_type_parameter (current_interface, l->data);
+ vala_interface_add_type_parameter (iface, l->data);
g_object_unref (l->data);
}
g_list_free ($8);
@@ -3070,15 +3023,17 @@ interface_declaration
if ($9 != NULL) {
GList *l;
for (l = $9; l != NULL; l = l->next) {
- vala_interface_add_prerequisite (current_interface, l->data);
+ vala_interface_add_prerequisite (iface, l->data);
g_object_unref (l->data);
}
g_list_free ($9);
}
+
+ push_symbol (VALA_SYMBOL (iface));
}
interface_body
{
- $$ = current_interface;
+ g_object_unref (pop_symbol ());
}
;
@@ -3101,7 +3056,7 @@ interface_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_interface_add_method (current_interface, $1);
+ vala_interface_add_method (VALA_INTERFACE (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -3109,7 +3064,7 @@ interface_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_interface_add_property (current_interface, $1);
+ vala_interface_add_property (VALA_INTERFACE (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -3117,7 +3072,7 @@ interface_member_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_interface_add_signal (current_interface, $1);
+ vala_interface_add_signal (VALA_INTERFACE (symbol_stack->data), $1);
g_object_unref ($1);
}
}
@@ -3130,34 +3085,50 @@ enum_declaration
char *name = $5;
+ ValaSymbol *parent_symbol = VALA_SYMBOL (g_object_ref (symbol_stack->data));
+ ValaScope *parent_scope = VALA_SCOPE (scope_stack->data);
+
if ($6 != NULL) {
ValaSourceReference *ns_src = src(@5);
- current_namespace = vala_namespace_new ($5, ns_src);
+ parent_symbol = vala_scope_lookup (parent_scope, $5);
+ if (parent_symbol != NULL) {
+ if (check_is_namespace (parent_symbol, src)) {
+ if (!vala_source_file_get_pkg (current_source_file)) {
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), FALSE);
+ }
+ }
+ } else {
+ parent_symbol = VALA_SYMBOL (vala_namespace_new ($5, ns_src));
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), vala_source_file_get_pkg (current_source_file));
+ vala_namespace_add_namespace (VALA_NAMESPACE (symbol_stack->data), VALA_NAMESPACE (parent_symbol));
+ }
+ parent_scope = vala_symbol_get_scope (parent_symbol);
g_free ($5);
g_object_unref (ns_src);
- current_namespace_implicit = TRUE;
-
- vala_code_context_add_namespace (vala_source_file_get_context (current_source_file), current_namespace);
- g_object_unref (current_namespace);
name = $6;
}
src = src_com(@5, $1);
- current_enum = vala_enum_new (name, src);
+ ValaEnum *en = vala_enum_new (name, src);
g_free (name);
g_object_unref (src);
- VALA_CODE_NODE(current_enum)->attributes = $2;
+ vala_namespace_add_enum (VALA_NAMESPACE (parent_symbol), en);
+ vala_source_file_add_node (current_source_file, VALA_CODE_NODE (en));
+ g_object_unref (parent_symbol);
+
+ VALA_CODE_NODE (en)->attributes = $2;
if ($3 != 0) {
- VALA_DATA_TYPE(current_enum)->access = $3;
+ VALA_DATA_TYPE (en)->access = $3;
}
+
+ push_symbol (VALA_SYMBOL (en));
}
enum_body
{
- $$ = current_enum;
- current_enum = NULL;
+ g_object_unref (pop_symbol ());
}
;
@@ -3180,7 +3151,7 @@ enum_member_declaration
{
ValaEnumValue *ev = vala_enum_value_new ($2);
g_free ($2);
- vala_enum_add_value (current_enum, ev);
+ vala_enum_add_value (VALA_ENUM (symbol_stack->data), ev);
g_object_unref (ev);
}
| opt_attributes identifier ASSIGN expression
@@ -3188,7 +3159,7 @@ enum_member_declaration
ValaEnumValue *ev = vala_enum_value_new_with_value ($2, $4);
g_free ($2);
g_object_unref ($4);
- vala_enum_add_value (current_enum, ev);
+ vala_enum_add_value (VALA_ENUM (symbol_stack->data), ev);
g_object_unref (ev);
}
;
@@ -3208,90 +3179,12 @@ enum_method_declaration
{
/* skip declarations with errors */
if ($1 != NULL) {
- vala_enum_add_method (current_enum, $1);
+ vala_enum_add_method (VALA_ENUM (symbol_stack->data), $1);
g_object_unref ($1);
}
}
;
-flags_declaration
- : comment opt_attributes opt_access_modifier FLAGS identifier opt_name_specifier flags_body
- {
- GList *l;
- ValaSourceReference *src;
-
- char *name = $5;
-
- if ($6 != NULL) {
- ValaSourceReference *ns_src = src(@5);
- current_namespace = vala_namespace_new ($5, ns_src);
- g_free ($5);
- g_object_unref (ns_src);
- current_namespace_implicit = TRUE;
-
- vala_code_context_add_namespace (vala_source_file_get_context (current_source_file), current_namespace);
- g_object_unref (current_namespace);
-
- name = $6;
- }
-
- src = src_com(@5, $1);
- $$ = vala_flags_new (name, src);
- g_free (name);
- g_object_unref (src);
-
- VALA_CODE_NODE($$)->attributes = $2;
-
- if ($3 != 0) {
- VALA_DATA_TYPE($$)->access = $3;
- }
- for (l = $7; l != NULL; l = l->next) {
- vala_flags_add_value ($$, l->data);
- g_object_unref (l->data);
- }
- }
- ;
-
-flags_body
- : OPEN_BRACE opt_flags_member_declarations CLOSE_BRACE
- {
- $$ = $2;
- }
- ;
-
-opt_flags_member_declarations
- : /* empty */
- {
- $$ = NULL;
- }
- | flags_member_declarations opt_comma
- ;
-
-flags_member_declarations
- : flags_member_declaration
- {
- $$ = g_list_append (NULL, $1);
- }
- | flags_member_declarations COMMA flags_member_declaration
- {
- $$ = g_list_append ($1, $3);
- }
- ;
-
-flags_member_declaration
- : opt_attributes identifier
- {
- $$ = vala_flags_value_new ($2);
- g_free ($2);
- }
- | opt_attributes identifier ASSIGN expression
- {
- $$ = vala_flags_value_new_with_value ($2, $4);
- g_free ($2);
- g_object_unref ($4);
- }
- ;
-
callback_declaration
: comment opt_attributes opt_access_modifier opt_modifiers DELEGATE type identifier opt_name_specifier opt_type_parameter_list OPEN_PARENS opt_formal_parameter_list CLOSE_PARENS opt_throws_declaration SEMICOLON
{
@@ -3299,43 +3192,61 @@ callback_declaration
GList *l;
char *name = $7;
+ ValaSymbol *parent_symbol = VALA_SYMBOL (g_object_ref (symbol_stack->data));
+ ValaScope *parent_scope = VALA_SCOPE (scope_stack->data);
+
if ($8 != NULL) {
ValaSourceReference *ns_src = src(@7);
- current_namespace = vala_namespace_new ($7, ns_src);
+ parent_symbol = vala_scope_lookup (parent_scope, $7);
+ if (parent_symbol != NULL) {
+ if (check_is_namespace (parent_symbol, src)) {
+ if (!vala_source_file_get_pkg (current_source_file)) {
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), FALSE);
+ }
+ }
+ } else {
+ parent_symbol = VALA_SYMBOL (vala_namespace_new ($7, ns_src));
+ vala_namespace_set_pkg (VALA_NAMESPACE (parent_symbol), vala_source_file_get_pkg (current_source_file));
+ vala_namespace_add_namespace (VALA_NAMESPACE (symbol_stack->data), VALA_NAMESPACE (parent_symbol));
+ }
+ parent_scope = vala_symbol_get_scope (parent_symbol);
g_free ($7);
g_object_unref (ns_src);
- current_namespace_implicit = TRUE;
-
- vala_code_context_add_namespace (vala_source_file_get_context (current_source_file), current_namespace);
- g_object_unref (current_namespace);
name = $8;
}
src = src_com(@7, $1);
- $$ = vala_callback_new (name, $6, src);
+ ValaCallback *cb = vala_callback_new (name, $6, src);
g_free (name);
g_object_unref ($6);
g_object_unref (src);
+
+ vala_namespace_add_callback (VALA_NAMESPACE (parent_symbol), cb);
+ vala_source_file_add_node (current_source_file, VALA_CODE_NODE (cb));
+ g_object_unref (parent_symbol);
+
if ($3 != 0) {
- VALA_DATA_TYPE($$)->access = $3;
+ VALA_DATA_TYPE (cb)->access = $3;
}
- VALA_CODE_NODE($$)->attributes = $2;
+ VALA_CODE_NODE (cb)->attributes = $2;
if ($9 != NULL) {
for (l = $9; l != NULL; l = l->next) {
- vala_callback_add_type_parameter ($$, l->data);
+ vala_callback_add_type_parameter (cb, l->data);
g_object_unref (l->data);
}
g_list_free ($9);
}
if ($11 != NULL) {
for (l = $11; l != NULL; l = l->next) {
- vala_callback_add_parameter ($$, l->data);
+ vala_callback_add_parameter (cb, l->data);
g_object_unref (l->data);
}
g_list_free ($11);
}
+
+ g_object_unref (cb);
}
;
@@ -3573,7 +3484,7 @@ void
vala_parser_parse_file (ValaParser *parser, ValaSourceFile *source_file)
{
current_source_file = source_file;
- current_namespace = vala_code_context_get_global_namespace (vala_source_file_get_context (current_source_file));
+ push_symbol (VALA_SYMBOL (vala_code_context_get_root (vala_source_file_get_context (source_file))));
yyin = fopen (vala_source_file_get_filename (current_source_file), "r");
if (yyin == NULL) {
printf ("Couldn't open source file: %s.\n", vala_source_file_get_filename (current_source_file));
@@ -3587,3 +3498,40 @@ vala_parser_parse_file (ValaParser *parser, ValaSourceFile *source_file)
fclose (yyin);
yyin = NULL;
}
+
+static void push_symbol (ValaSymbol *symbol) {
+ symbol_stack = g_list_prepend (symbol_stack, symbol);
+ scope_stack = g_list_prepend (scope_stack, vala_symbol_get_scope (symbol));
+}
+
+static ValaSymbol *pop_symbol (void) {
+ ValaSymbol *sym = VALA_SYMBOL (symbol_stack->data);
+ symbol_stack = g_list_delete_link (symbol_stack, symbol_stack);
+ scope_stack = g_list_delete_link (scope_stack, scope_stack);
+ return sym;
+}
+
+static gboolean check_is_namespace (ValaSymbol *symbol, ValaSourceReference *src) {
+ if (!VALA_IS_NAMESPACE (symbol)) {
+ char *sym_name = vala_symbol_get_full_name (symbol);
+ char *error_msg = g_strdup_printf ("`%s` already exists but is not a namespace", sym_name);
+ g_free (sym_name);
+ vala_report_error (src, error_msg);
+ g_free (error_msg);
+ return FALSE;
+ }
+ return TRUE;
+}
+
+static gboolean check_is_class (ValaSymbol *symbol, ValaSourceReference *src) {
+ if (!VALA_IS_CLASS (symbol)) {
+ char *sym_name = vala_symbol_get_full_name (symbol);
+ char *error_msg = g_strdup_printf ("`%s` already exists but is not a class", sym_name);
+ g_free (sym_name);
+ vala_report_error (src, error_msg);
+ g_free (error_msg);
+ return FALSE;
+ }
+ return TRUE;
+}
+
diff --git a/vala/scanner.l b/vala/scanner.l
index a7c608c97..a85de62b0 100644
--- a/vala/scanner.l
+++ b/vala/scanner.l
@@ -143,7 +143,6 @@ literal ({integer_literal}|{real_literal}|{character_literal}|{string_literal
"enum" { uploc; return ENUM; }
"false" { uploc; return VALA_FALSE; }
"finally" { uploc; return FINALLY; }
-"flags" { uploc; return FLAGS; }
"for" { uploc; return FOR; }
"foreach" { uploc; return FOREACH; }
"get" { uploc; return GET; }
diff --git a/vala/vala.h b/vala/vala.h
index ab5830e0f..bc016b899 100644
--- a/vala/vala.h
+++ b/vala/vala.h
@@ -28,8 +28,6 @@
#include <vala/valaexpression.h>
#include <vala/valaexpressionstatement.h>
#include <vala/valafield.h>
-#include <vala/valaflags.h>
-#include <vala/valaflagsvalue.h>
#include <vala/valaforeachstatement.h>
#include <vala/valaformalparameter.h>
#include <vala/valaforstatement.h>
@@ -60,6 +58,7 @@
#include <vala/valareferencetransferexpression.h>
#include <vala/valareport.h>
#include <vala/valareturnstatement.h>
+#include <vala/valascope.h>
#include <vala/valasignal.h>
#include <vala/valasizeofexpression.h>
#include <vala/valasourcefile.h>
diff --git a/vala/valaarray.vala b/vala/valaarray.vala
index 100e7a6b5..5cf51ed97 100644
--- a/vala/valaarray.vala
+++ b/vala/valaarray.vala
@@ -90,10 +90,8 @@ public class Vala.Array : DataType {
name = "%s]".printf (name);
length_field = new ArrayLengthField (source_reference);
- length_field.symbol = new Symbol (length_field);
resize_method = new ArrayResizeMethod (source_reference);
- resize_method.symbol = new Symbol (resize_method);
}
/**
diff --git a/vala/valaarraylengthfield.vala b/vala/valaarraylengthfield.vala
index 8cbf17139..9dc6ee278 100644
--- a/vala/valaarraylengthfield.vala
+++ b/vala/valaarraylengthfield.vala
@@ -30,7 +30,7 @@ public class Vala.ArrayLengthField : Field {
access = MemberAccessibility.PUBLIC;
var root_symbol = source_reference.file.context.root;
- type_reference.data_type = (DataType) root_symbol.lookup ("int").node;
+ type_reference.data_type = (DataType) root_symbol.scope.lookup ("int");
}
/**
diff --git a/vala/valaarrayresizemethod.vala b/vala/valaarrayresizemethod.vala
index e8b1eac1a..7a1b0c627 100644
--- a/vala/valaarrayresizemethod.vala
+++ b/vala/valaarrayresizemethod.vala
@@ -33,7 +33,7 @@ public class Vala.ArrayResizeMethod : Method {
var root_symbol = source_reference.file.context.root;
var int_type = new TypeReference ();
- int_type.data_type = (DataType) root_symbol.lookup ("int").node;
+ int_type.data_type = (DataType) root_symbol.scope.lookup ("int");
add_parameter (new FormalParameter ("length", int_type));
diff --git a/vala/valaattributeprocessor.vala b/vala/valaattributeprocessor.vala
index e78b5e321..525ff2855 100644
--- a/vala/valaattributeprocessor.vala
+++ b/vala/valaattributeprocessor.vala
@@ -42,6 +42,10 @@ public class Vala.AttributeProcessor : CodeVisitor {
public override void visit_namespace (Namespace! ns) {
ns.process_attributes ();
+
+ foreach (Namespace ns in ns.get_namespaces ()) {
+ ns.accept (this);
+ }
}
public override void visit_class (Class! cl) {
@@ -66,10 +70,6 @@ public class Vala.AttributeProcessor : CodeVisitor {
en.process_attributes ();
}
- public override void visit_flags (Flags! fl) {
- fl.process_attributes ();
- }
-
public override void visit_method (Method! m) {
m.process_attributes ();
}
diff --git a/vala/valablock.vala b/vala/valablock.vala
index 3f73c4b60..94830a608 100644
--- a/vala/valablock.vala
+++ b/vala/valablock.vala
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a source code block.
*/
-public class Vala.Block : Statement {
+public class Vala.Block : Symbol, Statement {
/**
* Specifies whether this block contains a jump statement. This
* information can be used to remove unreachable block cleanup code.
@@ -40,8 +40,7 @@ public class Vala.Block : Statement {
*
* @param source reference to source code
*/
- public Block (SourceReference source = null) {
- source_reference = source;
+ public Block (construct SourceReference source_reference = null) {
}
/**
diff --git a/vala/valabreakstatement.vala b/vala/valabreakstatement.vala
index 25f91b837..3180fd5a4 100644
--- a/vala/valabreakstatement.vala
+++ b/vala/valabreakstatement.vala
@@ -1,6 +1,6 @@
/* valabreakstatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a break statement in the source code.
*/
-public class Vala.BreakStatement : Statement {
+public class Vala.BreakStatement : CodeNode, Statement {
/**
* Creates a new break statement.
*
diff --git a/vala/valacallback.vala b/vala/valacallback.vala
index c1ad58874..a959fb198 100644
--- a/vala/valacallback.vala
+++ b/vala/valacallback.vala
@@ -51,10 +51,7 @@ public class Vala.Callback : DataType {
* @param source reference to source code
* @return newly created callback
*/
- public Callback (string _name, TypeReference _return_type, SourceReference source = null) {
- name = _name;
- return_type = _return_type;
- source_reference = source;
+ public Callback (construct string name, construct TypeReference return_type, construct SourceReference source_reference = null) {
}
/**
@@ -65,6 +62,7 @@ public class Vala.Callback : DataType {
public void add_type_parameter (TypeParameter! p) {
type_parameters.append (p);
p.type = this;
+ scope.add (p.name, p);
}
/**
@@ -74,6 +72,7 @@ public class Vala.Callback : DataType {
*/
public void add_parameter (FormalParameter! param) {
parameters.append (param);
+ scope.add (param.name, param);
}
/**
@@ -149,7 +148,7 @@ public class Vala.Callback : DataType {
public override string get_cname (bool const_type = false) {
if (cname == null) {
- cname = "%s%s".printf (@namespace.get_cprefix (), name);
+ cname = "%s%s".printf (parent_symbol.get_cprefix (), name);
}
return cname;
}
diff --git a/vala/valaclass.vala b/vala/valaclass.vala
index 66389cb9f..2786aba86 100644
--- a/vala/valaclass.vala
+++ b/vala/valaclass.vala
@@ -67,6 +67,10 @@ public class Vala.Class : DataType {
private List<Method> methods;
private List<Property> properties;
private List<Signal> signals;
+
+ // inner types
+ private List<Class> classes;
+ private List<Struct> structs;
/**
* Specifies the default construction method.
@@ -122,6 +126,7 @@ public class Vala.Class : DataType {
public void add_type_parameter (TypeParameter! p) {
type_parameters.append (p);
p.type = this;
+ scope.add (p.name, p);
}
/**
@@ -140,6 +145,7 @@ public class Vala.Class : DataType {
*/
public void add_constant (Constant! c) {
constants.append (c);
+ scope.add (c.name, c);
}
/**
@@ -154,6 +160,7 @@ public class Vala.Class : DataType {
if (f.access == MemberAccessibility.PRIVATE && f.instance) {
_has_private_fields = true;
}
+ scope.add (f.name, f);
}
/**
@@ -171,7 +178,17 @@ public class Vala.Class : DataType {
* @param m a method
*/
public void add_method (Method! m) {
+ if (m.instance) {
+ m.this_parameter = new FormalParameter ("this", new TypeReference ());
+ m.this_parameter.type_reference.data_type = this;
+ m.scope.add (m.this_parameter.name, m.this_parameter);
+ }
+ if (m is CreationMethod && m.name == null) {
+ default_construction_method = m;
+ }
+
methods.append (m);
+ scope.add (m.name, m);
}
/**
@@ -190,6 +207,11 @@ public class Vala.Class : DataType {
*/
public void add_property (Property! prop, bool no_field = false) {
properties.append (prop);
+ scope.add (prop.name, prop);
+
+ prop.this_parameter = new FormalParameter ("this", new TypeReference ());
+ prop.this_parameter.type_reference.data_type = this;
+ prop.scope.add (prop.this_parameter.name, prop.this_parameter);
if (!no_field && prop.set_accessor != null && prop.set_accessor.body == null &&
source_reference != null && !source_reference.file.pkg) {
@@ -219,6 +241,7 @@ public class Vala.Class : DataType {
*/
public void add_signal (Signal! sig) {
signals.append (sig);
+ scope.add (sig.name, sig);
}
/**
@@ -230,6 +253,26 @@ public class Vala.Class : DataType {
return signals.copy ();
}
+ /**
+ * Adds the specified class as an inner class.
+ *
+ * @param cl a class
+ */
+ public void add_class (Class! cl) {
+ classes.append (cl);
+ scope.add (cl.name, cl);
+ }
+
+ /**
+ * Adds the specified struct as an inner struct.
+ *
+ * @param st a struct
+ */
+ public void add_struct (Struct! st) {
+ structs.append (st);
+ scope.add (st.name, st);
+ }
+
public override void accept (CodeVisitor! visitor) {
visitor.visit_class (this);
}
@@ -270,11 +313,23 @@ public class Vala.Class : DataType {
if (destructor != null) {
destructor.accept (visitor);
}
+
+ foreach (Class cl in classes) {
+ cl.accept (visitor);
+ }
+
+ foreach (Struct st in structs) {
+ st.accept (visitor);
+ }
+ }
+
+ public override string! get_cprefix () {
+ return get_cname ();
}
public override string get_cname (bool const_type = false) {
if (cname == null) {
- cname = "%s%s".printf (@namespace.get_cprefix (), name);
+ cname = "%s%s".printf (parent_symbol.get_cprefix (), name);
}
return cname;
}
@@ -290,7 +345,7 @@ public class Vala.Class : DataType {
private string get_lower_case_csuffix () {
if (lower_case_csuffix == null) {
- lower_case_csuffix = Namespace.camel_case_to_lower_case (name);
+ lower_case_csuffix = camel_case_to_lower_case (name);
}
return lower_case_csuffix;
}
@@ -299,10 +354,10 @@ public class Vala.Class : DataType {
if (infix == null) {
infix = "";
}
- return "%s%s%s".printf (@namespace.get_lower_case_cprefix (), infix, get_lower_case_csuffix ());
+ return "%s%s%s".printf (parent_symbol.get_lower_case_cprefix (), infix, get_lower_case_csuffix ());
}
- public override string get_lower_case_cprefix () {
+ public override string! get_lower_case_cprefix () {
return "%s_".printf (get_lower_case_cname (null));
}
diff --git a/vala/valacodecontext.vala b/vala/valacodecontext.vala
index 118fb67d8..4ae5d3f26 100644
--- a/vala/valacodecontext.vala
+++ b/vala/valacodecontext.vala
@@ -85,49 +85,19 @@ public class Vala.CodeContext {
public Method module_init_method { get; set; }
List<SourceFile> source_files;
- private Symbol! _root = new Symbol ();
-
- private Namespace global_namespace = new Namespace (null);
- private List<Namespace> namespaces;
+ private Namespace! _root = new Namespace (null);
List<SourceFileCycle> cycles;
private List<string> packages;
/**
- * The root symbol of the code tree.
- *
- * @return root symbol
- */
- public Symbol! root {
- get { return _root; }
- }
-
- /**
- * Adds the specified namespace.
- *
- * @param ns a namespace
- */
- public void add_namespace (Namespace! ns) {
- namespaces.append (ns);
- }
-
- /**
- * Returns the implicitly declared root namespace.
+ * The root namespace of the symbol tree.
*
* @return root namespace
*/
- public Namespace! get_global_namespace () {
- return global_namespace;
- }
-
- /**
- * Returns a copy of the list of namespaces.
- *
- * @return namespace list
- */
- public List<weak Namespace> get_namespaces () {
- return namespaces.copy ();
+ public Namespace! root {
+ get { return _root; }
}
/**
@@ -182,11 +152,7 @@ public class Vala.CodeContext {
* @param visitor the visitor to be called when traversing
*/
public void accept (CodeVisitor! visitor) {
- global_namespace.accept (visitor);
-
- foreach (Namespace ns in namespaces) {
- ns.accept (visitor);
- }
+ root.accept (visitor);
foreach (SourceFile file in source_files) {
file.accept (visitor);
diff --git a/vala/valacodenode.vala b/vala/valacodenode.vala
index 696ad1453..5fc2bcb19 100644
--- a/vala/valacodenode.vala
+++ b/vala/valacodenode.vala
@@ -33,12 +33,7 @@ public abstract class Vala.CodeNode {
* Parent of this code node.
*/
public CodeNode parent_node { get; set; }
-
- /**
- * Symbol that corresponds to this code node.
- */
- public Symbol symbol { get; set; }
-
+
/**
* References the location in the source file where this code node has
* been written.
diff --git a/vala/valacodevisitor.vala b/vala/valacodevisitor.vala
index b4b702e44..9a92c4d45 100644
--- a/vala/valacodevisitor.vala
+++ b/vala/valacodevisitor.vala
@@ -84,22 +84,6 @@ public abstract class Vala.CodeVisitor {
}
/**
- * Visit operation called for flags.
- *
- * @param fl a flags
- */
- public virtual void visit_flags (Flags! fl) {
- }
-
- /**
- * Visit operation called for flags values.
- *
- * @param fv an flags value
- */
- public virtual void visit_flags_value (FlagsValue! fv) {
- }
-
- /**
* Visit operation called for callbacks.
*
* @param cb a callback
diff --git a/vala/valaconstant.vala b/vala/valaconstant.vala
index 13ebe0fff..16b30ca7b 100644
--- a/vala/valaconstant.vala
+++ b/vala/valaconstant.vala
@@ -27,11 +27,6 @@ using GLib;
*/
public class Vala.Constant : Member, Lockable {
/**
- * The symbol name of this constant.
- */
- public string! name { get; set construct; }
-
- /**
* The data type of this constant.
*/
public TypeReference! type_reference { get; set construct; }
@@ -90,17 +85,11 @@ public class Vala.Constant : Member, Lockable {
*/
public string! get_cname () {
if (cname == null) {
- if (symbol.parent_symbol.node is DataType) {
- var t = (DataType) symbol.parent_symbol.node;
- cname = "%s%s".printf (t.get_lower_case_cprefix ().up (), name);
+ if (parent_symbol == null) {
+ // global constant
+ cname = name;
} else {
- var ns = (Namespace) symbol.parent_symbol.node;
- if (ns == null) {
- // global constant
- cname = name;
- } else {
- cname = "%s%s".printf (ns.get_lower_case_cprefix ().up (), name);
- }
+ cname = "%s%s".printf (parent_symbol.get_lower_case_cprefix ().up (), name);
}
}
return cname;
diff --git a/vala/valaconstructor.vala b/vala/valaconstructor.vala
index 28b72e96f..0aea35128 100644
--- a/vala/valaconstructor.vala
+++ b/vala/valaconstructor.vala
@@ -25,11 +25,16 @@ using GLib;
/**
* Represents a class or instance constructor.
*/
-public class Vala.Constructor : CodeNode {
+public class Vala.Constructor : Symbol {
/**
* The body of this constructor.
*/
- public Statement body { get; set; }
+ public Block body { get; set; }
+
+ /**
+ * Specifies the generated `this' parameter for instance methods.
+ */
+ public FormalParameter this_parameter { get; set; }
private bool _instance = true;
diff --git a/vala/valacontinuestatement.vala b/vala/valacontinuestatement.vala
index da0f0d502..509f4e6d9 100644
--- a/vala/valacontinuestatement.vala
+++ b/vala/valacontinuestatement.vala
@@ -1,6 +1,6 @@
/* valacontinuestatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a continue statement in the source code.
*/
-public class Vala.ContinueStatement : Statement {
+public class Vala.ContinueStatement : CodeNode, Statement {
/**
* Creates a new continue statement.
*
diff --git a/vala/valacreationmethod.vala b/vala/valacreationmethod.vala
index 85e1075c3..dd86699a3 100644
--- a/vala/valacreationmethod.vala
+++ b/vala/valacreationmethod.vala
@@ -56,7 +56,7 @@ public class Vala.CreationMethod : Method {
}
public override string! get_default_cname () {
- var parent = symbol.parent_symbol.node;
+ var parent = parent_symbol;
assert (parent is DataType);
if (name == null) {
return "%snew".printf (((DataType) parent).get_lower_case_cprefix ());
diff --git a/vala/valadatatype.vala b/vala/valadatatype.vala
index cd55bceea..85299666a 100644
--- a/vala/valadatatype.vala
+++ b/vala/valadatatype.vala
@@ -27,12 +27,7 @@ using GLib;
* Represents a runtime data type. This data type may be defined in Vala source
* code or imported from an external library with a Vala API file.
*/
-public abstract class Vala.DataType : CodeNode {
- /**
- * The symbol name of this data type.
- */
- public string name { get; set; }
-
+public abstract class Vala.DataType : Symbol {
/**
* Specifies the accessibility of the class. Public accessibility
* doesn't limit access. Default accessibility limits access to this
@@ -41,11 +36,6 @@ public abstract class Vala.DataType : CodeNode {
*/
public MemberAccessibility access;
- /**
- * The namespace containing this data type.
- */
- public weak Namespace @namespace;
-
private List<string> cheader_filenames;
private Pointer pointer_type;
@@ -178,29 +168,6 @@ public abstract class Vala.DataType : CodeNode {
public virtual string get_upper_case_cname (string infix = null) {
return null;
}
-
- /**
- * Returns the C name of this data type in lower case. Words are
- * separated by underscores. The lower case C name of the namespace is
- * prefix of the result.
- *
- * @param infix a string to be placed between namespace and data type
- * name or null
- * @return the lower case name to be used in C code
- */
- public virtual string get_lower_case_cname (string infix = null) {
- return null;
- }
-
- /**
- * Returns the string to be prefixed to members of this data type in
- * lower case when used in C code.
- *
- * @return the lower case prefix to be used in C code
- */
- public virtual string get_lower_case_cprefix () {
- return null;
- }
/**
* Returns the default value for the given type. Returning null means
@@ -221,7 +188,7 @@ public abstract class Vala.DataType : CodeNode {
public virtual List<weak string> get_cheader_filenames () {
if (cheader_filenames == null) {
/* default to header filenames of the namespace */
- foreach (string filename in @namespace.get_cheader_filenames ()) {
+ foreach (string filename in parent_symbol.get_cheader_filenames ()) {
add_cheader_filename (filename);
}
@@ -252,11 +219,10 @@ public abstract class Vala.DataType : CodeNode {
if (pointer_type == null) {
pointer_type = new Pointer (this, source_reference);
/* create a new Symbol */
- pointer_type.symbol = new Symbol (pointer_type);
- this.symbol.parent_symbol.add (pointer_type.name, pointer_type.symbol);
+ parent_symbol.scope.add (pointer_type.name, pointer_type);
/* link the namespace */
- pointer_type.@namespace = this.@namespace;
+ pointer_type.owner = parent_symbol.scope;
}
return pointer_type;
@@ -273,19 +239,15 @@ public abstract class Vala.DataType : CodeNode {
if (array_type == null) {
var new_array_type = new Array (this, rank, source_reference);
- /* create a new Symbol */
- new_array_type.symbol = new Symbol (new_array_type);
- this.symbol.parent_symbol.add (new_array_type.name, new_array_type.symbol);
+ parent_symbol.scope.add (new_array_type.name, new_array_type);
/* add internal length field */
- new_array_type.symbol.add (new_array_type.get_length_field ().name, new_array_type.get_length_field ().symbol);
+ new_array_type.scope.add (new_array_type.get_length_field ().name, new_array_type.get_length_field ());
/* add internal resize method */
- new_array_type.symbol.add (new_array_type.get_resize_method ().name, new_array_type.get_resize_method ().symbol);
+ new_array_type.scope.add (new_array_type.get_resize_method ().name, new_array_type.get_resize_method ());
/* link the array type to the same source as the container type */
new_array_type.source_reference = this.source_reference;
- /* link the namespace */
- new_array_type.@namespace = this.@namespace;
array_types.insert (rank.to_string (), new_array_type);
diff --git a/vala/valadeclarationstatement.vala b/vala/valadeclarationstatement.vala
index 44b5172d6..f045b9eb8 100644
--- a/vala/valadeclarationstatement.vala
+++ b/vala/valadeclarationstatement.vala
@@ -1,6 +1,6 @@
/* valadeclarationstatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a local variable declaration statement in the source code.
*/
-public class Vala.DeclarationStatement : Statement {
+public class Vala.DeclarationStatement : CodeNode, Statement {
/**
* The local variable declaration.
*/
diff --git a/vala/valadestructor.vala b/vala/valadestructor.vala
index a169e1b79..85ea47a40 100644
--- a/vala/valadestructor.vala
+++ b/vala/valadestructor.vala
@@ -25,11 +25,11 @@ using GLib;
/**
* Represents a class or instance destructor.
*/
-public class Vala.Destructor : CodeNode {
+public class Vala.Destructor : Symbol {
/**
* The body of this constructor.
*/
- public Statement body { get; set; }
+ public Block body { get; set; }
private bool _instance = true;
@@ -37,22 +37,17 @@ public class Vala.Destructor : CodeNode {
* Specifies whether this is an instance or a class destructor.
*/
public bool instance {
- get {
- return _instance;
- }
- set {
- _instance = value;
- }
+ get { return _instance; }
+ set { _instance = value; }
}
/**
* Creates a new destructor.
*
- * @param source reference to source code
- * @return newly created destructor
+ * @param source_reference reference to source code
+ * @return newly created destructor
*/
- public Destructor (SourceReference source) {
- source_reference = source;
+ public Destructor (construct SourceReference source_reference = null) {
}
public override void accept (CodeVisitor! visitor) {
diff --git a/vala/valadostatement.vala b/vala/valadostatement.vala
index 92ea9e99b..f54a9167e 100644
--- a/vala/valadostatement.vala
+++ b/vala/valadostatement.vala
@@ -1,6 +1,6 @@
/* valadostatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,11 +25,11 @@ using GLib;
/**
* Represents a do iteration statement in the source code.
*/
-public class Vala.DoStatement : Statement {
+public class Vala.DoStatement : CodeNode, Statement {
/**
* Specifies the loop body.
*/
- public Statement body { get; set; }
+ public Block body { get; set; }
/**
* Specifies the loop condition.
@@ -54,10 +54,7 @@ public class Vala.DoStatement : Statement {
* @param source reference to source code
* @return newly created do statement
*/
- public DoStatement (Statement! _body, Expression! cond, SourceReference source) {
- body = _body;
- condition = cond;
- source_reference = source;
+ public DoStatement (construct Block! body, construct Expression! condition, construct SourceReference source_reference = null) {
}
public override void accept (CodeVisitor! visitor) {
diff --git a/vala/valaemptystatement.vala b/vala/valaemptystatement.vala
index 9dd75fe1b..6ca047db8 100644
--- a/vala/valaemptystatement.vala
+++ b/vala/valaemptystatement.vala
@@ -1,6 +1,6 @@
/* valaemptystatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,7 +25,7 @@ using GLib;
/**
* An empty statement.
*/
-public class Vala.EmptyStatement : Statement {
+public class Vala.EmptyStatement : CodeNode, Statement {
/**
* Creates a new empty statement.
*
diff --git a/vala/valaenum.vala b/vala/valaenum.vala
index 2f9e4f01b..fd7c520f2 100644
--- a/vala/valaenum.vala
+++ b/vala/valaenum.vala
@@ -55,6 +55,7 @@ public class Vala.Enum : DataType {
*/
public void add_value (EnumValue! value) {
values.append (value);
+ scope.add (value.name, value);
}
/**
@@ -63,7 +64,20 @@ public class Vala.Enum : DataType {
* @param m a method
*/
public void add_method (Method! m) {
+ if (m is CreationMethod) {
+ Report.error (m.source_reference, "construction methods may only be declared within classes and structs");
+
+ m.error = true;
+ return;
+ }
+ if (m.instance) {
+ m.this_parameter = new FormalParameter ("this", new TypeReference ());
+ m.this_parameter.type_reference.data_type = this;
+ m.scope.add (m.this_parameter.name, m.this_parameter);
+ }
+
methods.append (m);
+ scope.add (m.name, m);
}
/**
@@ -91,12 +105,12 @@ public class Vala.Enum : DataType {
public override string get_cname (bool const_type = false) {
if (cname == null) {
- cname = "%s%s".printf (@namespace.get_cprefix (), name);
+ cname = "%s%s".printf (parent_symbol.get_cprefix (), name);
}
return cname;
}
- public override string get_lower_case_cprefix () {
+ public override string! get_lower_case_cprefix () {
if (lower_case_cprefix == null) {
lower_case_cprefix = "%s_".printf (get_lower_case_cname (null));
}
@@ -105,7 +119,7 @@ public class Vala.Enum : DataType {
private string get_lower_case_csuffix () {
if (lower_case_csuffix == null) {
- lower_case_csuffix = Namespace.camel_case_to_lower_case (name);
+ lower_case_csuffix = camel_case_to_lower_case (name);
}
return lower_case_csuffix;
}
@@ -114,11 +128,11 @@ public class Vala.Enum : DataType {
if (infix == null) {
infix = "";
}
- return "%s%s%s".printf (@namespace.get_lower_case_cprefix (), infix, get_lower_case_csuffix ());
+ return "%s%s%s".printf (parent_symbol.get_lower_case_cprefix (), infix, get_lower_case_csuffix ());
}
public override string get_upper_case_cname (string infix) {
- return "%s%s".printf (@namespace.get_lower_case_cprefix (), Namespace.camel_case_to_lower_case (name)).up ();
+ return "%s%s".printf (parent_symbol.get_lower_case_cprefix (), camel_case_to_lower_case (name)).up ();
}
public override bool is_reference_type () {
diff --git a/vala/valaenumvalue.vala b/vala/valaenumvalue.vala
index 740983ef2..a95a29c2d 100644
--- a/vala/valaenumvalue.vala
+++ b/vala/valaenumvalue.vala
@@ -25,12 +25,7 @@ using GLib;
/**
* Represents an enum member in the source code.
*/
-public class Vala.EnumValue : CodeNode {
- /**
- * The symbol name of this enum value.
- */
- public string! name { get; set construct; }
-
+public class Vala.EnumValue : Symbol {
/**
* Specifies the numerical representation of this enum value.
*/
@@ -44,8 +39,7 @@ public class Vala.EnumValue : CodeNode {
* @param name enum value name
* @return newly created enum value
*/
- public EnumValue (string! _name) {
- name = _name;
+ public EnumValue (construct string! name) {
}
/**
@@ -55,9 +49,7 @@ public class Vala.EnumValue : CodeNode {
* @param value numerical representation
* @return newly created enum value
*/
- public EnumValue.with_value (string! _name, Expression _value) {
- name = _name;
- value = _value;
+ public EnumValue.with_value (construct string! name, construct Expression value) {
}
public override void accept (CodeVisitor! visitor) {
@@ -71,7 +63,7 @@ public class Vala.EnumValue : CodeNode {
*/
public string! get_cname () {
if (cname == null) {
- var en = (Enum) symbol.parent_symbol.node;
+ var en = (Enum) parent_symbol;
cname = "%s%s".printf (en.get_cprefix (), name);
}
return cname;
diff --git a/vala/valaexpressionstatement.vala b/vala/valaexpressionstatement.vala
index 472ec195f..58925b6d9 100644
--- a/vala/valaexpressionstatement.vala
+++ b/vala/valaexpressionstatement.vala
@@ -1,6 +1,6 @@
/* valaexpressionstatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -26,7 +26,7 @@ using GLib;
* A code statement that evaluates a given expression. The value computed by the
* expression, if any, is discarded.
*/
-public class Vala.ExpressionStatement : Statement {
+public class Vala.ExpressionStatement : CodeNode, Statement {
/**
* Specifies the expression to evaluate.
*/
@@ -49,9 +49,7 @@ public class Vala.ExpressionStatement : Statement {
* @param source reference to source code
* @return newly created expression statement
*/
- public ExpressionStatement (Expression! expr, SourceReference source = null) {
- expression = expr;
- source_reference = source;
+ public ExpressionStatement (construct Expression! expression, construct SourceReference source_reference = null) {
}
public override void accept (CodeVisitor! visitor) {
@@ -66,20 +64,20 @@ public class Vala.ExpressionStatement : Statement {
}
}
- public override int get_number_of_set_construction_parameters () {
+ /**
+ * Returns whether this statement sets a property.
+ *
+ * @return true if this statement sets a property, false otherwise
+ */
+ public bool sets_property () {
if (expression is Assignment) {
var assign = (Assignment) expression;
if (assign.left is MemberAccess) {
var ma = (MemberAccess) assign.left;
- if (ma.symbol_reference != null) {
- if (ma.symbol_reference.node is Property) {
- var prop = (Property) ma.symbol_reference.node;
- return 1;
- }
- }
+ return (ma.symbol_reference is Property);
}
}
- return -1;
+ return false;
}
}
diff --git a/vala/valafield.vala b/vala/valafield.vala
index 3ccd10c8a..576ea8c0e 100644
--- a/vala/valafield.vala
+++ b/vala/valafield.vala
@@ -27,11 +27,6 @@ using GLib;
*/
public class Vala.Field : Member, Invokable, Lockable {
/**
- * The symbol name of this field.
- */
- public string! name { get; set construct; }
-
- /**
* The data type of this field.
*/
public TypeReference! type_reference { get; set construct; }
@@ -54,12 +49,8 @@ public class Vala.Field : Member, Invokable, Lockable {
* the contained type.
*/
public bool instance {
- get {
- return _instance;
- }
- set {
- _instance = value;
- }
+ get { return _instance; }
+ set { _instance = value; }
}
/**
@@ -82,11 +73,7 @@ public class Vala.Field : Member, Invokable, Lockable {
* @param source reference to source code
* @return newly created field
*/
- public Field (string! _name, TypeReference! type, Expression init, SourceReference source) {
- name = _name;
- type_reference = type;
- initializer = init;
- source_reference = source;
+ public Field (construct string! name, construct TypeReference! type_reference, construct Expression initializer, construct SourceReference source_reference = null) {
}
public override void accept (CodeVisitor! visitor) {
@@ -110,9 +97,8 @@ public class Vala.Field : Member, Invokable, Lockable {
*/
public string! get_cname () {
if (cname == null) {
- if (!instance && symbol.parent_symbol.node is DataType) {
- var t = (DataType) symbol.parent_symbol.node;
- cname = "%s_%s".printf (t.get_lower_case_cname (null), name);
+ if (!instance) {
+ cname = "%s_%s".printf (parent_symbol.get_lower_case_cname (null), name);
} else {
cname = name;
}
diff --git a/vala/valaflags.vala b/vala/valaflags.vala
deleted file mode 100644
index fb5f2b598..000000000
--- a/vala/valaflags.vala
+++ /dev/null
@@ -1,150 +0,0 @@
-/* valaflags.vala
- *
- * Copyright (C) 2006-2007 Jürg Billeter
- *
- * This library 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; either
- * version 2 of the License, or (at your option) any later version.
-
- * This library 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 library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- *
- * Author:
- * Jürg Billeter <j@bitron.ch>
- */
-
-using GLib;
-
-/**
- * Represents a flags declaration in the source code.
- */
-public class Vala.Flags : DataType {
- private List<FlagsValue> values;
- private string cname;
- private string cprefix;
-
- /**
- * Creates a new flags.
- *
- * @param name type name
- * @param source reference to source code
- * @return newly created flags
- */
- public Flags (construct string! name, construct SourceReference source_reference = null) {
- }
-
- /**
- * Appends the specified flags value to the list of values.
- *
- * @param value a flags value
- */
- public void add_value (FlagsValue! value) {
- values.append (value);
- }
-
- public override void accept (CodeVisitor! visitor) {
- visitor.visit_flags (this);
- }
-
- public override void accept_children (CodeVisitor! visitor) {
- foreach (FlagsValue value in values) {
- value.accept (visitor);
- }
- }
-
- public override string get_cname (bool const_type = false) {
- if (cname == null) {
- cname = "%s%s".printf (@namespace.get_cprefix (), name);
- }
- return cname;
- }
-
- public override string get_upper_case_cname (string infix) {
- return "%s%s".printf (@namespace.get_lower_case_cprefix (), Namespace.camel_case_to_lower_case (name)).up ();
- }
-
- public override bool is_reference_type () {
- return false;
- }
-
- private void set_cname (string! cname) {
- this.cname = cname;
- }
-
- /**
- * Returns the string to be prepended to the name of members of this
- * enum when used in C code.
- *
- * @return the prefix to be used in C code
- */
- public string! get_cprefix () {
- if (cprefix == null) {
- cprefix = "%s_".printf (get_upper_case_cname (null));
- }
- return cprefix;
- }
-
- /**
- * Sets the string to be prepended to the name of members of this enum
- * when used in C code.
- *
- * @param cprefix the prefix to be used in C code
- */
- public void set_cprefix (string! cprefix) {
- this.cprefix = cprefix;
- }
-
- private void process_ccode_attribute (Attribute! a) {
- if (a.has_argument ("cname")) {
- set_cname (a.get_string ("cname"));
- }
- if (a.has_argument ("cprefix")) {
- set_cprefix (a.get_string ("cprefix"));
- }
- if (a.has_argument ("cheader_filename")) {
- var val = a.get_string ("cheader_filename");
- foreach (string filename in val.split (",")) {
- add_cheader_filename (filename);
- }
- }
- }
-
- /**
- * Process all associated attributes.
- */
- public void process_attributes () {
- foreach (Attribute a in attributes) {
- if (a.name == "CCode") {
- process_ccode_attribute (a);
- }
- }
- }
-
- public override string get_type_id () {
- // FIXME: use GType-registered flags
- return "G_TYPE_INT";
- }
-
- public override string get_marshaller_type_name () {
- return "FLAGS";
- }
-
- public override string get_get_value_function () {
- return "g_value_get_flags";
- }
-
- public override string get_set_value_function () {
- return "g_value_set_flags";
- }
-
- public override string get_default_value () {
- return "0";
- }
-}
diff --git a/vala/valaflagsvalue.vala b/vala/valaflagsvalue.vala
deleted file mode 100644
index 232bc322d..000000000
--- a/vala/valaflagsvalue.vala
+++ /dev/null
@@ -1,80 +0,0 @@
-/* valaflagsvalue.vala
- *
- * Copyright (C) 2006 Jürg Billeter
- *
- * This library 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; either
- * version 2 of the License, or (at your option) any later version.
-
- * This library 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 library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- *
- * Author:
- * Jürg Billeter <j@bitron.ch>
- */
-
-using GLib;
-
-/**
- * Represents a flags member in the source code.
- */
-public class Vala.FlagsValue : CodeNode {
- /**
- * The symbol name of this flags value.
- */
- public string! name { get; set construct; }
-
- /**
- * Specifies the numerical representation of this flags value.
- */
- public Expression value { get; set; }
-
- private string cname;
-
- /**
- * Creates a new flags value.
- *
- * @param name flags value name
- * @return newly created flags value
- */
- public FlagsValue (string! _name) {
- name = _name;
- }
-
- /**
- * Creates a new flags value with the specified numerical
- * representation.
- *
- * @param name flags value name
- * @param value numerical representation
- * @return newly created flags value
- */
- public FlagsValue.with_value (string! _name, Expression _value) {
- name = _name;
- value = _value;
- }
-
- public override void accept (CodeVisitor! visitor) {
- visitor.visit_flags_value (this);
- }
-
- /**
- * Returns the name of this flags value as it is used in C code.
- *
- * @return the name to be used in C code
- */
- public string! get_cname () {
- if (cname == null) {
- var fl = (Flags) symbol.parent_symbol.node;
- cname = "%s_%s".printf (fl.get_upper_case_cname (null), name);
- }
- return cname;
- }
-}
diff --git a/vala/valaforeachstatement.vala b/vala/valaforeachstatement.vala
index 7c0055b77..c97302430 100644
--- a/vala/valaforeachstatement.vala
+++ b/vala/valaforeachstatement.vala
@@ -26,7 +26,7 @@ using GLib;
* Represents a foreach statement in the source code. Foreach statements iterate
* over the elements of a collection.
*/
-public class Vala.ForeachStatement : Statement {
+public class Vala.ForeachStatement : CodeNode, Statement {
/**
* Specifies the element type.
*/
@@ -53,7 +53,7 @@ public class Vala.ForeachStatement : Statement {
/**
* Specifies the loop body.
*/
- public Statement body { get; set; }
+ public Block body { get; set; }
/**
* Specifies the declarator for the generated element variable.
@@ -71,12 +71,7 @@ public class Vala.ForeachStatement : Statement {
* @param source reference to source code
* @return newly created foreach statement
*/
- public ForeachStatement (TypeReference! type, string! id, Expression! col, Statement _body, SourceReference source) {
- type_reference = type;
- variable_name = id;
- collection = col;
- body = _body;
- source_reference = source;
+ public ForeachStatement (construct TypeReference! type_reference, construct string! variable_name, construct Expression! collection, construct Block body, construct SourceReference source_reference) {
}
public override void accept (CodeVisitor! visitor) {
diff --git a/vala/valaformalparameter.vala b/vala/valaformalparameter.vala
index 1ee8d38af..363e26ac7 100644
--- a/vala/valaformalparameter.vala
+++ b/vala/valaformalparameter.vala
@@ -26,12 +26,7 @@ using GLib;
/**
* Represents a formal parameter in method and callback signatures.
*/
-public class Vala.FormalParameter : CodeNode, Invokable {
- /**
- * The parameter name.
- */
- public string! name { get; set construct; }
-
+public class Vala.FormalParameter : Symbol, Invokable {
/**
* The parameter type.
*/
diff --git a/vala/valaforstatement.vala b/vala/valaforstatement.vala
index 6017482be..37bbd62bb 100644
--- a/vala/valaforstatement.vala
+++ b/vala/valaforstatement.vala
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a for iteration statement in the source code.
*/
-public class Vala.ForStatement : Statement {
+public class Vala.ForStatement : CodeNode, Statement {
/**
* Specifies the loop condition.
*/
@@ -42,7 +42,7 @@ public class Vala.ForStatement : Statement {
/**
* Specifies the loop body.
*/
- public Statement body { get; set; }
+ public Block body { get; set; }
private List<Expression> initializer;
private List<Expression> iterator;
@@ -57,10 +57,7 @@ public class Vala.ForStatement : Statement {
* @param source reference to source code
* @return newly created for statement
*/
- public ForStatement (Expression cond, Statement _body, SourceReference source) {
- condition = cond;
- body = _body;
- source_reference = source;
+ public ForStatement (construct Expression condition, construct Block body, construct SourceReference source_reference = null) {
}
/**
diff --git a/vala/valaifstatement.vala b/vala/valaifstatement.vala
index 2912db849..5af3ca5a6 100644
--- a/vala/valaifstatement.vala
+++ b/vala/valaifstatement.vala
@@ -1,6 +1,6 @@
/* valaifstatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents an if selection statement in the source code.
*/
-public class Vala.IfStatement : Statement {
+public class Vala.IfStatement : CodeNode, Statement {
/**
* The boolean condition to evaluate.
*/
diff --git a/vala/valainterface.vala b/vala/valainterface.vala
index 5534bbe74..4655f364a 100644
--- a/vala/valainterface.vala
+++ b/vala/valainterface.vala
@@ -52,9 +52,7 @@ public class Vala.Interface : DataType {
* @param source reference to source code
* @return newly created interface
*/
- public Interface (string! _name, SourceReference source = null) {
- name = _name;
- source_reference = source;
+ public Interface (construct string! name, construct SourceReference source_reference = null) {
}
/**
@@ -65,6 +63,7 @@ public class Vala.Interface : DataType {
public void add_type_parameter (TypeParameter! p) {
type_parameters.append (p);
p.type = this;
+ scope.add (p.name, p);
}
/**
@@ -92,7 +91,20 @@ public class Vala.Interface : DataType {
* @param m a method
*/
public void add_method (Method! m) {
+ if (m is CreationMethod) {
+ Report.error (m.source_reference, "construction methods may only be declared within classes and structs");
+
+ m.error = true;
+ return;
+ }
+ if (m.instance) {
+ m.this_parameter = new FormalParameter ("this", new TypeReference ());
+ m.this_parameter.type_reference.data_type = this;
+ m.scope.add (m.this_parameter.name, m.this_parameter);
+ }
+
methods.append (m);
+ scope.add (m.name, m);
}
/**
@@ -111,6 +123,7 @@ public class Vala.Interface : DataType {
*/
public void add_property (Property! prop) {
properties.append (prop);
+ scope.add (prop.name, prop);
}
/**
@@ -129,6 +142,7 @@ public class Vala.Interface : DataType {
*/
public void add_signal (Signal! sig) {
signals.append (sig);
+ scope.add (sig.name, sig);
}
/**
@@ -142,7 +156,7 @@ public class Vala.Interface : DataType {
public override string get_cname (bool const_type = false) {
if (cname == null) {
- cname = "%s%s".printf (@namespace.get_cprefix (), name);
+ cname = "%s%s".printf (parent_symbol.get_cprefix (), name);
}
return cname;
}
@@ -155,7 +169,7 @@ public class Vala.Interface : DataType {
*/
public string! get_lower_case_csuffix () {
if (lower_case_csuffix == null) {
- lower_case_csuffix = Namespace.camel_case_to_lower_case (name);
+ lower_case_csuffix = camel_case_to_lower_case (name);
}
return lower_case_csuffix;
}
@@ -174,10 +188,10 @@ public class Vala.Interface : DataType {
if (infix == null) {
infix = "";
}
- return "%s%s%s".printf (@namespace.get_lower_case_cprefix (), infix, get_lower_case_csuffix ());
+ return "%s%s%s".printf (parent_symbol.get_lower_case_cprefix (), infix, get_lower_case_csuffix ());
}
- public override string get_lower_case_cprefix () {
+ public override string! get_lower_case_cprefix () {
return "%s_".printf (get_lower_case_cname (null));
}
diff --git a/vala/valainterfacewriter.vala b/vala/valainterfacewriter.vala
index 58d0af279..a011a42f1 100644
--- a/vala/valainterfacewriter.vala
+++ b/vala/valainterfacewriter.vala
@@ -55,7 +55,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
}
public override void visit_namespace (Namespace! ns) {
- if (ns.source_reference != null && ns.source_reference.file.pkg) {
+ if (ns.pkg) {
return;
}
@@ -64,10 +64,8 @@ public class Vala.InterfaceWriter : CodeVisitor {
return;
}
- current_cheader_filename = ns.get_cheader_filename ();
-
write_indent ();
- write_string ("[CCode (cprefix = \"%s\", lower_case_cprefix = \"%s\", cheader_filename = \"%s\")]".printf (ns.get_cprefix (), ns.get_lower_case_cprefix (), current_cheader_filename));
+ write_string ("[CCode (cprefix = \"%s\", lower_case_cprefix = \"%s\")]".printf (ns.get_cprefix (), ns.get_lower_case_cprefix ()));
write_newline ();
write_indent ();
@@ -124,7 +122,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
} else {
first = false;
}
- write_string (base_type.data_type.symbol.get_full_name ());
+ write_string (base_type.data_type.get_full_name ());
}
}
write_begin_block ();
@@ -150,6 +148,21 @@ public class Vala.InterfaceWriter : CodeVisitor {
}
write_indent ();
+
+ var first = true;
+ string cheaders;
+ foreach (string cheader in st.get_cheader_filenames ()) {
+ if (first) {
+ cheaders = cheader;
+ first = false;
+ } else {
+ cheaders = "%s, %s".printf (cheaders, cheader);
+ }
+ }
+ write_string ("[CCode (cheader_filename = \"%s\")]".printf (cheaders));
+ write_newline ();
+
+ write_indent ();
write_string ("public struct ");
write_identifier (st.name);
write_begin_block ();
@@ -207,7 +220,18 @@ public class Vala.InterfaceWriter : CodeVisitor {
}
write_indent ();
- write_string ("[CCode (cprefix = \"%s\")]".printf (en.get_cprefix ()));
+
+ var first = true;
+ string cheaders;
+ foreach (string cheader in en.get_cheader_filenames ()) {
+ if (first) {
+ cheaders = cheader;
+ first = false;
+ } else {
+ cheaders = "%s, %s".printf (cheaders, cheader);
+ }
+ }
+ write_string ("[CCode (cprefix = \"%s\", cheader_filename = \"%s\")]".printf (en.get_cprefix (), cheaders));
write_indent ();
write_string ("public enum ");
@@ -227,36 +251,6 @@ public class Vala.InterfaceWriter : CodeVisitor {
write_newline ();
}
- public override void visit_flags (Flags! fl) {
- if (fl.source_reference != null && fl.source_reference.file.pkg) {
- return;
- }
-
- if (fl.access == MemberAccessibility.PRIVATE) {
- return;
- }
-
- write_indent ();
- write_string ("[CCode (cprefix = \"%s\")]".printf (fl.get_cprefix ()));
-
- write_indent ();
- write_string ("public flags ");
- write_identifier (fl.name);
- write_begin_block ();
-
- fl.accept_children (this);
-
- write_end_block ();
- write_newline ();
- }
-
- public override void visit_flags_value (FlagsValue! fv) {
- write_indent ();
- write_identifier (fv.name);
- write_string (",");
- write_newline ();
- }
-
public override void visit_constant (Constant! c) {
if (c.source_reference != null && c.source_reference.file.pkg) {
return;
@@ -264,7 +258,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
write_indent ();
write_string ("public const ");
- write_string (c.type_reference.data_type.symbol.get_full_name ());
+ write_string (c.type_reference.data_type.get_full_name ());
write_string (" ");
write_identifier (c.name);
@@ -288,7 +282,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
!f.type_reference.takes_ownership) {
write_string ("weak ");
}
- write_string (f.type_reference.data_type.symbol.get_full_name ());
+ write_string (f.type_reference.data_type.get_full_name ());
var type_args = f.type_reference.get_type_arguments ();
if (!(f.type_reference.data_type is Array) && type_args != null) {
@@ -297,7 +291,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
if (!type_arg.takes_ownership) {
write_string ("weak ");
}
- write_string (type_arg.data_type.symbol.get_full_name ());
+ write_string (type_arg.data_type.get_full_name ());
}
write_string (">");
}
@@ -329,7 +323,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
} else if (param.type_reference.is_out) {
write_string ("out ");
}
- write_string (param.type_reference.data_type.symbol.get_full_name ());
+ write_string (param.type_reference.data_type.get_full_name ());
var type_args = param.type_reference.get_type_arguments ();
if (!(param.type_reference.data_type is Array) && type_args != null) {
@@ -338,7 +332,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
if (!type_arg.takes_ownership) {
write_string ("weak ");
}
- write_string (type_arg.data_type.symbol.get_full_name ());
+ write_string (type_arg.data_type.get_full_name ());
}
write_string (">");
}
@@ -382,7 +376,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
if (cb.return_type.transfers_ownership) {
write_string ("ref ");
}
- write_string (cb.return_type.data_type.symbol.get_full_name ());
+ write_string (cb.return_type.data_type.get_full_name ());
}
write_string (" ");
@@ -398,6 +392,10 @@ public class Vala.InterfaceWriter : CodeVisitor {
}
public override void visit_method (Method! m) {
+ if (m.source_reference != null && m.source_reference.file.pkg) {
+ return;
+ }
+
if (m.access == MemberAccessibility.PRIVATE || m.overrides) {
return;
}
@@ -433,7 +431,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
if (m is CreationMethod) {
write_string (" ");
- var datatype = (DataType) m.symbol.parent_symbol.node;
+ var datatype = (DataType) m.parent_symbol;
write_identifier (datatype.name);
if (m.name != null) {
@@ -459,7 +457,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
} else if ((m.return_type.data_type != null && m.return_type.data_type.is_reference_type ()) || m.return_type.type_parameter != null) {
write_string ("weak ");
}
- write_string (m.return_type.data_type.symbol.get_full_name ());
+ write_string (m.return_type.data_type.get_full_name ());
if (m.return_type.non_null) {
write_string ("!");
}
@@ -493,7 +491,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
if (!prop.type_reference.takes_ownership) {
write_string ("weak ");
}
- write_string (prop.type_reference.data_type.symbol.get_full_name ());
+ write_string (prop.type_reference.data_type.get_full_name ());
var type_args = prop.type_reference.get_type_arguments ();
if (!(prop.type_reference.data_type is Array) && type_args != null) {
@@ -502,7 +500,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
if (!type_arg.takes_ownership) {
write_string ("weak ");
}
- write_string (type_arg.data_type.symbol.get_full_name ());
+ write_string (type_arg.data_type.get_full_name ());
}
write_string (">");
}
@@ -546,7 +544,7 @@ public class Vala.InterfaceWriter : CodeVisitor {
if (sig.return_type.transfers_ownership) {
write_string ("ref ");
}
- write_string (sig.return_type.data_type.symbol.get_full_name ());
+ write_string (sig.return_type.data_type.get_full_name ());
if (sig.return_type.non_null) {
write_string ("!");
}
@@ -579,8 +577,8 @@ public class Vala.InterfaceWriter : CodeVisitor {
}
private void write_identifier (string! s) {
- if (s == "base" || s == "callback" || s == "class" ||
- s == "construct" || s == "flags" || s == "foreach" ||
+ if (s == "base" || s == "class" ||
+ s == "construct" || s == "delegate" || s == "foreach" ||
s == "in" || s == "interface" || s == "lock" ||
s == "namespace" || s == "out" || s == "ref") {
stream.putc ('@');
diff --git a/vala/valalockstatement.vala b/vala/valalockstatement.vala
index 775725e08..9243c9a6b 100644
--- a/vala/valalockstatement.vala
+++ b/vala/valalockstatement.vala
@@ -1,6 +1,6 @@
/* valalockstatement.vala
*
- * Copyright (C) 2006 Raffaele Sandrini
+ * Copyright (C) 2006-2007 Raffaele Sandrini, Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a lock statement e.g. "lock (a) { f(a) }".
*/
-public class Vala.LockStatement : Statement {
+public class Vala.LockStatement : CodeNode, Statement {
/**
* Expression representing the resource to be locked.
*/
@@ -34,12 +34,9 @@ public class Vala.LockStatement : Statement {
/**
* The statement during its execution the resource is locked.
*/
- public Statement! body { get; set construct; }
+ public Block! body { get; set construct; }
- public LockStatement (Expression _resource, Statement _body, SourceReference source) {
- resource = _resource;
- body = _body;
- source_reference = source;
+ public LockStatement (construct Expression resource, construct Block body, construct SourceReference source_reference = null) {
}
public override void accept (CodeVisitor! visitor) {
diff --git a/vala/valamember.vala b/vala/valamember.vala
index 651a98b1e..de4014df9 100644
--- a/vala/valamember.vala
+++ b/vala/valamember.vala
@@ -1,6 +1,6 @@
/* valamember.vala
*
- * Copyright (C) 2006 Raffaele Sandrini
+ * Copyright (C) 2006-2007 Raffaele Sandrini, Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -23,7 +23,7 @@
/**
* Represents a general class member.
*/
-public class Vala.Member : CodeNode {
+public class Vala.Member : Symbol {
public override void accept (CodeVisitor! visitor) {
visitor.visit_member (this);
}
diff --git a/vala/valamemorymanager.vala b/vala/valamemorymanager.vala
index 28e4b5e65..b580ce2b9 100644
--- a/vala/valamemorymanager.vala
+++ b/vala/valamemorymanager.vala
@@ -88,7 +88,7 @@ public class Vala.MemoryManager : CodeVisitor {
}
public override void visit_method (Method! m) {
- current_symbol = m.symbol;
+ current_symbol = m;
m.accept_children (this);
}
@@ -98,7 +98,7 @@ public class Vala.MemoryManager : CodeVisitor {
}
public override void visit_property (Property! prop) {
- current_symbol = prop.symbol;
+ current_symbol = prop;
prop.accept_children (this);
}
@@ -135,8 +135,8 @@ public class Vala.MemoryManager : CodeVisitor {
public override void visit_end_return_statement (ReturnStatement! stmt) {
if (stmt.return_expression != null) {
- if (current_symbol.node is Method) {
- var m = (Method) current_symbol.node;
+ if (current_symbol is Method) {
+ var m = (Method) current_symbol;
if (m.return_type.transfers_ownership) {
visit_possibly_missing_copy_expression (stmt.return_expression);
@@ -172,23 +172,23 @@ public class Vala.MemoryManager : CodeVisitor {
List<weak FormalParameter> params;
var msym = expr.call.symbol_reference;
- if (msym.node is VariableDeclarator) {
- var decl = (VariableDeclarator) msym.node;
+ if (msym is VariableDeclarator) {
+ var decl = (VariableDeclarator) msym;
var cb = (Callback) decl.type_reference.data_type;
params = cb.get_parameters ();
- } else if (msym.node is FormalParameter) {
- var param = (FormalParameter) msym.node;
+ } else if (msym is FormalParameter) {
+ var param = (FormalParameter) msym;
var cb = (Callback) param.type_reference.data_type;
params = cb.get_parameters ();
- } else if (msym.node is Field) {
- var f = (Field) msym.node;
+ } else if (msym is Field) {
+ var f = (Field) msym;
var cb = (Callback) f.type_reference.data_type;
params = cb.get_parameters ();
- } else if (msym.node is Method) {
- var m = (Method) msym.node;
+ } else if (msym is Method) {
+ var m = (Method) msym;
params = m.get_parameters ();
- } else if (msym.node is Signal) {
- var sig = (Signal) msym.node;
+ } else if (msym is Signal) {
+ var sig = (Signal) msym;
params = sig.get_parameters ();
}
weak List<weak FormalParameter> params_it = params;
@@ -206,7 +206,7 @@ public class Vala.MemoryManager : CodeVisitor {
var ma = (MemberAccess) expr.call;
TypeReference instance_type = ma.inner.static_type;
// trace type arguments back to the datatype where the method has been declared
- while (instance_type.data_type != msym.parent_symbol.node) {
+ while (instance_type.data_type != msym.parent_symbol) {
List<weak TypeReference> base_types = null;
if (instance_type.data_type is Class) {
var cl = (Class) instance_type.data_type;
@@ -220,7 +220,7 @@ public class Vala.MemoryManager : CodeVisitor {
return;
}
foreach (TypeReference base_type in base_types) {
- if (SemanticAnalyzer.symbol_lookup_inherited (base_type.data_type.symbol, msym.name) != null) {
+ if (SemanticAnalyzer.symbol_lookup_inherited (base_type.data_type, msym.name) != null) {
// construct a new type reference for the base type with correctly linked type arguments
var instance_base_type = new TypeReference ();
instance_base_type.data_type = base_type.data_type;
@@ -241,7 +241,7 @@ public class Vala.MemoryManager : CodeVisitor {
}
}
}
- if (instance_type.data_type != msym.parent_symbol.node) {
+ if (instance_type.data_type != msym.parent_symbol) {
Report.error (expr.source_reference, "internal error: generic type parameter tracing not supported yet");
expr.error = true;
return;
@@ -284,7 +284,7 @@ public class Vala.MemoryManager : CodeVisitor {
}
public override void visit_end_assignment (Assignment! a) {
- if (a.left is PointerIndirection || (a.left.symbol_reference != null && a.left.symbol_reference.node is Signal)) {
+ if (a.left is PointerIndirection || a.left.symbol_reference is Signal) {
} else {
if (a.left.static_type.takes_ownership) {
visit_possibly_missing_copy_expression (a.right);
diff --git a/vala/valamethod.vala b/vala/valamethod.vala
index c6c85abcd..16ad70637 100644
--- a/vala/valamethod.vala
+++ b/vala/valamethod.vala
@@ -28,11 +28,6 @@ using GLib;
*/
public class Vala.Method : Member, Invokable {
/**
- * The symbol name of this method.
- */
- public string name { get; set; }
-
- /**
* The return type of this method.
*/
public TypeReference return_type { get; set; }
@@ -150,10 +145,7 @@ public class Vala.Method : Member, Invokable {
* @param source reference to source code
* @return newly created method
*/
- public Method (string _name, TypeReference _return_type, SourceReference source = null) {
- name = _name;
- return_type = _return_type;
- source_reference = source;
+ public Method (construct string name, construct TypeReference return_type, construct SourceReference source_reference = null) {
}
/**
@@ -167,6 +159,9 @@ public class Vala.Method : Member, Invokable {
}
parameters.append (param);
+ if (!param.ellipsis) {
+ scope.add (param.name, param);
+ }
}
public List<weak FormalParameter> get_parameters () {
@@ -222,17 +217,10 @@ public class Vala.Method : Member, Invokable {
* @return the name to be used in C code by default
*/
public virtual string! get_default_cname () {
- var parent = symbol.parent_symbol.node;
- if (parent is DataType) {
- if (name.has_prefix ("_")) {
- return "_%s%s".printf (((DataType) parent).get_lower_case_cprefix (), name.offset (1));
- } else {
- return "%s%s".printf (((DataType) parent).get_lower_case_cprefix (), name);
- }
- } else if (parent is Namespace) {
- return "%s%s".printf (((Namespace) parent).get_lower_case_cprefix (), name);
+ if (name.has_prefix ("_")) {
+ return "_%s%s".printf (parent_symbol.get_lower_case_cprefix (), name.offset (1));
} else {
- return name;
+ return "%s%s".printf (parent_symbol.get_lower_case_cprefix (), name);
}
}
@@ -244,8 +232,7 @@ public class Vala.Method : Member, Invokable {
*/
public string! get_real_cname () {
if (base_method != null || base_interface_method != null) {
- var parent = (Class) symbol.parent_symbol.node;
- return "%s_real_%s".printf (parent.get_lower_case_cname (null), name);
+ return "%s_real_%s".printf (parent_symbol.get_lower_case_cname (null), name);
} else {
return get_cname ();
}
diff --git a/vala/valanamespace.vala b/vala/valanamespace.vala
index b76d52d66..25c235047 100644
--- a/vala/valanamespace.vala
+++ b/vala/valanamespace.vala
@@ -25,17 +25,16 @@ using GLib;
/**
* Represents a namespace declaration in the source code.
*/
-public class Vala.Namespace : CodeNode {
+public class Vala.Namespace : Symbol {
/**
- * The name of this namespace.
+ * Specifies whether this namespace is only used in a VAPI package file.
*/
- public string name { get; set; }
+ public bool pkg { get; set; }
private List<Class> classes;
private List<Interface> interfaces;
private List<Struct> structs;
private List<Enum> enums;
- private List<Flags> flags_;
private List<Callback> callbacks;
private List<Constant> constants;
private List<Field> fields;
@@ -45,7 +44,9 @@ public class Vala.Namespace : CodeNode {
private string lower_case_cprefix;
private List<string> cheader_filenames;
-
+
+ private List<Namespace> namespaces;
+
/**
* Creates a new namespace.
*
@@ -53,29 +54,36 @@ public class Vala.Namespace : CodeNode {
* @param source reference to source code
* @return newly created namespace
*/
- public Namespace (string _name, SourceReference source = null) {
- name = _name;
- source_reference = source;
+ public Namespace (construct string name, construct SourceReference source_reference = null) {
}
/**
- * Adds the specified class to this namespace.
+ * Adds the specified namespace to this source file.
*
- * @param cl a class
+ * @param ns a namespace
*/
- public void add_class (Class! cl) {
- classes.append (cl);
- cl.@namespace = this;
+ public void add_namespace (Namespace! ns) {
+ namespaces.append (ns);
+ scope.add (ns.name, ns);
}
-
+
/**
- * Removes the specified class from this namespace.
+ * Returns a copy of the list of namespaces.
+ *
+ * @return namespace list
+ */
+ public List<weak Namespace> get_namespaces () {
+ return namespaces.copy ();
+ }
+
+ /**
+ * Adds the specified class to this namespace.
*
* @param cl a class
*/
- public void remove_class (Class! cl) {
- cl.@namespace = null;
- classes.remove (cl);
+ public void add_class (Class! cl) {
+ classes.append (cl);
+ scope.add (cl.name, cl);
}
/**
@@ -85,7 +93,7 @@ public class Vala.Namespace : CodeNode {
*/
public void add_interface (Interface! iface) {
interfaces.append (iface);
- iface.@namespace = this;
+ scope.add (iface.name, iface);
}
/**
@@ -95,7 +103,7 @@ public class Vala.Namespace : CodeNode {
*/
public void add_struct (Struct! st) {
structs.append (st);
- st.@namespace = this;
+ scope.add (st.name, st);
}
/**
@@ -105,27 +113,17 @@ public class Vala.Namespace : CodeNode {
*/
public void add_enum (Enum! en) {
enums.append (en);
- en.@namespace = this;
+ scope.add (en.name, en);
}
/**
- * Adds the specified flags to this namespace.
- *
- * @param fl a flags
- */
- public void add_flags (Flags! fl) {
- flags_.append (fl);
- fl.@namespace = this;
- }
-
- /**
* Adds the specified callback to this namespace.
*
* @param cb a callback
*/
public void add_callback (Callback! cb) {
callbacks.append (cb);
- cb.@namespace = this;
+ scope.add (cb.name, cb);
}
/**
@@ -162,6 +160,7 @@ public class Vala.Namespace : CodeNode {
*/
public void add_constant (Constant! constant) {
constants.append (constant);
+ scope.add (constant.name, constant);
}
/**
@@ -171,6 +170,7 @@ public class Vala.Namespace : CodeNode {
*/
public void add_field (Field! f) {
fields.append (f);
+ scope.add (f.name, f);
}
/**
@@ -179,7 +179,21 @@ public class Vala.Namespace : CodeNode {
* @param m a method
*/
public void add_method (Method! m) {
+ if (m is CreationMethod) {
+ Report.error (m.source_reference, "construction methods may only be declared within classes and structs");
+
+ m.error = true;
+ return;
+ }
+ if (m.instance) {
+ Report.error (m.source_reference, "instance methods not allowed outside of data types");
+
+ m.error = true;
+ return;
+ }
+
methods.append (m);
+ scope.add (m.name, m);
}
public override void accept (CodeVisitor! visitor) {
@@ -187,13 +201,13 @@ public class Vala.Namespace : CodeNode {
}
public override void accept_children (CodeVisitor! visitor) {
- /* process enums and flags first to avoid order problems in C code */
- foreach (Enum en in enums) {
- en.accept (visitor);
+ foreach (Namespace ns in namespaces) {
+ ns.accept (visitor);
}
- foreach (Flags fl in flags_) {
- fl.accept (visitor);
+ /* process enums first to avoid order problems in C code */
+ foreach (Enum en in enums) {
+ en.accept (visitor);
}
foreach (Class cl in classes) {
@@ -224,55 +238,8 @@ public class Vala.Namespace : CodeNode {
m.accept (visitor);
}
}
-
- /**
- * Converts a string from CamelCase to lower_case.
- *
- * @param camel_case a string in camel case
- * @return the specified string converted to lower case
- */
- public static string! camel_case_to_lower_case (string! camel_case) {
- String result = new String ("");
-
- weak string i = camel_case;
-
- bool first = true;
- while (i.len () > 0) {
- unichar c = i.get_char ();
- if (c.isupper () && !first) {
- /* current character is upper case and
- * we're not at the beginning */
- weak string t = i.prev_char ();
- bool prev_upper = t.get_char ().isupper ();
- t = i.next_char ();
- bool next_upper = t.get_char ().isupper ();
- if (!prev_upper || (i.len () >= 2 && !next_upper)) {
- /* previous character wasn't upper case or
- * next character isn't upper case*/
- int len = result.str.len ();
- if (len != 1 && result.str.offset (len - 2).get_char () != '_') {
- /* we're not creating 1 character words */
- result.append_c ('_');
- }
- }
- }
-
- result.append_unichar (c.tolower ());
-
- first = false;
- i = i.next_char ();
- }
-
- return result.str;
- }
- /**
- * Returns the camel case string to be prepended to the name of members
- * of this namespace when used in C code.
- *
- * @return the camel case prefix to be used in C code
- */
- public string! get_cprefix () {
+ public override string! get_cprefix () {
if (cprefix == null) {
if (name == null) {
cprefix = "";
@@ -299,7 +266,7 @@ public class Vala.Namespace : CodeNode {
*
* @return the lower case prefix to be used in C code
*/
- public string! get_lower_case_cprefix () {
+ public override string! get_lower_case_cprefix () {
if (lower_case_cprefix == null) {
if (name == null) {
lower_case_cprefix = "";
@@ -320,19 +287,7 @@ public class Vala.Namespace : CodeNode {
this.lower_case_cprefix = cprefix;
}
- /**
- * Returns a list of C header filenames users of this namespace must
- * include.
- *
- * @return list of C header filenames for this namespace
- */
- public List<weak string> get_cheader_filenames () {
- if (cheader_filenames == null) {
- if (source_reference != null && !source_reference.file.pkg) {
- // don't add default include directives for VAPI files
- cheader_filenames.append (source_reference.file.get_cinclude_filename ());
- }
- }
+ public override List<weak string> get_cheader_filenames () {
return cheader_filenames.copy ();
}
diff --git a/vala/valaproperty.vala b/vala/valaproperty.vala
index 0de75331f..3009ad90d 100644
--- a/vala/valaproperty.vala
+++ b/vala/valaproperty.vala
@@ -27,11 +27,6 @@ using GLib;
*/
public class Vala.Property : Member, Lockable {
/**
- * The property name.
- */
- public string! name { get; set construct; }
-
- /**
* The property type.
*/
public TypeReference! type_reference { get; set construct; }
@@ -147,7 +142,7 @@ public class Vala.Property : Member, Lockable {
* @return the upper case name to be used in C code
*/
public string! get_upper_case_cname () {
- return "%s_%s".printf (((DataType) symbol.parent_symbol.node).get_lower_case_cname (null), Namespace.camel_case_to_lower_case (name)).up ();
+ return "%s_%s".printf (parent_symbol.get_lower_case_cname (null), camel_case_to_lower_case (name)).up ();
}
/**
diff --git a/vala/valapropertyaccessor.vala b/vala/valapropertyaccessor.vala
index 1dd0ab8c9..7bd3a15d9 100644
--- a/vala/valapropertyaccessor.vala
+++ b/vala/valapropertyaccessor.vala
@@ -27,6 +27,11 @@ using GLib;
*/
public class Vala.PropertyAccessor : CodeNode {
/**
+ * The corresponding property.
+ */
+ public weak Property prop { get; set; }
+
+ /**
* Specifies whether this accessor may be used to get the property.
*/
public bool readable { get; set; }
@@ -45,7 +50,7 @@ public class Vala.PropertyAccessor : CodeNode {
/**
* The accessor body.
*/
- public Statement body { get; set; }
+ public Block body { get; set; }
/**
* Represents the generated value parameter in a set accessor.
@@ -62,12 +67,7 @@ public class Vala.PropertyAccessor : CodeNode {
* @param source reference to source code
* @return newly created property accessor
*/
- public PropertyAccessor (bool _readable, bool _writable, bool _construction, Statement _body, SourceReference source) {
- readable = _readable;
- writable = _writable;
- construction = _construction;
- body = _body;
- source_reference = source;
+ public PropertyAccessor (construct bool readable, construct bool writable, construct bool construction, construct Block body, construct SourceReference source_reference) {
}
public override void accept (CodeVisitor! visitor) {
diff --git a/vala/valareturnstatement.vala b/vala/valareturnstatement.vala
index 52e7b0841..3ec1ab720 100644
--- a/vala/valareturnstatement.vala
+++ b/vala/valareturnstatement.vala
@@ -1,6 +1,6 @@
/* valareturnstatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a return statement in the source code.
*/
-public class Vala.ReturnStatement : Statement {
+public class Vala.ReturnStatement : CodeNode, Statement {
/**
* The optional expression to return.
*/
diff --git a/vala/valascope.vala b/vala/valascope.vala
new file mode 100644
index 000000000..745c8e58a
--- /dev/null
+++ b/vala/valascope.vala
@@ -0,0 +1,89 @@
+/* valascope.vala
+ *
+ * Copyright (C) 2006-2007 Jürg Billeter
+ *
+ * This library 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; either
+ * version 2 of the License, or (at your option) any later version.
+
+ * This library 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 library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ *
+ * Author:
+ * Jürg Billeter <j@bitron.ch>
+ */
+
+using GLib;
+
+/**
+ * Represents a part of the symbol tree.
+ */
+public class Vala.Scope {
+ /**
+ * The symbol that owns this scope.
+ */
+ public weak Symbol owner { get; set; }
+
+ /**
+ * The parent of this scope.
+ */
+ public weak Scope parent_scope { get; set; }
+
+ private HashTable<string,Symbol> symbol_table;
+
+ /**
+ * Creates a new scope.
+ *
+ * @return newly created scope
+ */
+ public Scope (construct Symbol owner = null) {
+ }
+
+ /**
+ * Adds the specified symbol with the specified name to the symbol table
+ * of this scope.
+ *
+ * @param name name for the specified symbol
+ * @param sym a symbol
+ */
+ public void add (string name, Symbol! sym) {
+ if (name != null) {
+ if (symbol_table == null) {
+ symbol_table = new HashTable.full (str_hash, str_equal, g_free, g_object_unref);
+ } else if (lookup (name) != null) {
+ owner.error = true;
+ Report.error (owner.source_reference, "`%s' already contains a definition for `%s'".printf (owner.get_full_name (), name));
+ return;
+ }
+
+ symbol_table.insert (name, sym);
+ }
+ sym.owner = this;
+ }
+
+ /**
+ * Returns the symbol stored in the symbol table with the specified
+ * name.
+ *
+ * @param name name of the symbol to be returned
+ * @return found symbol or null
+ */
+ public Symbol lookup (string! name) {
+ if (symbol_table == null) {
+ return null;
+ }
+ Symbol sym = symbol_table.lookup (name);
+ if (sym != null && !sym.active) {
+ sym = null;
+ }
+ return sym;
+ }
+}
+
diff --git a/vala/valasemanticanalyzer.vala b/vala/valasemanticanalyzer.vala
index 2309f35c2..f11f3bba8 100644
--- a/vala/valasemanticanalyzer.vala
+++ b/vala/valasemanticanalyzer.vala
@@ -69,37 +69,37 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
root_symbol = context.root;
bool_type = new TypeReference ();
- bool_type.data_type = (DataType) root_symbol.lookup ("bool").node;
+ bool_type.data_type = (DataType) root_symbol.scope.lookup ("bool");
string_type = new TypeReference ();
- string_type.data_type = (DataType) root_symbol.lookup ("string").node;
+ string_type.data_type = (DataType) root_symbol.scope.lookup ("string");
- pointer_type = (DataType) root_symbol.lookup ("pointer").node;
+ pointer_type = (DataType) root_symbol.scope.lookup ("pointer");
int_type = new TypeReference ();
- int_type.data_type = (DataType) root_symbol.lookup ("int").node;
+ int_type.data_type = (DataType) root_symbol.scope.lookup ("int");
uint_type = new TypeReference ();
- uint_type.data_type = (DataType) root_symbol.lookup ("uint").node;
+ uint_type.data_type = (DataType) root_symbol.scope.lookup ("uint");
ulong_type = new TypeReference ();
- ulong_type.data_type = (DataType) root_symbol.lookup ("ulong").node;
+ ulong_type.data_type = (DataType) root_symbol.scope.lookup ("ulong");
unichar_type = new TypeReference ();
- unichar_type.data_type = (DataType) root_symbol.lookup ("unichar").node;
+ unichar_type.data_type = (DataType) root_symbol.scope.lookup ("unichar");
// TODO: don't require GLib namespace in semantic analyzer
- var glib_ns = root_symbol.lookup ("GLib");
+ var glib_ns = root_symbol.scope.lookup ("GLib");
if (glib_ns != null) {
- initially_unowned_type = (DataType) glib_ns.lookup ("InitiallyUnowned").node;
+ initially_unowned_type = (DataType) glib_ns.scope.lookup ("InitiallyUnowned");
type_type = new TypeReference ();
- type_type.data_type = (DataType) glib_ns.lookup ("Type").node;
+ type_type.data_type = (DataType) glib_ns.scope.lookup ("Type");
- glist_type = (DataType) glib_ns.lookup ("List").node;
- gslist_type = (DataType) glib_ns.lookup ("SList").node;
+ glist_type = (DataType) glib_ns.scope.lookup ("List");
+ gslist_type = (DataType) glib_ns.scope.lookup ("SList");
- gerror_type = (DataType) glib_ns.lookup ("Error").node;
+ gerror_type = (DataType) glib_ns.scope.lookup ("Error");
}
current_symbol = root_symbol;
@@ -118,15 +118,15 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
public override void visit_class (Class! cl) {
- current_symbol = cl.symbol;
+ current_symbol = cl;
current_class = cl;
if (cl.base_class != null) {
- current_source_file.add_symbol_dependency (cl.base_class.symbol, SourceFileDependencyType.HEADER_FULL);
+ current_source_file.add_symbol_dependency (cl.base_class, SourceFileDependencyType.HEADER_FULL);
}
foreach (TypeReference base_type_reference in cl.get_base_types ()) {
- current_source_file.add_symbol_dependency (base_type_reference.data_type.symbol, SourceFileDependencyType.HEADER_FULL);
+ current_source_file.add_symbol_dependency (base_type_reference.data_type, SourceFileDependencyType.HEADER_FULL);
}
cl.accept_children (this);
@@ -142,14 +142,14 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
List<string> missing_prereqs = null;
foreach (DataType prereq in prerequisites) {
if (!class_is_a (cl, prereq)) {
- missing_prereqs.prepend (prereq.symbol.get_full_name ());
+ missing_prereqs.prepend (prereq.get_full_name ());
}
}
/* report any missing prerequisites */
if (missing_prereqs != null) {
cl.error = true;
- string error_string = "%s: some prerequisites (".printf (cl.symbol.get_full_name ());
+ string error_string = "%s: some prerequisites (".printf (cl.get_full_name ());
bool first = true;
foreach (string s in missing_prereqs) {
if (first) {
@@ -175,10 +175,10 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
/* check methods */
foreach (Method m in iface.get_methods ()) {
if (m.is_abstract) {
- var sym = cl.symbol.lookup (m.name);
- if (sym == null || !(sym.node is Method) || ((Method) sym.node).base_interface_method != m) {
+ var sym = cl.scope.lookup (m.name);
+ if (sym == null || !(sym is Method) || ((Method) sym).base_interface_method != m) {
cl.error = true;
- Report.error (cl.source_reference, "`%s' does not implement interface method `%s'".printf (cl.symbol.get_full_name (), m.symbol.get_full_name ()));
+ Report.error (cl.source_reference, "`%s' does not implement interface method `%s'".printf (cl.get_full_name (), m.get_full_name ()));
}
}
}
@@ -193,10 +193,10 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
while (base_class != null && base_class.is_abstract) {
foreach (Method m in base_class.get_methods ()) {
if (m.is_abstract) {
- var sym = cl.symbol.lookup (m.name);
- if (sym == null || !(sym.node is Method) || ((Method) sym.node).base_method != m) {
+ var sym = cl.scope.lookup (m.name);
+ if (sym == null || !(sym is Method) || ((Method) sym).base_method != m) {
cl.error = true;
- Report.error (cl.source_reference, "`%s' does not implement abstract method `%s'".printf (cl.symbol.get_full_name (), m.symbol.get_full_name ()));
+ Report.error (cl.source_reference, "`%s' does not implement abstract method `%s'".printf (cl.get_full_name (), m.get_full_name ()));
}
}
}
@@ -248,7 +248,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
public override void visit_struct (Struct! st) {
- current_symbol = st.symbol;
+ current_symbol = st;
current_struct = st;
st.accept_children (this);
@@ -258,10 +258,10 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
public override void visit_interface (Interface! iface) {
- current_symbol = iface.symbol;
+ current_symbol = iface;
foreach (TypeReference prerequisite_reference in iface.get_prerequisites ()) {
- current_source_file.add_symbol_dependency (prerequisite_reference.data_type.symbol, SourceFileDependencyType.HEADER_FULL);
+ current_source_file.add_symbol_dependency (prerequisite_reference.data_type, SourceFileDependencyType.HEADER_FULL);
}
iface.accept_children (this);
@@ -279,7 +279,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (class_or_interface is Class) {
if (prereq_class != null) {
iface.error = true;
- Report.error (iface.source_reference, "%s: Interfaces cannot have multiple instantiable prerequisites (`%s' and `%s')".printf (iface.symbol.get_full_name (), class_or_interface.symbol.get_full_name (), prereq_class.symbol.get_full_name ()));
+ Report.error (iface.source_reference, "%s: Interfaces cannot have multiple instantiable prerequisites (`%s' and `%s')".printf (iface.get_full_name (), class_or_interface.get_full_name (), prereq_class.get_full_name ()));
return;
}
@@ -311,18 +311,18 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (f.access != MemberAccessibility.PRIVATE) {
if (f.type_reference.data_type != null) {
/* is null if it references a type parameter */
- current_source_file.add_symbol_dependency (f.type_reference.data_type.symbol, SourceFileDependencyType.HEADER_SHALLOW);
+ current_source_file.add_symbol_dependency (f.type_reference.data_type, SourceFileDependencyType.HEADER_SHALLOW);
}
} else {
if (f.type_reference.data_type != null) {
/* is null if it references a type parameter */
- current_source_file.add_symbol_dependency (f.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (f.type_reference.data_type, SourceFileDependencyType.SOURCE);
}
}
}
public override void visit_method (Method! m) {
- current_symbol = m.symbol;
+ current_symbol = m;
current_return_type = m.return_type;
var init_attr = m.get_attribute ("ModuleInit");
@@ -332,7 +332,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (m.return_type.data_type != null) {
/* is null if it is void or a reference to a type parameter */
- current_source_file.add_symbol_dependency (m.return_type.data_type.symbol, SourceFileDependencyType.HEADER_SHALLOW);
+ current_source_file.add_symbol_dependency (m.return_type.data_type, SourceFileDependencyType.HEADER_SHALLOW);
}
m.accept_children (this);
@@ -340,39 +340,38 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
current_symbol = current_symbol.parent_symbol;
current_return_type = null;
- if (current_symbol.parent_symbol != null &&
- current_symbol.parent_symbol.node is Method) {
+ if (current_symbol.parent_symbol is Method) {
/* lambda expressions produce nested methods */
- var up_method = (Method) current_symbol.parent_symbol.node;
+ var up_method = (Method) current_symbol.parent_symbol;
current_return_type = up_method.return_type;
}
- if (current_symbol.node is Class) {
+ if (current_symbol is Class) {
if (!(m is CreationMethod)) {
- find_base_interface_method (m, (Class) current_symbol.node);
+ find_base_interface_method (m, (Class) current_symbol);
if (m.is_virtual || m.overrides) {
- find_base_class_method (m, (Class) current_symbol.node);
+ find_base_class_method (m, (Class) current_symbol);
if (m.base_method == null) {
- Report.error (m.source_reference, "%s: no suitable method found to override".printf (m.symbol.get_full_name ()));
+ Report.error (m.source_reference, "%s: no suitable method found to override".printf (m.get_full_name ()));
}
}
}
- } else if (current_symbol.node is Struct) {
+ } else if (current_symbol is Struct) {
if (m.is_abstract || m.is_virtual || m.overrides) {
- Report.error (m.source_reference, "A struct member `%s' cannot be marked as override, virtual, or abstract".printf (m.symbol.get_full_name ()));
+ Report.error (m.source_reference, "A struct member `%s' cannot be marked as override, virtual, or abstract".printf (m.get_full_name ()));
return;
}
}
}
private void find_base_class_method (Method! m, Class! cl) {
- var sym = cl.symbol.lookup (m.name);
- if (sym != null && sym.node is Method) {
- var base_method = (Method) sym.node;
+ var sym = cl.scope.lookup (m.name);
+ if (sym is Method) {
+ var base_method = (Method) sym;
if (base_method.is_abstract || base_method.is_virtual) {
if (!m.equals (base_method)) {
m.error = true;
- Report.error (m.source_reference, "Return type and/or parameters of overriding method `%s' do not match overridden method `%s'.".printf (m.symbol.get_full_name (), base_method.symbol.get_full_name ()));
+ Report.error (m.source_reference, "Return type and/or parameters of overriding method `%s' do not match overridden method `%s'.".printf (m.get_full_name (), base_method.get_full_name ()));
return;
}
@@ -390,13 +389,13 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
// FIXME report error if multiple possible base methods are found
foreach (TypeReference type in cl.get_base_types ()) {
if (type.data_type is Interface) {
- var sym = type.data_type.symbol.lookup (m.name);
- if (sym != null && sym.node is Method) {
- var base_method = (Method) sym.node;
+ var sym = type.data_type.scope.lookup (m.name);
+ if (sym is Method) {
+ var base_method = (Method) sym;
if (base_method.is_abstract) {
if (!m.equals (base_method)) {
m.error = true;
- Report.error (m.source_reference, "Return type and/or parameters of overriding method `%s' do not match overridden method `%s'.".printf (m.symbol.get_full_name (), base_method.symbol.get_full_name ()));
+ Report.error (m.source_reference, "Return type and/or parameters of overriding method `%s' do not match overridden method `%s'.".printf (m.get_full_name (), base_method.get_full_name ()));
return;
}
@@ -410,12 +409,12 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
public override void visit_creation_method (CreationMethod! m) {
m.return_type = new TypeReference ();
- m.return_type.data_type = (DataType) current_symbol.node;
+ m.return_type.data_type = (DataType) m.parent_symbol;
m.return_type.transfers_ownership = true;
- if (current_symbol.node is Class) {
+ if (current_symbol is Class) {
// check for floating reference
- var cl = (Class) current_symbol.node;
+ var cl = (Class) current_symbol;
while (cl != null) {
if (cl == initially_unowned_type) {
m.return_type.floating_reference = true;
@@ -426,7 +425,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
}
- current_symbol = m.symbol;
+ current_symbol = m;
current_return_type = m.return_type;
m.accept_children (this);
@@ -434,26 +433,25 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
current_symbol = current_symbol.parent_symbol;
current_return_type = null;
- if (current_symbol.parent_symbol != null &&
- current_symbol.parent_symbol.node is Method) {
+ if (current_symbol.parent_symbol is Method) {
/* lambda expressions produce nested methods */
- var up_method = (Method) current_symbol.parent_symbol.node;
+ var up_method = (Method) current_symbol.parent_symbol;
current_return_type = up_method.return_type;
}
- if (current_symbol.node is Class) {
+ if (current_symbol is Class) {
if (!(m is CreationMethod)) {
- find_base_interface_method (m, (Class) current_symbol.node);
+ find_base_interface_method (m, (Class) current_symbol);
if (m.is_virtual || m.overrides) {
- find_base_class_method (m, (Class) current_symbol.node);
+ find_base_class_method (m, (Class) current_symbol);
if (m.base_method == null) {
- Report.error (m.source_reference, "%s: no suitable method found to override".printf (m.symbol.get_full_name ()));
+ Report.error (m.source_reference, "%s: no suitable method found to override".printf (m.get_full_name ()));
}
}
}
- } else if (current_symbol.node is Struct) {
+ } else if (current_symbol is Struct) {
if (m.is_abstract || m.is_virtual || m.overrides) {
- Report.error (m.source_reference, "A struct member `%s' cannot be marked as override, virtual, or abstract".printf (m.symbol.get_full_name ()));
+ Report.error (m.source_reference, "A struct member `%s' cannot be marked as override, virtual, or abstract".printf (m.get_full_name ()));
return;
}
}
@@ -461,13 +459,12 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (m.body != null && current_class != null) {
int n_params = 0;
foreach (Statement stmt in m.body.get_statements ()) {
- int params = stmt.get_number_of_set_construction_parameters ();
- if (params == -1) {
+ if (!(stmt is ExpressionStatement) || !((ExpressionStatement) stmt).sets_property ()) {
m.error = true;
Report.error (stmt.source_reference, "class creation methods only allow property assignment statements");
return;
}
- n_params += params;
+ n_params++;
}
m.n_construction_params = n_params;
}
@@ -479,46 +476,46 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (!p.ellipsis) {
if (p.type_reference.data_type != null) {
/* is null if it references a type parameter */
- current_source_file.add_symbol_dependency (p.type_reference.data_type.symbol, SourceFileDependencyType.HEADER_SHALLOW);
- current_source_file.add_symbol_dependency (p.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (p.type_reference.data_type, SourceFileDependencyType.HEADER_SHALLOW);
+ current_source_file.add_symbol_dependency (p.type_reference.data_type, SourceFileDependencyType.SOURCE);
}
}
/* special treatment for construct formal parameters used in creation methods */
if (p.construct_parameter) {
- if (!(p.symbol.parent_symbol.node is CreationMethod)) {
+ if (!(p.parent_symbol is CreationMethod)) {
p.error = true;
Report.error (p.source_reference, "construct parameters are only allowed in type creation methods");
return;
}
- var method_body = ((CreationMethod)p.symbol.parent_symbol.node).body;
+ var method_body = ((CreationMethod) p.parent_symbol).body;
var left = new MemberAccess.simple (p.name);
var right = new MemberAccess.simple (p.name);
/* try to lookup the requested property */
- var prop_sym = symbol_lookup_inherited (current_class.symbol, p.name);
- if (!(prop_sym.node is Property)) {
+ var prop_sym = symbol_lookup_inherited (current_class, p.name);
+ if (!(prop_sym is Property)) {
p.error = true;
- Report.error (p.source_reference, "class `%s' does not contain a property named `%s'".printf (current_class.symbol.get_full_name (), p.name));
+ Report.error (p.source_reference, "class `%s' does not contain a property named `%s'".printf (current_class.get_full_name (), p.name));
return;
}
left.symbol_reference = prop_sym;
- right.symbol_reference = p.symbol;
+ right.symbol_reference = p;
method_body.add_statement (new ExpressionStatement (new Assignment (left, right)));
}
}
private void find_base_class_property (Property! prop, Class! cl) {
- var sym = cl.symbol.lookup (prop.name);
- if (sym != null && sym.node is Property) {
- var base_property = (Property) sym.node;
+ var sym = cl.scope.lookup (prop.name);
+ if (sym is Property) {
+ var base_property = (Property) sym;
if (base_property.is_abstract || base_property.is_virtual) {
if (!prop.equals (base_property)) {
prop.error = true;
- Report.error (prop.source_reference, "Type and/or accessors of overriding property `%s' do not match overridden property `%s'.".printf (prop.symbol.get_full_name (), base_property.symbol.get_full_name ()));
+ Report.error (prop.source_reference, "Type and/or accessors of overriding property `%s' do not match overridden property `%s'.".printf (prop.get_full_name (), base_property.get_full_name ()));
return;
}
@@ -536,13 +533,13 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
// FIXME report error if multiple possible base properties are found
foreach (TypeReference type in cl.get_base_types ()) {
if (type.data_type is Interface) {
- var sym = type.data_type.symbol.lookup (prop.name);
- if (sym != null && sym.node is Property) {
- var base_property = (Property) sym.node;
+ var sym = type.data_type.scope.lookup (prop.name);
+ if (sym is Property) {
+ var base_property = (Property) sym;
if (base_property.is_abstract) {
if (!prop.equals (base_property)) {
prop.error = true;
- Report.error (prop.source_reference, "Type and/or accessors of overriding property `%s' do not match overridden property `%s'.".printf (prop.symbol.get_full_name (), base_property.symbol.get_full_name ()));
+ Report.error (prop.source_reference, "Type and/or accessors of overriding property `%s' do not match overridden property `%s'.".printf (prop.get_full_name (), base_property.get_full_name ()));
return;
}
@@ -555,37 +552,59 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
public override void visit_property (Property! prop) {
+ current_symbol = prop;
+
prop.accept_children (this);
+ current_symbol = current_symbol.parent_symbol;
+
if (prop.type_reference.data_type != null) {
/* is null if it references a type parameter */
- current_source_file.add_symbol_dependency (prop.type_reference.data_type.symbol, SourceFileDependencyType.HEADER_SHALLOW);
- current_source_file.add_symbol_dependency (prop.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (prop.type_reference.data_type, SourceFileDependencyType.HEADER_SHALLOW);
+ current_source_file.add_symbol_dependency (prop.type_reference.data_type, SourceFileDependencyType.SOURCE);
}
- if (prop.symbol.parent_symbol.node is Class) {
- var cl = (Class) prop.symbol.parent_symbol.node;
+ if (prop.parent_symbol is Class) {
+ var cl = (Class) prop.parent_symbol;
find_base_interface_property (prop, cl);
if (prop.is_virtual || prop.overrides) {
find_base_class_property (prop, cl);
if (prop.base_property == null) {
prop.error = true;
- Report.error (prop.source_reference, "%s: no suitable property found to override".printf (prop.symbol.get_full_name ()));
+ Report.error (prop.source_reference, "%s: no suitable property found to override".printf (prop.get_full_name ()));
}
}
}
}
public override void visit_property_accessor (PropertyAccessor! acc) {
- var prop = (Property) acc.symbol.parent_symbol.node;
+ acc.prop = (Property) current_symbol;
if (acc.readable) {
- current_return_type = prop.type_reference;
+ current_return_type = acc.prop.type_reference;
} else {
// void
current_return_type = new TypeReference ();
}
+ if (!acc.source_reference.file.pkg) {
+ if (acc.body == null && !acc.prop.interface_only && !acc.prop.is_abstract) {
+ /* no accessor body specified, insert default body */
+
+ acc.body = new Block ();
+ if (acc.readable) {
+ acc.body.add_statement (new ReturnStatement (new MemberAccess.simple ("_%s".printf (acc.prop.name))));
+ } else {
+ acc.body.add_statement (new ExpressionStatement (new Assignment (new MemberAccess.simple ("_%s".printf (acc.prop.name)), new MemberAccess.simple ("value"))));
+ }
+ }
+
+ if (acc.writable || acc.construction) {
+ acc.value_parameter = new FormalParameter ("value", acc.prop.type_reference);
+ acc.body.scope.add (acc.value_parameter.name, acc.value_parameter);
+ }
+ }
+
acc.accept_children (this);
current_return_type = null;
@@ -596,7 +615,12 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
public override void visit_constructor (Constructor! c) {
- current_symbol = c.symbol;
+ c.this_parameter = new FormalParameter ("this", new TypeReference ());
+ c.this_parameter.type_reference.data_type = (DataType) current_symbol;
+ c.scope.add (c.this_parameter.name, c.this_parameter);
+
+ c.owner = current_symbol.scope;
+ current_symbol = c;
c.accept_children (this);
@@ -604,7 +628,8 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
public override void visit_destructor (Destructor! d) {
- current_symbol = d.symbol;
+ d.owner = current_symbol.scope;
+ current_symbol = d;
d.accept_children (this);
@@ -615,12 +640,13 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
public override void visit_begin_block (Block! b) {
- current_symbol = b.symbol;
+ b.owner = current_symbol.scope;
+ current_symbol = b;
}
public override void visit_end_block (Block! b) {
foreach (VariableDeclarator decl in b.get_local_variables ()) {
- decl.symbol.active = false;
+ decl.active = false;
}
current_symbol = current_symbol.parent_symbol;
@@ -654,15 +680,15 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
return;
}
- if (decl.initializer.symbol_reference.node is Method &&
+ if (decl.initializer.symbol_reference is Method &&
decl.type_reference.data_type is Callback) {
- var m = (Method) decl.initializer.symbol_reference.node;
+ var m = (Method) decl.initializer.symbol_reference;
var cb = (Callback) decl.type_reference.data_type;
/* check whether method matches callback type */
if (!cb.matches_method (m)) {
decl.error = true;
- Report.error (decl.source_reference, "declaration of method `%s' doesn't match declaration of callback `%s'".printf (m.symbol.get_full_name (), cb.symbol.get_full_name ()));
+ Report.error (decl.source_reference, "declaration of method `%s' doesn't match declaration of callback `%s'".printf (m.get_full_name (), cb.get_full_name ()));
return;
}
@@ -688,16 +714,15 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
if (decl.type_reference.data_type != null) {
- current_source_file.add_symbol_dependency (decl.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (decl.type_reference.data_type, SourceFileDependencyType.SOURCE);
}
- decl.symbol = new Symbol (decl);
- current_symbol.add (decl.name, decl.symbol);
+ current_symbol.scope.add (decl.name, decl);
- var block = (Block) current_symbol.node;
+ var block = (Block) current_symbol;
block.add_local_variable (decl);
- decl.symbol.active = true;
+ decl.active = true;
}
/**
@@ -820,14 +845,13 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
public override void visit_begin_foreach_statement (ForeachStatement! stmt) {
if (stmt.type_reference.data_type != null) {
- current_source_file.add_symbol_dependency (stmt.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (stmt.type_reference.data_type, SourceFileDependencyType.SOURCE);
}
stmt.variable_declarator = new VariableDeclarator (stmt.variable_name);
stmt.variable_declarator.type_reference = stmt.type_reference;
- stmt.variable_declarator.symbol = new Symbol (stmt.variable_declarator);
- stmt.body.symbol.add (stmt.variable_name, stmt.variable_declarator.symbol);
+ stmt.body.scope.add (stmt.variable_name, stmt.variable_declarator);
}
public override void visit_end_foreach_statement (ForeachStatement! stmt) {
@@ -874,8 +898,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
if (stmt.return_expression != null &&
- stmt.return_expression.symbol_reference != null &&
- stmt.return_expression.symbol_reference.node is VariableDeclarator &&
+ stmt.return_expression.symbol_reference is VariableDeclarator &&
stmt.return_expression.static_type.takes_ownership &&
!current_return_type.transfers_ownership) {
Report.warning (stmt.source_reference, "Local variable with strong reference used as return value and method return type hasn't been declared to transfer ownership");
@@ -892,15 +915,14 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
public override void visit_catch_clause (CatchClause! clause) {
if (clause.type_reference.data_type != null) {
- current_source_file.add_symbol_dependency (clause.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (clause.type_reference.data_type, SourceFileDependencyType.SOURCE);
}
clause.variable_declarator = new VariableDeclarator (clause.variable_name);
clause.variable_declarator.type_reference = new TypeReference ();
clause.variable_declarator.type_reference.data_type = gerror_type;
- clause.variable_declarator.symbol = new Symbol (clause.variable_declarator);
- clause.body.symbol.add (clause.variable_name, clause.variable_declarator.symbol);
+ clause.body.scope.add (clause.variable_name, clause.variable_declarator);
clause.accept_children (this);
}
@@ -912,7 +934,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
*/
public override void visit_lock_statement (LockStatement! stmt) {
/* resource must be a member access and denote a Lockable */
- if (!(stmt.resource is MemberAccess && stmt.resource.symbol_reference.node is Lockable)) {
+ if (!(stmt.resource is MemberAccess && stmt.resource.symbol_reference is Lockable)) {
stmt.error = true;
stmt.resource.error = true;
Report.error (stmt.resource.source_reference, "Expression is either not a member access or does not denote a lockable member");
@@ -920,13 +942,13 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
/* parent symbol must be the current class */
- if (stmt.resource.symbol_reference.parent_symbol.node != current_class) {
+ if (stmt.resource.symbol_reference.parent_symbol != current_class) {
stmt.error = true;
stmt.resource.error = true;
Report.error (stmt.resource.source_reference, "Only members of the current class are lockable");
}
- ((Lockable)stmt.resource.symbol_reference.node).set_lock_used (true);
+ ((Lockable) stmt.resource.symbol_reference).set_lock_used (true);
}
public override void visit_begin_array_creation_expression (ArrayCreationExpression! expr) {
@@ -993,17 +1015,17 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
public override void visit_character_literal (CharacterLiteral! expr) {
expr.static_type = new TypeReference ();
- expr.static_type.data_type = (DataType) root_symbol.lookup ("char").node;
+ expr.static_type.data_type = (DataType) root_symbol.scope.lookup ("char");
}
public override void visit_integer_literal (IntegerLiteral! expr) {
expr.static_type = new TypeReference ();
- expr.static_type.data_type = (DataType) root_symbol.lookup (expr.get_type_name ()).node;
+ expr.static_type.data_type = (DataType) root_symbol.scope.lookup (expr.get_type_name ());
}
public override void visit_real_literal (RealLiteral! expr) {
expr.static_type = new TypeReference ();
- expr.static_type.data_type = (DataType) root_symbol.lookup (expr.get_type_name ()).node;
+ expr.static_type.data_type = (DataType) root_symbol.scope.lookup (expr.get_type_name ());
}
public override void visit_string_literal (StringLiteral! expr) {
@@ -1021,60 +1043,60 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
expr.static_type = expr.literal.static_type;
}
- private TypeReference get_static_type_for_node (CodeNode! node) {
- if (node is Field) {
- var f = (Field) node;
+ private TypeReference get_static_type_for_symbol (Symbol! sym) {
+ if (sym is Field) {
+ var f = (Field) sym;
return f.type_reference;
- } else if (node is Constant) {
- var c = (Constant) node;
+ } else if (sym is Constant) {
+ var c = (Constant) sym;
return c.type_reference;
- } else if (node is Property) {
- var prop = (Property) node;
+ } else if (sym is Property) {
+ var prop = (Property) sym;
var type = prop.type_reference.copy ();
type.takes_ownership = false;
return type;
- } else if (node is FormalParameter) {
- var p = (FormalParameter) node;
+ } else if (sym is FormalParameter) {
+ var p = (FormalParameter) sym;
return p.type_reference;
- } else if (node is TypeReference) {
- return (TypeReference) node;
- } else if (node is VariableDeclarator) {
- var decl = (VariableDeclarator) node;
+ } else if (sym is TypeReference) {
+ return (TypeReference) sym;
+ } else if (sym is VariableDeclarator) {
+ var decl = (VariableDeclarator) sym;
return decl.type_reference;
- } else if (node is EnumValue || node is FlagsValue) {
+ } else if (sym is EnumValue) {
var type = new TypeReference ();
- type.data_type = (DataType) node.symbol.parent_symbol.node;
+ type.data_type = (DataType) sym.parent_symbol;
return type;
}
return null;
}
public static Symbol symbol_lookup_inherited (Symbol! sym, string! name) {
- var result = sym.lookup (name);
+ var result = sym.scope.lookup (name);
if (result != null) {
return result;
}
- if (sym.node is Class) {
- var cl = (Class) sym.node;
+ if (sym is Class) {
+ var cl = (Class) sym;
foreach (TypeReference base_type in cl.get_base_types ()) {
- result = symbol_lookup_inherited (base_type.data_type.symbol, name);
+ result = symbol_lookup_inherited (base_type.data_type, name);
if (result != null) {
return result;
}
}
- } else if (sym.node is Struct) {
- var st = (Struct) sym.node;
+ } else if (sym is Struct) {
+ var st = (Struct) sym;
foreach (TypeReference base_type in st.get_base_types ()) {
- result = symbol_lookup_inherited (base_type.data_type.symbol, name);
+ result = symbol_lookup_inherited (base_type.data_type, name);
if (result != null) {
return result;
}
}
- } else if (sym.node is Interface) {
- var iface = (Interface) sym.node;
+ } else if (sym is Interface) {
+ var iface = (Interface) sym;
foreach (TypeReference prerequisite in iface.get_prerequisites ()) {
- result = symbol_lookup_inherited (prerequisite.data_type.symbol, name);
+ result = symbol_lookup_inherited (prerequisite.data_type, name);
if (result != null) {
return result;
}
@@ -1092,8 +1114,8 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
private DataType find_parent_type (Symbol sym) {
while (sym != null) {
- if (sym.node is DataType) {
- return (DataType) sym.node;
+ if (sym is DataType) {
+ return (DataType) sym;
}
sym = sym.parent_symbol;
}
@@ -1114,7 +1136,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (expr.symbol_reference == null) {
foreach (NamespaceReference ns in current_using_directives) {
- var local_sym = ns.namespace_symbol.lookup (expr.member_name);
+ var local_sym = ns.namespace_symbol.scope.lookup (expr.member_name);
if (local_sym != null) {
if (expr.symbol_reference != null) {
expr.error = true;
@@ -1134,14 +1156,13 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (expr.inner is MemberAccess || expr.inner is BaseAccess) {
base_symbol = expr.inner.symbol_reference;
- if (base_symbol.node is Namespace ||
- base_symbol.node is DataType) {
- expr.symbol_reference = base_symbol.lookup (expr.member_name);
+ if (base_symbol is Namespace || base_symbol is DataType) {
+ expr.symbol_reference = base_symbol.scope.lookup (expr.member_name);
}
}
if (expr.symbol_reference == null && expr.inner.static_type != null) {
- base_symbol = expr.inner.static_type.data_type.symbol;
+ base_symbol = expr.inner.static_type.data_type;
expr.symbol_reference = symbol_lookup_inherited (base_symbol, expr.member_name);
}
}
@@ -1152,7 +1173,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
return;
}
- var member = expr.symbol_reference.node;
+ var member = expr.symbol_reference;
MemberAccessibility access = MemberAccessibility.PUBLIC;
if (member is Field) {
access = ((Field) member).access;
@@ -1161,19 +1182,19 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
if (access == MemberAccessibility.PRIVATE) {
- var target_type = (DataType) member.symbol.parent_symbol.node;
+ var target_type = (DataType) member.parent_symbol;
var this_type = find_parent_type (current_symbol);
if (target_type != this_type) {
expr.error = true;
- Report.error (expr.source_reference, "Access to private member `%s' denied".printf (member.symbol.get_full_name ()));
+ Report.error (expr.source_reference, "Access to private member `%s' denied".printf (member.get_full_name ()));
return;
}
}
current_source_file.add_symbol_dependency (expr.symbol_reference, SourceFileDependencyType.SOURCE);
- expr.static_type = get_static_type_for_node (expr.symbol_reference.node);
+ expr.static_type = get_static_type_for_symbol (expr.symbol_reference);
}
private bool is_type_compatible (TypeReference! expression_type, TypeReference! expected_type) {
@@ -1266,8 +1287,8 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
List<weak FormalParameter> params;
- if (msym.node is Invokable) {
- var m = (Invokable) msym.node;
+ if (msym is Invokable) {
+ var m = (Invokable) msym;
if (m.is_invokable ()) {
params = m.get_parameters ();
} else {
@@ -1303,7 +1324,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
weak List<weak Expression> prev_arg_it = null;
weak List<weak Expression> arg_it = args;
- bool diag = (msym.node.get_attribute ("Diagnostics") != null);
+ bool diag = (msym.get_attribute ("Diagnostics") != null);
bool ellipsis = false;
int i = 0;
@@ -1315,7 +1336,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
/* header file necessary if we need to cast argument */
if (param.type_reference.data_type != null) {
- current_source_file.add_symbol_dependency (param.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (param.type_reference.data_type, SourceFileDependencyType.SOURCE);
}
if (arg_it == null) {
@@ -1373,8 +1394,8 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
TypeReference ret_type;
List<weak FormalParameter> params;
- if (msym.node is Invokable) {
- var m = (Invokable) msym.node;
+ if (msym is Invokable) {
+ var m = (Invokable) msym;
ret_type = m.get_return_type ();
params = m.get_parameters ();
@@ -1403,7 +1424,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
} else {
TypeReference instance_type = ma.inner.static_type;
// trace type arguments back to the datatype where the method has been declared
- while (instance_type.data_type != msym.parent_symbol.node) {
+ while (instance_type.data_type != msym.parent_symbol) {
List<weak TypeReference> base_types = null;
if (instance_type.data_type is Class) {
var cl = (Class) instance_type.data_type;
@@ -1417,7 +1438,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
return;
}
foreach (TypeReference base_type in base_types) {
- if (symbol_lookup_inherited (base_type.data_type.symbol, msym.name) != null) {
+ if (symbol_lookup_inherited (base_type.data_type, msym.name) != null) {
// construct a new type reference for the base type with correctly linked type arguments
var instance_base_type = new TypeReference ();
instance_base_type.data_type = base_type.data_type;
@@ -1438,7 +1459,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
}
}
- if (instance_type.data_type != msym.parent_symbol.node) {
+ if (instance_type.data_type != msym.parent_symbol) {
Report.error (expr.source_reference, "internal error: generic type parameter tracing not supported yet");
expr.error = true;
return;
@@ -1459,8 +1480,8 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
}
}
- if (msym.node is Method) {
- var m = (Method) msym.node;
+ if (msym is Method) {
+ var m = (Method) msym;
expr.tree_can_fail = expr.can_fail = (m.get_error_domains ().length () > 0);
}
@@ -1532,7 +1553,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
expr.static_type.data_type = current_class.base_class;
}
- expr.symbol_reference = expr.static_type.data_type.symbol;
+ expr.symbol_reference = expr.static_type.data_type;
}
public override void visit_postfix_expression (PostfixExpression! expr) {
@@ -1554,37 +1575,37 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
return;
}
- var constructor_node = expr.member_name.symbol_reference.node;
- var type_node = expr.member_name.symbol_reference.node;
+ var constructor_sym = expr.member_name.symbol_reference;
+ var type_sym = expr.member_name.symbol_reference;
var type_args = expr.member_name.get_type_arguments ();
- if (constructor_node is Method) {
- type_node = constructor_node.symbol.parent_symbol.node;
+ if (constructor_sym is Method) {
+ type_sym = constructor_sym.parent_symbol;
- var constructor = (Method) constructor_node;
- if (!(constructor_node is CreationMethod)) {
+ var constructor = (Method) constructor_sym;
+ if (!(constructor_sym is CreationMethod)) {
expr.error = true;
- Report.error (expr.source_reference, "`%s' is not a creation method".printf (constructor.symbol.get_full_name ()));
+ Report.error (expr.source_reference, "`%s' is not a creation method".printf (constructor.get_full_name ()));
return;
}
- expr.symbol_reference = constructor.symbol;
+ expr.symbol_reference = constructor;
type_args = ((MemberAccess) expr.member_name.inner).get_type_arguments ();
- } else if (constructor_node is EnumValue) {
- type_node = constructor_node.symbol.parent_symbol.node;
+ } else if (constructor_sym is EnumValue) {
+ type_sym = constructor_sym.parent_symbol;
- expr.symbol_reference = constructor_node.symbol;
+ expr.symbol_reference = constructor_sym;
}
- if (type_node is Class || type_node is Struct) {
- type = (DataType) type_node;
- } else if (type_node is Enum && ((Enum) type_node).error_domain) {
- type = (DataType) type_node;
+ if (type_sym is Class || type_sym is Struct) {
+ type = (DataType) type_sym;
+ } else if (type_sym is Enum && ((Enum) type_sym).error_domain) {
+ type = (DataType) type_sym;
} else {
expr.error = true;
- Report.error (expr.source_reference, "`%s' is not a class, struct, or error domain".printf (type_node.symbol.get_full_name ()));
+ Report.error (expr.source_reference, "`%s' is not a class, struct, or error domain".printf (type_sym.get_full_name ()));
return;
}
@@ -1603,7 +1624,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
return;
}
- current_source_file.add_symbol_dependency (type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (type, SourceFileDependencyType.SOURCE);
expr.static_type = expr.type_reference.copy ();
expr.static_type.transfers_ownership = true;
@@ -1614,12 +1635,12 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (cl.is_abstract) {
expr.static_type = null;
expr.error = true;
- Report.error (expr.source_reference, "Can't create instance of abstract class `%s'".printf (cl.symbol.get_full_name ()));
+ Report.error (expr.source_reference, "Can't create instance of abstract class `%s'".printf (cl.get_full_name ()));
return;
}
- if (expr.symbol_reference == null && cl.default_construction_method != null) {
- expr.symbol_reference = cl.default_construction_method.symbol;
+ if (expr.symbol_reference == null) {
+ expr.symbol_reference = cl.default_construction_method;
}
while (cl != null) {
@@ -1633,21 +1654,21 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
} else if (type is Struct) {
var st = (Struct) type;
- if (expr.symbol_reference == null && st.default_construction_method != null) {
- expr.symbol_reference = st.default_construction_method.symbol;
+ if (expr.symbol_reference == null) {
+ expr.symbol_reference = st.default_construction_method;
}
}
if (expr.symbol_reference == null && expr.get_argument_list ().length () != 0) {
expr.static_type = null;
expr.error = true;
- Report.error (expr.source_reference, "No arguments allowed when constructing type `%s'".printf (type.symbol.get_full_name ()));
+ Report.error (expr.source_reference, "No arguments allowed when constructing type `%s'".printf (type.get_full_name ()));
return;
}
- if (expr.symbol_reference != null && expr.symbol_reference.node is Method) {
- var m = (Method) expr.symbol_reference.node;
- check_arguments (expr, m.symbol, m.get_parameters (), expr.get_argument_list ());
+ if (expr.symbol_reference is Method) {
+ var m = (Method) expr.symbol_reference;
+ check_arguments (expr, m, m.get_parameters (), expr.get_argument_list ());
expr.tree_can_fail = expr.can_fail = (m.get_error_domains ().length () > 0);
} else if (type is Enum) {
@@ -1784,7 +1805,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
// FIXME: check whether cast is allowed
if (expr.type_reference.data_type != null) {
- current_source_file.add_symbol_dependency (expr.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (expr.type_reference.data_type, SourceFileDependencyType.SOURCE);
}
expr.static_type = expr.type_reference;
@@ -2009,7 +2030,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
return;
}
- current_source_file.add_symbol_dependency (expr.type_reference.data_type.symbol, SourceFileDependencyType.SOURCE);
+ current_source_file.add_symbol_dependency (expr.type_reference.data_type, SourceFileDependencyType.SOURCE);
expr.static_type = bool_type;
}
@@ -2151,8 +2172,8 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
private Method find_current_method () {
var sym = current_symbol;
while (sym != null) {
- if (sym.node is Method) {
- return (Method) sym.node;
+ if (sym is Method) {
+ return (Method) sym;
}
sym = sym.parent_symbol;
}
@@ -2162,7 +2183,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
private bool is_in_constructor () {
var sym = current_symbol;
while (sym != null) {
- if (sym.node is Constructor) {
+ if (sym is Constructor) {
return true;
}
sym = sym.parent_symbol;
@@ -2188,8 +2209,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
var cb = (Callback) l.expected_type.data_type;
l.method = new Method (get_lambda_name (), cb.return_type);
l.method.instance = cb.instance && in_instance_method;
- l.method.symbol = new Symbol (l.method);
- l.method.symbol.parent_symbol = current_symbol;
+ l.method.owner = current_symbol.scope;
var lambda_params = l.get_parameters ();
weak List<weak FormalParameter> lambda_param_it = lambda_params;
@@ -2202,8 +2222,6 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
var lambda_param = (string) lambda_param_it.data;
var param = new FormalParameter (lambda_param, cb_param.type_reference);
- param.symbol = new Symbol (param);
- l.method.symbol.add (param.name, param.symbol);
l.method.add_parameter (param);
@@ -2219,8 +2237,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (l.expression_body != null) {
var block = new Block ();
- block.symbol = new Symbol (block);
- block.symbol.parent_symbol = l.method.symbol;
+ block.scope.parent_scope = l.method.scope;
if (l.method.return_type.data_type != null) {
block.add_statement (new ReturnStatement (l.expression_body));
@@ -2231,11 +2248,11 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
l.method.body = block;
} else {
l.method.body = l.statement_body;
- l.method.body.symbol.parent_symbol = l.method.symbol;
}
+ l.method.body.owner = l.method.scope;
/* lambda expressions should be usable like MemberAccess of a method */
- l.symbol_reference = l.method.symbol;
+ l.symbol_reference = l.method;
}
public override void visit_begin_assignment (Assignment! a) {
@@ -2248,8 +2265,8 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
return;
}
- if (ma.symbol_reference.node is Signal) {
- var sig = (Signal) ma.symbol_reference.node;
+ if (ma.symbol_reference is Signal) {
+ var sig = (Signal) ma.symbol_reference;
a.right.expected_type = new TypeReference ();
a.right.expected_type.data_type = sig.get_callback ();
@@ -2277,7 +2294,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
var ma = (MemberAccess) a.left;
- if (!(ma.symbol_reference.node is Signal)) {
+ if (!(ma.symbol_reference is Signal)) {
var old_value = new MemberAccess (ma.inner, ma.member_name);
var bin = new BinaryExpression (BinaryOperator.PLUS, old_value, new ParenthesizedExpression (a.right, a.right.source_reference));
@@ -2314,8 +2331,8 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
if (a.left is MemberAccess) {
var ma = (MemberAccess) a.left;
- if (ma.symbol_reference.node is Signal) {
- var sig = (Signal) ma.symbol_reference.node;
+ if (ma.symbol_reference is Signal) {
+ var sig = (Signal) ma.symbol_reference;
if (a.right.symbol_reference == null) {
a.error = true;
@@ -2323,7 +2340,7 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
return;
}
- var m = (Method) a.right.symbol_reference.node;
+ var m = (Method) a.right.symbol_reference;
if (m.instance && m.access != MemberAccessibility.PRIVATE) {
/* TODO: generate wrapper function */
@@ -2342,27 +2359,27 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
*/
m.instance_last = true;
}
- } else if (ma.symbol_reference.node is Property) {
- var prop = (Property) ma.symbol_reference.node;
+ } else if (ma.symbol_reference is Property) {
+ var prop = (Property) ma.symbol_reference;
if (prop.set_accessor == null) {
ma.error = true;
- Report.error (ma.source_reference, "Property `%s' is read-only".printf (prop.symbol.get_full_name ()));
+ Report.error (ma.source_reference, "Property `%s' is read-only".printf (prop.get_full_name ()));
return;
}
- } else if (ma.symbol_reference.node is VariableDeclarator && a.right.static_type == null) {
- var decl = (VariableDeclarator) ma.symbol_reference.node;
+ } else if (ma.symbol_reference is VariableDeclarator && a.right.static_type == null) {
+ var decl = (VariableDeclarator) ma.symbol_reference;
var right_ma = (MemberAccess) a.right;
- if (right_ma.symbol_reference.node is Method &&
+ if (right_ma.symbol_reference is Method &&
decl.type_reference.data_type is Callback) {
- var m = (Method) right_ma.symbol_reference.node;
+ var m = (Method) right_ma.symbol_reference;
var cb = (Callback) decl.type_reference.data_type;
/* check whether method matches callback type */
if (!cb.matches_method (m)) {
decl.error = true;
- Report.error (a.source_reference, "declaration of method `%s' doesn't match declaration of callback `%s'".printf (m.symbol.get_full_name (), cb.symbol.get_full_name ()));
+ Report.error (a.source_reference, "declaration of method `%s' doesn't match declaration of callback `%s'".printf (m.get_full_name (), cb.get_full_name ()));
return;
}
@@ -2372,19 +2389,19 @@ public class Vala.SemanticAnalyzer : CodeVisitor {
Report.error (a.source_reference, "Assignment: Invalid callback assignment attempt");
return;
}
- } else if (ma.symbol_reference.node is Field && a.right.static_type == null) {
- var f = (Field) ma.symbol_reference.node;
+ } else if (ma.symbol_reference is Field && a.right.static_type == null) {
+ var f = (Field) ma.symbol_reference;
var right_ma = (MemberAccess) a.right;
- if (right_ma.symbol_reference.node is Method &&
+ if (right_ma.symbol_reference is Method &&
f.type_reference.data_type is Callback) {
- var m = (Method) right_ma.symbol_reference.node;
+ var m = (Method) right_ma.symbol_reference;
var cb = (Callback) f.type_reference.data_type;
/* check whether method matches callback type */
if (!cb.matches_method (m)) {
f.error = true;
- Report.error (a.source_reference, "declaration of method `%s' doesn't match declaration of callback `%s'".printf (m.symbol.get_full_name (), cb.symbol.get_full_name ()));
+ Report.error (a.source_reference, "declaration of method `%s' doesn't match declaration of callback `%s'".printf (m.get_full_name (), cb.get_full_name ()));
return;
}
diff --git a/vala/valasignal.vala b/vala/valasignal.vala
index 88ea75333..5e1b89ac8 100644
--- a/vala/valasignal.vala
+++ b/vala/valasignal.vala
@@ -27,11 +27,6 @@ using GLib;
*/
public class Vala.Signal : Member, Invokable, Lockable {
/**
- * The symbol name of this signal.
- */
- public string! name { get; set construct; }
-
- /**
* The return type of handlers of this signal.
*/
public TypeReference! return_type { get; set construct; }
@@ -62,10 +57,7 @@ public class Vala.Signal : Member, Invokable, Lockable {
* @param source reference to source code
* @return newly created signal
*/
- public Signal (string! _name, TypeReference! _return_type, SourceReference source) {
- name = _name;
- return_type = _return_type;
- source_reference = source;
+ public Signal (construct string! name, construct TypeReference! return_type, construct SourceReference source_reference = null) {
}
/**
@@ -75,6 +67,7 @@ public class Vala.Signal : Member, Invokable, Lockable {
*/
public void add_parameter (FormalParameter! param) {
parameters.append (param);
+ scope.add (param.name, param);
}
public List<weak FormalParameter> get_parameters () {
@@ -100,7 +93,7 @@ public class Vala.Signal : Member, Invokable, Lockable {
generated_callback.instance = true;
var sender_type = new TypeReference ();
- sender_type.data_type = (DataType) symbol.parent_symbol.node;
+ sender_type.data_type = (DataType) parent_symbol;
var sender_param = new FormalParameter ("sender", sender_type);
generated_callback.add_parameter (sender_param);
diff --git a/vala/valasourcefile.vala b/vala/valasourcefile.vala
index d04ecde01..a1b40eedc 100644
--- a/vala/valasourcefile.vala
+++ b/vala/valasourcefile.vala
@@ -67,7 +67,7 @@ public class Vala.SourceFile {
* The context this source file belongs to.
*/
public weak CodeContext context { get; set; }
-
+
private List<NamespaceReference> using_directives;
private List<CodeNode> nodes;
@@ -91,10 +91,7 @@ public class Vala.SourceFile {
* @param pkg true if this is a VAPI package file
* @return newly created source file
*/
- public SourceFile (CodeContext! _context, string! _filename, bool _pkg = false) {
- context = _context;
- filename = _filename;
- pkg = _pkg;
+ public SourceFile (construct CodeContext! context, construct string! filename, construct bool pkg = false) {
}
/**
@@ -210,28 +207,28 @@ public class Vala.SourceFile {
public void add_symbol_dependency (Symbol! sym, SourceFileDependencyType dep_type) {
DataType t;
- if (sym.node is DataType) {
- t = (DataType) sym.node;
- } else if (sym.node is Method || sym.node is Field) {
- if (sym.parent_symbol.node is DataType) {
- t = (DataType) sym.parent_symbol.node;
+ if (sym is DataType) {
+ t = (DataType) sym;
+ } else if (sym is Method || sym is Field) {
+ if (sym.parent_symbol is DataType) {
+ t = (DataType) sym.parent_symbol;
} else {
return;
}
- } else if (sym.node is Property) {
- t = (DataType) sym.parent_symbol.node;
- } else if (sym.node is Constant) {
- if (sym.parent_symbol.node is DataType) {
- t = (DataType) sym.parent_symbol.node;
- } else if (sym.parent_symbol.node is Namespace) {
- var ns = (Namespace) sym.parent_symbol.node;
+ } else if (sym is Property) {
+ t = (DataType) sym.parent_symbol;
+ } else if (sym is Constant) {
+ if (sym.parent_symbol is DataType) {
+ t = (DataType) sym.parent_symbol;
+ } else if (sym.parent_symbol is Namespace) {
+ var ns = (Namespace) sym.parent_symbol;
source_internal_includes.concat (ns.get_cheader_filenames ());
return;
} else {
return;
}
- } else if (sym.node is FormalParameter) {
- var fp = (FormalParameter) sym.node;
+ } else if (sym is FormalParameter) {
+ var fp = (FormalParameter) sym;
t = fp.type_reference.data_type;
if (t == null) {
/* generic type parameter */
diff --git a/vala/valastatement.vala b/vala/valastatement.vala
index 75cc69af5..b38a69380 100644
--- a/vala/valastatement.vala
+++ b/vala/valastatement.vala
@@ -23,17 +23,7 @@
using GLib;
/**
- * Base class for all statement types.
+ * Interface for all statement types.
*/
-public abstract class Vala.Statement : CodeNode {
- /**
- * Returns the number of construction parameters this statement sets in
- * maximum or -1 if this statement may not be used in the construction
- * part of a construction method.
- *
- * @return number of construction parameters set or -1
- */
- public virtual int get_number_of_set_construction_parameters () {
- return -1;
- }
+public interface Vala.Statement : CodeNode {
}
diff --git a/vala/valastruct.vala b/vala/valastruct.vala
index ac34755ed..f5841948b 100644
--- a/vala/valastruct.vala
+++ b/vala/valastruct.vala
@@ -74,6 +74,7 @@ public class Vala.Struct : DataType {
public void add_type_parameter (TypeParameter! p) {
type_parameters.append (p);
p.type = this;
+ scope.add (p.name, p);
}
/**
@@ -83,6 +84,7 @@ public class Vala.Struct : DataType {
*/
public void add_constant (Constant! c) {
constants.append (c);
+ scope.add (c.name, c);
}
/**
@@ -92,6 +94,7 @@ public class Vala.Struct : DataType {
*/
public void add_field (Field! f) {
fields.append (f);
+ scope.add (f.name, f);
}
/**
@@ -111,7 +114,17 @@ public class Vala.Struct : DataType {
public void add_method (Method! m) {
return_if_fail (m != null);
+ if (m.instance) {
+ m.this_parameter = new FormalParameter ("this", new TypeReference ());
+ m.this_parameter.type_reference.data_type = this;
+ m.scope.add (m.this_parameter.name, m.this_parameter);
+ }
+ if (m is CreationMethod && m.name == null) {
+ default_construction_method = m;
+ }
+
methods.append (m);
+ scope.add (m.name, m);
}
/**
@@ -151,7 +164,7 @@ public class Vala.Struct : DataType {
}
if (cname == null) {
- cname = "%s%s".printf (@namespace.get_cprefix (), name);
+ cname = "%s%s".printf (parent_symbol.get_cprefix (), name);
}
return cname;
}
@@ -164,7 +177,7 @@ public class Vala.Struct : DataType {
this.const_cname = cname;
}
- public override string get_lower_case_cprefix () {
+ public override string! get_lower_case_cprefix () {
if (lower_case_cprefix == null) {
lower_case_cprefix = "%s_".printf (get_lower_case_cname (null));
}
@@ -173,7 +186,7 @@ public class Vala.Struct : DataType {
private string get_lower_case_csuffix () {
if (lower_case_csuffix == null) {
- lower_case_csuffix = Namespace.camel_case_to_lower_case (name);
+ lower_case_csuffix = camel_case_to_lower_case (name);
}
return lower_case_csuffix;
}
@@ -182,7 +195,7 @@ public class Vala.Struct : DataType {
if (infix == null) {
infix = "";
}
- return "%s%s%s".printf (@namespace.get_lower_case_cprefix (), infix, get_lower_case_csuffix ());
+ return "%s%s%s".printf (parent_symbol.get_lower_case_cprefix (), infix, get_lower_case_csuffix ());
}
public override string get_upper_case_cname (string infix) {
@@ -309,7 +322,7 @@ public class Vala.Struct : DataType {
public override string get_dup_function () {
if (dup_function == null) {
- Report.error (source_reference, "The type `%s` doesn't contain a copy function".printf (symbol.get_full_name ()));
+ Report.error (source_reference, "The type `%s` doesn't contain a copy function".printf (get_full_name ()));
}
return dup_function;
}
@@ -320,7 +333,7 @@ public class Vala.Struct : DataType {
public override string get_free_function () {
if (free_function == null) {
- Report.error (source_reference, "The type `%s` doesn't contain a free function".printf (symbol.get_full_name ()));
+ Report.error (source_reference, "The type `%s` doesn't contain a free function".printf (get_full_name ()));
}
return free_function;
}
@@ -334,7 +347,7 @@ public class Vala.Struct : DataType {
if (is_reference_type ()) {
type_id = "G_TYPE_POINTER";
} else {
- Report.error (source_reference, "The type `%s` doesn't declare a type id".printf (symbol.get_full_name ()));
+ Report.error (source_reference, "The type `%s` doesn't declare a type id".printf (get_full_name ()));
}
}
return type_id;
@@ -349,7 +362,7 @@ public class Vala.Struct : DataType {
if (is_reference_type ()) {
marshaller_type_name = "POINTER";
} else {
- Report.error (source_reference, "The type `%s` doesn't declare a marshaller type name".printf (symbol.get_full_name ()));
+ Report.error (source_reference, "The type `%s` doesn't declare a marshaller type name".printf (get_full_name ()));
}
}
return marshaller_type_name;
@@ -364,7 +377,7 @@ public class Vala.Struct : DataType {
if (is_reference_type ()) {
return "g_value_get_pointer";
} else {
- Report.error (source_reference, "The value type `%s` doesn't declare a GValue get function".printf (symbol.get_full_name ()));
+ Report.error (source_reference, "The value type `%s` doesn't declare a GValue get function".printf (get_full_name ()));
return null;
}
} else {
@@ -377,7 +390,7 @@ public class Vala.Struct : DataType {
if (is_reference_type ()) {
return "g_value_set_pointer";
} else {
- Report.error (source_reference, "The value type `%s` doesn't declare a GValue set function".printf (symbol.get_full_name ()));
+ Report.error (source_reference, "The value type `%s` doesn't declare a GValue set function".printf (get_full_name ()));
return null;
}
} else {
diff --git a/vala/valaswitchstatement.vala b/vala/valaswitchstatement.vala
index b7c5a23d1..1d0ae011f 100644
--- a/vala/valaswitchstatement.vala
+++ b/vala/valaswitchstatement.vala
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a switch selection statement in the source code.
*/
-public class Vala.SwitchStatement : Statement {
+public class Vala.SwitchStatement : CodeNode, Statement {
/**
* Specifies the switch expression.
*/
diff --git a/vala/valasymbol.vala b/vala/valasymbol.vala
index e5c5941f5..0ff6f9af4 100644
--- a/vala/valasymbol.vala
+++ b/vala/valasymbol.vala
@@ -25,16 +25,32 @@ using GLib;
/**
* Represents a node in the symbol tree.
*/
-public class Vala.Symbol {
+public abstract class Vala.Symbol : CodeNode {
/**
- * The code node that created this symbol, if applicable.
+ * The parent of this symbol.
*/
- public weak CodeNode node { get; set; }
-
+ public weak Symbol parent_symbol {
+ get {
+ if (owner == null) {
+ return null;
+ } else {
+ return owner.owner;
+ }
+ }
+ }
+
/**
- * The parent of this symbol.
+ * The scope this symbol opens.
*/
- public weak Symbol parent_symbol { get; set; }
+ public weak Scope owner {
+ get {
+ return _owner;
+ }
+ set {
+ _owner = value;
+ _scope.parent_scope = value;
+ }
+ }
/**
* The symbol name.
@@ -50,20 +66,16 @@ public class Vala.Symbol {
* jump statements.
*/
public bool active { get; set; }
-
- private HashTable<string,Symbol> symbol_table = new HashTable.full (str_hash, str_equal, g_free, g_object_unref);
-
- /**
- * Creates a new symbol.
- *
- * @param node the corresponding code node
- * @return newly created symbol
- */
- public Symbol (CodeNode _node = null) {
- node = _node;
+
+ public Scope scope {
+ get { return _scope; }
}
-
+
+ private Scope _owner;
+ private Scope _scope;
+
construct {
+ _scope = new Scope (this);
active = true;
}
@@ -88,32 +100,92 @@ public class Vala.Symbol {
return "%s.%s".printf (parent_symbol.get_full_name (), name);
}
-
+
/**
- * Adds the specified symbol with the specified name to the symbol table
- * of this symbol.
+ * Returns the camel case string to be prepended to the name of members
+ * of this symbol when used in C code.
*
- * @param name name for the specified symbol
- * @param sym a symbol
+ * @return the camel case prefix to be used in C code
*/
- public void add (string! name, Symbol! sym) {
- symbol_table.insert (name, sym);
- sym.parent_symbol = this;
- sym.name = name;
+ public virtual string! get_cprefix () {
+ if (name == null) {
+ return "";
+ } else {
+ return name;
+ }
}
/**
- * Returns the symbol stored in the symbol table with the specified
- * name.
+ * Returns the C name of this symbol in lower case. Words are
+ * separated by underscores. The lower case C name of the parent symbol
+ * is prefix of the result, if there is one.
+ *
+ * @param infix a string to be placed between namespace and data type
+ * name or null
+ * @return the lower case name to be used in C code
+ */
+ public virtual string get_lower_case_cname (string infix = null) {
+ return null;
+ }
+
+ /**
+ * Returns the string to be prefixed to members of this symbol in
+ * lower case when used in C code.
+ *
+ * @return the lower case prefix to be used in C code
+ */
+ public virtual string! get_lower_case_cprefix () {
+ return "";
+ }
+
+ /**
+ * Returns a list of C header filenames users of this symbol must
+ * include.
+ *
+ * @return list of C header filenames for this symbol
+ */
+ public virtual List<weak string> get_cheader_filenames () {
+ return null;
+ }
+
+ /**
+ * Converts a string from CamelCase to lower_case.
*
- * @param name name of the symbol to be returned
- * @return found symbol or null
+ * @param camel_case a string in camel case
+ * @return the specified string converted to lower case
*/
- public Symbol lookup (string! name) {
- Symbol sym = symbol_table.lookup (name);
- if (sym != null && !sym.active) {
- sym = null;
+ public static string! camel_case_to_lower_case (string! camel_case) {
+ String result = new String ("");
+
+ weak string i = camel_case;
+
+ bool first = true;
+ while (i.len () > 0) {
+ unichar c = i.get_char ();
+ if (c.isupper () && !first) {
+ /* current character is upper case and
+ * we're not at the beginning */
+ weak string t = i.prev_char ();
+ bool prev_upper = t.get_char ().isupper ();
+ t = i.next_char ();
+ bool next_upper = t.get_char ().isupper ();
+ if (!prev_upper || (i.len () >= 2 && !next_upper)) {
+ /* previous character wasn't upper case or
+ * next character isn't upper case*/
+ int len = result.str.len ();
+ if (len != 1 && result.str.offset (len - 2).get_char () != '_') {
+ /* we're not creating 1 character words */
+ result.append_c ('_');
+ }
+ }
+ }
+
+ result.append_unichar (c.tolower ());
+
+ first = false;
+ i = i.next_char ();
}
- return sym;
+
+ return result.str;
}
}
diff --git a/vala/valasymbolbuilder.vala b/vala/valasymbolbuilder.vala
deleted file mode 100644
index 31be7f90d..000000000
--- a/vala/valasymbolbuilder.vala
+++ /dev/null
@@ -1,427 +0,0 @@
-/* valasymbolbuilder.vala
- *
- * Copyright (C) 2006-2007 Jürg Billeter, Raffaele Sandrini
- *
- * This library 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; either
- * version 2 of the License, or (at your option) any later version.
-
- * This library 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 library; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- *
- * Author:
- * Jürg Billeter <j@bitron.ch>
- * Raffaele Sandrini <rasa@gmx.ch>
- */
-
-using GLib;
-
-/**
- * Code visitor building the symbol tree.
- */
-public class Vala.SymbolBuilder : CodeVisitor {
- Symbol root;
- Symbol current_type;
- Symbol current_symbol;
-
- /**
- * Build the symbol tree for the specified code context.
- *
- * @param context a code context
- */
- public void build (CodeContext! context) {
- root = context.root;
- context.accept (this);
- }
-
- public override void visit_namespace (Namespace! ns) {
- if (ns.name == null) {
- ns.symbol = root;
- }
-
- if (ns.symbol == null) {
- ns.symbol = root.lookup (ns.name);
- }
- if (ns.symbol == null) {
- ns.symbol = new Symbol (ns);
- root.add (ns.name, ns.symbol);
- }
-
- current_symbol = ns.symbol;
-
- ns.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- private weak Symbol add_symbol (string name, CodeNode! node) {
- if (name != null) {
- if (current_symbol.lookup (name) != null) {
- node.error = true;
- Report.error (node.source_reference, "`%s' already contains a definition for `%s'".printf (current_symbol.get_full_name (), name));
- return null;
- }
- }
- node.symbol = new Symbol (node);
- if (name != null) {
- current_symbol.add (name, node.symbol);
- } else {
- node.symbol.parent_symbol = current_symbol;
- }
-
- return node.symbol;
- }
-
- public override void visit_class (Class! cl) {
- if (cl.error) {
- /* skip classes with errors */
- return;
- }
-
- var class_symbol = current_symbol.lookup (cl.name);
- if (class_symbol == null || !(class_symbol.node is Class)) {
- class_symbol = add_symbol (cl.name, cl);
- } else {
- /* merge this class declaration with existing class symbol */
- var main_class = (Class) class_symbol.node;
- foreach (TypeReference base_type in cl.get_base_types ()) {
- main_class.add_base_type (base_type);
- }
- foreach (Field f in cl.get_fields ()) {
- main_class.add_field (f);
- }
- foreach (Method m in cl.get_methods ()) {
- main_class.add_method (m);
- }
- foreach (Property prop in cl.get_properties ()) {
- main_class.add_property (prop, true);
- }
- foreach (Signal sig in cl.get_signals ()) {
- main_class.add_signal (sig);
- }
- if (cl.constructor != null) {
- if (main_class.constructor != null) {
- cl.error = true;
- Report.error (cl.constructor.source_reference, "`%s' already contains a constructor".printf (current_symbol.get_full_name ()));
- return;
- }
- main_class.constructor = cl.constructor;
- }
- if (cl.destructor != null) {
- if (main_class.destructor != null) {
- cl.error = true;
- Report.error (cl.destructor.source_reference, "`%s' already contains a destructor".printf (current_symbol.get_full_name ()));
- return;
- }
- main_class.destructor = cl.destructor;
- }
- }
-
- current_symbol = class_symbol;
-
- cl.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
-
- if (cl.symbol == null) {
- /* remove merged class */
- cl.@namespace.remove_class (cl);
- if (cl.source_reference != null) {
- cl.source_reference.file.remove_node (cl);
- }
- }
- }
-
- public override void visit_struct (Struct! st) {
- if (st.error) {
- /* skip structs with errors */
- return;
- }
-
- if (add_symbol (st.name, st) == null) {
- return;
- }
-
- current_symbol = st.symbol;
-
- st.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_interface (Interface! iface) {
- if (iface.error) {
- /* skip interfaces with errors */
- return;
- }
-
- if (add_symbol (iface.name, iface) == null) {
- return;
- }
-
- current_symbol = iface.symbol;
-
- iface.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_enum (Enum! en) {
- if (en.error) {
- /* skip enums with errors */
- return;
- }
-
- if (add_symbol (en.name, en) == null) {
- return;
- }
-
- current_symbol = en.symbol;
-
- en.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_enum_value (EnumValue! ev) {
- ev.symbol = new Symbol (ev);
- current_symbol.add (ev.name, ev.symbol);
- }
-
- public override void visit_flags (Flags! fl) {
- if (fl.error) {
- /* skip flags with errors */
- return;
- }
-
- if (add_symbol (fl.name, fl) == null) {
- return;
- }
-
- current_symbol = fl.symbol;
-
- fl.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_flags_value (FlagsValue! fv) {
- fv.symbol = new Symbol (fv);
- current_symbol.add (fv.name, fv.symbol);
- }
-
- public override void visit_callback (Callback! cb) {
- if (cb.error) {
- /* skip enums with errors */
- return;
- }
-
- if (add_symbol (cb.name, cb) == null) {
- return;
- }
-
- current_symbol = cb.symbol;
-
- cb.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_constant (Constant! c) {
- add_symbol (c.name, c);
- }
-
- public override void visit_field (Field! f) {
- add_symbol (f.name, f);
- }
-
- public override void visit_method (Method! m) {
- if (add_symbol (m.name, m) == null) {
- return;
- }
-
- if (m.instance) {
- if (!(m.symbol.parent_symbol.node is DataType)) {
- Report.error (m.source_reference, "instance methods not allowed outside of data types");
-
- m.error = true;
- return;
- }
-
- m.this_parameter = new FormalParameter ("this", new TypeReference ());
- m.this_parameter.type_reference.data_type = (DataType) m.symbol.parent_symbol.node;
- m.this_parameter.symbol = new Symbol (m.this_parameter);
- current_symbol.add (m.this_parameter.name, m.this_parameter.symbol);
- }
-
- current_symbol = m.symbol;
-
- m.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_creation_method (CreationMethod! m) {
- if (add_symbol (m.name, m) == null) {
- return;
- }
-
- var type_node = m.symbol.parent_symbol.node;
- if (!(type_node is Class || type_node is Struct)) {
- Report.error (m.source_reference, "construction methods may only be declared within classes and structs");
-
- m.error = true;
- return;
- }
-
- if (m.name == null) {
- if (type_node is Class) {
- ((Class) type_node).default_construction_method = m;
- } else if (type_node is Struct) {
- ((Struct) type_node).default_construction_method = m;
- }
- }
-
- current_symbol = m.symbol;
-
- m.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_formal_parameter (FormalParameter! p) {
- if (!p.ellipsis) {
- add_symbol (p.name, p);
- }
- }
-
- public override void visit_property (Property! prop) {
- if (prop.error) {
- /* skip properties with errors */
- return;
- }
-
- if (add_symbol (prop.name, prop) == null) {
- return;
- }
-
- current_symbol = prop.symbol;
-
- prop.this_parameter = new FormalParameter ("this", new TypeReference ());
- prop.this_parameter.type_reference.data_type = (DataType) prop.symbol.parent_symbol.node;
- prop.this_parameter.symbol = new Symbol (prop.this_parameter);
- current_symbol.add (prop.this_parameter.name, prop.this_parameter.symbol);
-
- prop.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_property_accessor (PropertyAccessor! acc) {
- acc.symbol = new Symbol (acc);
- acc.symbol.parent_symbol = current_symbol;
-
- if (acc.source_reference.file.pkg) {
- return;
- }
-
- current_symbol = acc.symbol;
-
- if (acc.writable || acc.construction) {
- acc.value_parameter = new FormalParameter ("value", ((Property) current_symbol.parent_symbol.node).type_reference);
- acc.value_parameter.symbol = new Symbol (acc.value_parameter);
-
- current_symbol.add (acc.value_parameter.name, acc.value_parameter.symbol);
- }
-
- if (acc.body == null) {
- /* no accessor body specified, insert default body */
-
- var prop = (Property) acc.symbol.parent_symbol.node;
-
- if (prop.interface_only || prop.is_abstract) {
- current_symbol = current_symbol.parent_symbol;
- return;
- }
-
- var block = new Block ();
- if (acc.readable) {
- block.add_statement (new ReturnStatement (new MemberAccess.simple ("_%s".printf (prop.name))));
- } else {
- block.add_statement (new ExpressionStatement (new Assignment (new MemberAccess.simple ("_%s".printf (prop.name)), new MemberAccess.simple ("value"))));
- }
- acc.body = block;
- }
-
- acc.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_signal (Signal! sig) {
- if (sig.error) {
- /* skip signals with errors */
- return;
- }
-
- if (add_symbol (sig.name, sig) == null) {
- return;
- }
-
- current_symbol = sig.symbol;
-
- sig.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_constructor (Constructor! c) {
- c.symbol = new Symbol (c);
- c.symbol.parent_symbol = current_symbol;
- current_symbol = c.symbol;
-
- c.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_destructor (Destructor! d) {
- d.symbol = new Symbol (d);
- d.symbol.parent_symbol = current_symbol;
- current_symbol = d.symbol;
-
- d.accept_children (this);
-
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_try_statement (TryStatement! stmt) {
- stmt.accept_children (this);
- }
-
- public override void visit_catch_clause (CatchClause! clause) {
- clause.accept_children (this);
- }
-
- public override void visit_begin_block (Block! b) {
- b.symbol = new Symbol (b);
- b.symbol.parent_symbol = current_symbol;
- current_symbol = b.symbol;
- }
-
- public override void visit_end_block (Block! b) {
- current_symbol = current_symbol.parent_symbol;
- }
-
- public override void visit_type_parameter (TypeParameter! p) {
- add_symbol (p.name, p);
- }
-}
-
diff --git a/vala/valasymbolresolver.vala b/vala/valasymbolresolver.vala
index 2b90d628d..379ebeb84 100644
--- a/vala/valasymbolresolver.vala
+++ b/vala/valasymbolresolver.vala
@@ -27,7 +27,7 @@ using GLib;
*/
public class Vala.SymbolResolver : CodeVisitor {
Symbol root_symbol;
- Symbol current_scope;
+ Scope current_scope;
List<weak NamespaceReference> current_using_directives;
Class object_class;
@@ -39,12 +39,12 @@ public class Vala.SymbolResolver : CodeVisitor {
*/
public void resolve (CodeContext! context) {
root_symbol = context.root;
- current_scope = root_symbol;
+ current_scope = root_symbol.scope;
// TODO: don't require GLib namespace in symbol resolver
- var glib_ns = root_symbol.lookup ("GLib");
+ var glib_ns = root_symbol.scope.lookup ("GLib");
if (glib_ns != null) {
- object_class = (Class) glib_ns.lookup ("Object").node;
+ object_class = (Class) glib_ns.scope.lookup ("Object");
}
context.accept (this);
@@ -52,7 +52,7 @@ public class Vala.SymbolResolver : CodeVisitor {
public override void visit_source_file (SourceFile! file) {
current_using_directives = file.get_using_directives ();
- current_scope = root_symbol;
+ current_scope = root_symbol.scope;
file.accept_children (this);
@@ -60,14 +60,14 @@ public class Vala.SymbolResolver : CodeVisitor {
}
public override void visit_class (Class! cl) {
- current_scope = cl.symbol;
+ current_scope = cl.scope;
cl.accept_children (this);
foreach (TypeReference type in cl.get_base_types ()) {
if (type.data_type is Class) {
if (cl.base_class != null) {
- Report.error (type.source_reference, "%s: Classes cannot have multiple base classes (`%s' and `%s')".printf (cl.symbol.get_full_name (), cl.base_class.symbol.get_full_name (), type.data_type.symbol.get_full_name ()));
+ Report.error (type.source_reference, "%s: Classes cannot have multiple base classes (`%s' and `%s')".printf (cl.get_full_name (), cl.base_class.get_full_name (), type.data_type.get_full_name ()));
return;
}
cl.base_class = (Class) type.data_type;
@@ -80,51 +80,61 @@ public class Vala.SymbolResolver : CodeVisitor {
cl.base_class = object_class;
}
- current_scope = current_scope.parent_symbol;
+ current_scope = current_scope.parent_scope;
}
public override void visit_struct (Struct! st) {
- current_scope = st.symbol;
+ current_scope = st.scope;
st.accept_children (this);
- current_scope = current_scope.parent_symbol;
+ current_scope = current_scope.parent_scope;
}
public override void visit_interface (Interface! iface) {
- current_scope = iface.symbol;
+ current_scope = iface.scope;
iface.accept_children (this);
- current_scope = current_scope.parent_symbol;
+ current_scope = current_scope.parent_scope;
}
public override void visit_enum (Enum! en) {
- current_scope = en.symbol;
+ current_scope = en.scope;
en.accept_children (this);
- current_scope = current_scope.parent_symbol;
+ current_scope = current_scope.parent_scope;
}
public override void visit_callback (Callback! cb) {
- current_scope = cb.symbol;
+ current_scope = cb.scope;
cb.accept_children (this);
- current_scope = current_scope.parent_symbol;
+ current_scope = current_scope.parent_scope;
}
public override void visit_constant (Constant! c) {
+ current_scope = c.scope;
+
c.accept_children (this);
}
public override void visit_field (Field! f) {
+ current_scope = f.scope;
+
f.accept_children (this);
+
+ current_scope = current_scope.parent_scope;
}
public override void visit_method (Method! m) {
+ current_scope = m.scope;
+
m.accept_children (this);
+
+ current_scope = current_scope.parent_scope;
}
public override void visit_creation_method (CreationMethod! m) {
@@ -173,11 +183,11 @@ public class Vala.SymbolResolver : CodeVisitor {
if (type.namespace_name == null) {
Symbol sym = null;
- Symbol scope = current_scope;
+ Scope scope = current_scope;
while (sym == null && scope != null) {
sym = scope.lookup (type.type_name);
- scope = scope.parent_symbol;
- if (sym != null && !(sym.node is DataType) && !(sym.node is TypeParameter)) {
+ scope = scope.parent_scope;
+ if (sym != null && !(sym is DataType) && !(sym is TypeParameter)) {
// ignore non-type symbols
sym = null;
}
@@ -188,7 +198,7 @@ public class Vala.SymbolResolver : CodeVisitor {
continue;
}
- var local_sym = ns.namespace_symbol.lookup (type.type_name);
+ var local_sym = ns.namespace_symbol.scope.lookup (type.type_name);
if (local_sym != null) {
if (sym != null) {
Report.error (type.source_reference, "`%s' is an ambiguous reference between `%s' and `%s'".printf (type.type_name, sym.get_full_name (), local_sym.get_full_name ()));
@@ -202,25 +212,25 @@ public class Vala.SymbolResolver : CodeVisitor {
Report.error (type.source_reference, "The type name `%s' could not be found".printf (type.type_name));
return;
}
- if (sym.node is TypeParameter) {
- type.type_parameter = (TypeParameter) sym.node;
+ if (sym is TypeParameter) {
+ type.type_parameter = (TypeParameter) sym;
} else {
- type.data_type = (DataType) sym.node;
+ type.data_type = (DataType) sym;
}
} else {
- var ns_symbol = root_symbol.lookup (type.namespace_name);
+ var ns_symbol = root_symbol.scope.lookup (type.namespace_name);
if (ns_symbol == null) {
type.error = true;
Report.error (type.source_reference, "The namespace name `%s' could not be found".printf (type.namespace_name));
return;
}
- var sym = ns_symbol.lookup (type.type_name);
+ var sym = ns_symbol.scope.lookup (type.type_name);
if (sym == null) {
Report.error (type.source_reference, "The type name `%s' does not exist in the namespace `%s'".printf (type.type_name, type.namespace_name));
return;
}
- type.data_type = (DataType) sym.node;
+ type.data_type = (DataType) sym;
}
if (type.pointer_level > 0) {
diff --git a/vala/valathrowstatement.vala b/vala/valathrowstatement.vala
index f89854e67..079550162 100644
--- a/vala/valathrowstatement.vala
+++ b/vala/valathrowstatement.vala
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a throw statement in the source code.
*/
-public class Vala.ThrowStatement : Statement {
+public class Vala.ThrowStatement : CodeNode, Statement {
/**
* The error expression to throw.
*/
diff --git a/vala/valatrystatement.vala b/vala/valatrystatement.vala
index 3e25a4911..dca02eca2 100644
--- a/vala/valatrystatement.vala
+++ b/vala/valatrystatement.vala
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a try statement in the source code.
*/
-public class Vala.TryStatement : Statement {
+public class Vala.TryStatement : CodeNode, Statement {
/**
* Specifies the body of the try statement.
*/
diff --git a/vala/valatypeparameter.vala b/vala/valatypeparameter.vala
index 46d1f35aa..bf73bb484 100644
--- a/vala/valatypeparameter.vala
+++ b/vala/valatypeparameter.vala
@@ -25,12 +25,7 @@ using GLib;
/**
* Represents a generic type parameter in the source code.
*/
-public class Vala.TypeParameter : CodeNode {
- /**
- * The parameter name.
- */
- public string! name { get; set construct; }
-
+public class Vala.TypeParameter : Symbol {
/**
* The generic type declaring this parameter.
*/
@@ -67,14 +62,12 @@ public class Vala.TypeParameter : CodeNode {
if (array_type == null) {
var new_array_type = new Array.with_type_parameter (this, rank, source_reference);
- /* create a new Symbol */
- new_array_type.symbol = new Symbol (new_array_type);
- this.symbol.parent_symbol.add (new_array_type.name, new_array_type.symbol);
+ parent_symbol.scope.add (new_array_type.name, new_array_type);
/* add internal length field */
- new_array_type.symbol.add (new_array_type.get_length_field ().name, new_array_type.get_length_field ().symbol);
+ new_array_type.scope.add (new_array_type.get_length_field ().name, new_array_type.get_length_field ());
/* add internal resize method */
- new_array_type.symbol.add (new_array_type.get_resize_method ().name, new_array_type.get_resize_method ().symbol);
+ new_array_type.scope.add (new_array_type.get_resize_method ().name, new_array_type.get_resize_method ());
/* link the array type to the same source as the container type */
new_array_type.source_reference = this.source_reference;
diff --git a/vala/valatypereference.vala b/vala/valatypereference.vala
index 52371f5da..482a8493a 100644
--- a/vala/valatypereference.vala
+++ b/vala/valatypereference.vala
@@ -259,7 +259,7 @@ public class Vala.TypeReference : CodeNode {
*/
public string! to_string () {
if (data_type != null) {
- return data_type.symbol.get_full_name ();
+ return data_type.get_full_name ();
} else if (type_parameter != null) {
return type_parameter.name;
} else {
diff --git a/vala/valavariabledeclarator.vala b/vala/valavariabledeclarator.vala
index 4a3ae8197..743a4348b 100644
--- a/vala/valavariabledeclarator.vala
+++ b/vala/valavariabledeclarator.vala
@@ -25,12 +25,7 @@ using GLib;
/**
* Represents a variable declarator in the source code.
*/
-public class Vala.VariableDeclarator : CodeNode, Invokable {
- /**
- * The variable name.
- */
- public string! name { get; set construct; }
-
+public class Vala.VariableDeclarator : Symbol, Invokable {
/**
* The optional initializer expression.
*/
@@ -61,10 +56,7 @@ public class Vala.VariableDeclarator : CodeNode, Invokable {
* @param source reference to source code
* @return newly created variable declarator
*/
- public VariableDeclarator (string! _name, Expression init = null, SourceReference source = null) {
- name = _name;
- initializer = init;
- source_reference = source;
+ public VariableDeclarator (construct string! name, construct Expression initializer = null, construct SourceReference source_reference = null) {
}
public override void accept (CodeVisitor! visitor) {
diff --git a/vala/valawhilestatement.vala b/vala/valawhilestatement.vala
index ea22ea8db..496038aa4 100644
--- a/vala/valawhilestatement.vala
+++ b/vala/valawhilestatement.vala
@@ -1,6 +1,6 @@
/* valawhilestatement.vala
*
- * Copyright (C) 2006 Jürg Billeter
+ * Copyright (C) 2006-2007 Jürg Billeter
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -25,7 +25,7 @@ using GLib;
/**
* Represents a while iteration statement in the source code.
*/
-public class Vala.WhileStatement : Statement {
+public class Vala.WhileStatement : CodeNode, Statement {
/**
* Specifies the loop condition.
*/
@@ -42,7 +42,7 @@ public class Vala.WhileStatement : Statement {
/**
* Specifies the loop body.
*/
- public Statement body { get; set; }
+ public Block body { get; set; }
private Expression! _condition;
@@ -54,10 +54,7 @@ public class Vala.WhileStatement : Statement {
* @param source reference to source code
* @return newly created while statement
*/
- public WhileStatement (Expression! cond, Statement! _body, SourceReference source) {
- condition = cond;
- body = _body;
- source_reference = source;
+ public WhileStatement (construct Expression! condition, construct Block! body, construct SourceReference source_reference = null) {
}
public override void accept (CodeVisitor! visitor) {