diff options
author | Iain Sandoe <iains@gcc.gnu.org> | 2010-09-30 16:51:00 +0000 |
---|---|---|
committer | Iain Sandoe <iains@gcc.gnu.org> | 2010-09-30 16:51:00 +0000 |
commit | 92902b1bafff14a118ef08dc323dfdc12b2a63ae (patch) | |
tree | 42ebcaff8a7ee59b29d662bbc60c7b6727371ef5 /gcc/objc/objc-act.c | |
parent | 0eeccfa3ff890e75c4db2375262c2484de62f475 (diff) | |
download | gcc-92902b1bafff14a118ef08dc323dfdc12b2a63ae.zip gcc-92902b1bafff14a118ef08dc323dfdc12b2a63ae.tar.gz gcc-92902b1bafff14a118ef08dc323dfdc12b2a63ae.tar.bz2 |
add @optional/@required to prto lists
add @optional/@required to prto lists
gcc:
* c-parser.c (c_parser_objc_methodprotolist): Amend preceding comment,
parse @optional/@required and set the flags as appropriate.
gcc/c-family:
* c-common.c: Add two new entries for @optional
and @required keywords.
merge from FSF 'apple/trunk' branch.
2006-01-30 Fariborz Jahanian <fjahanian@apple.com>
Radar 4386773
* c-common.h (RID_AT_OPTIONAL, RID_AT_REQUIRED): Two new
objective-c keywords.
(objc_set_method_opt): New declaration.
* stub-objc.c (objc_set_method_opt): New stub.
gcc/cp:
merge from FSF 'apple/trunk' branch.
2006-01-30 Fariborz Jahanian <fjahanian@apple.com>
Radar 4386773
* cp/parser.c (cp_parser_objc_interstitial_code): For
@optional/@required set the optional/required flag.
gcc/objc:
merge from FSF 'apple/trunk' branch.
2006-01-30 Fariborz Jahanian <fjahanian@apple.com>
Radar 4386773
* objc/objc-act.c (objc_set_method_opt): New function.
(objc_start_protocol, objc_finish_interface): Reset
objc_method_optional_flag flag.
(objc_add_method_declaration): Pass on the new
flag to objc_add_method.
(objc_add_method): Add optional methods to new chain in
the protocol class.
* objc/objc-act.h (CLASS_OPTIONAL_CLS_METHODS,
CLASS_OPTIONAL_NST_METHODS): New macros accessing a protocol
class's optional method chains.
testsuite:
merge from FSF 'apple/trunk' branch.
2006-01-30 Fariborz Jahanian <fjahanian@apple.com>
Radar 4386773
* objc.dg/enhanced-proto-1.m: New.
* objc.dg/enhanced-proto-2.m: New.
* obj-c++.dg/enhanced-proto-1.mm: New
* obj-c++.dg/enhanced-proto-2.mm: New.
From-SVN: r164754
Diffstat (limited to 'gcc/objc/objc-act.c')
-rw-r--r-- | gcc/objc/objc-act.c | 54 |
1 files changed, 48 insertions, 6 deletions
diff --git a/gcc/objc/objc-act.c b/gcc/objc/objc-act.c index 934d78d..dffdb71 100644 --- a/gcc/objc/objc-act.c +++ b/gcc/objc/objc-act.c @@ -146,7 +146,7 @@ static void objc_start_function (tree, tree, tree, struct c_arg_info *); #endif static tree start_protocol (enum tree_code, tree, tree); static tree build_method_decl (enum tree_code, tree, tree, tree, bool); -static tree objc_add_method (tree, tree, int); +static tree objc_add_method (tree, tree, int, bool); static tree add_instance_variable (tree, int, tree); static tree build_ivar_reference (tree); static tree is_ivar (tree, tree); @@ -352,6 +352,10 @@ int objc_public_flag; /* Use to generate method labels. */ static int method_slot = 0; +/* Flag to say whether methods in a protocol are optional or + required. */ +static bool objc_method_optional_flag = false; + static int objc_collecting_ivars = 0; #define BUFSIZE 1024 @@ -687,6 +691,7 @@ objc_start_protocol (tree name, tree protos, tree attributes) " of the compiler, (ignored)"); objc_interface_context = start_protocol (PROTOCOL_INTERFACE_TYPE, name, protos); + objc_method_optional_flag = false; } void @@ -701,6 +706,7 @@ objc_finish_interface (void) { finish_class (objc_interface_context); objc_interface_context = NULL_TREE; + objc_method_optional_flag = false; } void @@ -753,6 +759,18 @@ objc_set_visibility (int visibility) } void +objc_set_method_opt (bool optional) +{ + objc_method_optional_flag = optional; + if (!objc_interface_context + || TREE_CODE (objc_interface_context) != PROTOCOL_INTERFACE_TYPE) + { + error ("@optional/@required is allowed in @protocol context only."); + objc_method_optional_flag = false; + } +} + +void objc_set_method_type (enum tree_code type) { objc_inherit_code = (type == PLUS_EXPR @@ -787,7 +805,8 @@ objc_add_method_declaration (tree decl, tree attributes) objc_add_method (objc_interface_context, decl, - objc_inherit_code == CLASS_METHOD_DECL); + objc_inherit_code == CLASS_METHOD_DECL, + objc_method_optional_flag); } /* Return 'true' if the method definition could be started, and @@ -816,7 +835,8 @@ objc_start_method_definition (tree decl, tree attributes) objc_add_method (objc_implementation_context, decl, - objc_inherit_code == CLASS_METHOD_DECL); + objc_inherit_code == CLASS_METHOD_DECL, + /* is optional */ false); start_method_def (decl); return true; } @@ -7073,11 +7093,32 @@ add_method_to_hash_list (hash *hash_list, tree method) } static tree -objc_add_method (tree klass, tree method, int is_class) +objc_add_method (tree klass, tree method, int is_class, bool is_optional) { tree mth; - if (!(mth = lookup_method (is_class + /* @optional methods are added to protocol's OPTIONAL list */ + if (is_optional) + { + gcc_assert (TREE_CODE (klass) == PROTOCOL_INTERFACE_TYPE); + if (!(mth = lookup_method (is_class + ? PROTOCOL_OPTIONAL_CLS_METHODS (klass) + : PROTOCOL_OPTIONAL_NST_METHODS (klass), + method))) + { + if (is_class) + { + TREE_CHAIN (method) = PROTOCOL_OPTIONAL_CLS_METHODS (klass); + PROTOCOL_OPTIONAL_CLS_METHODS (klass) = method; + } + else + { + TREE_CHAIN (method) = PROTOCOL_OPTIONAL_NST_METHODS (klass); + PROTOCOL_OPTIONAL_NST_METHODS (klass) = method; + } + } + } + else if (!(mth = lookup_method (is_class ? CLASS_CLS_METHODS (klass) : CLASS_NST_METHODS (klass), method))) { @@ -9064,7 +9105,8 @@ really_start_method (tree method, if (interface) objc_add_method (interface, copy_node (method), - TREE_CODE (method) == CLASS_METHOD_DECL); + TREE_CODE (method) == CLASS_METHOD_DECL, + /* is_optional= */ false); } } } |