This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: Your 'Class <Protocol>' Work
- From: David Ayers <d dot ayers at inode dot at>
- To: Ziemowit Laski <zlaski at apple dot com>
- Cc: gcc-patches at gcc dot gnu dot org
- Date: Sat, 02 Oct 2004 19:05:15 +0200
- Subject: Re: Your 'Class <Protocol>' Work
- References: <B5E59844-10B9-11D9-900A-000393673036@apple.com> <4159078B.1060306@inode.at> <4159B568.2060108@inode.at> <4159B74E.2090405@inode.at> <EEFE950A-11AF-11D9-8A9A-000393673036@apple.com> <415AF226.2050006@inode.at> <ED04F876-1252-11D9-BAE3-000393673036@apple.com> <81.223.113.201.1096495217.wm@webmail.inode.at> <DCF147A0-1280-11D9-BAE3-000393673036@apple.com> <415BFB2B.2090308@inode.at> <CF6F7415-1328-11D9-A719-000393673036@apple.com> <81.223.113.201.1096587115.wm@webmail.inode.at> <8AD84E9F-1344-11D9-A719-000393673036@apple.com> <415D1C9D.70604@inode.at> <415DA07C.2070108@inode.at> <415DBE7A.3030007@inode.at>
David Ayers wrote:
If you need more explanations, I'll have to ask you be a little patient,
and I'll try to summarize the patch again. Otherwise, I'd be glad to
know what you think.
So here is the overview of this patch:
http://gcc.gnu.org/ml/gcc-patches/2004-10/msg00084.html
It implements protocol qualified 'Class' reference for Objective-C.
It changes the formal grammar by removing the 'id' keyword which was
used for the type specifier:
id [ protocol-reference-list ]
and changes this type specifier to:
typedef-name [ protocol-reference-list ]
yet the code asserts that the provided typedef-name corresponds to
either 'id' or 'Class'. This change also allows us to remove a
workaround for the cases that 'id' actually corresponded to a
non-typedef identifier: (i.e. void foo (id id);)
lookup_method_protocol_in_list now takes either 0, 1 or 2 as the search
flag. This function searches the provided protocol list for the
selector. The search option 0 indicates that only instance methods are
searched, 1 only class methods and 2 class methods and instance methods
of protocols that have been adopted by root classes, but the class
methods take precedence. When the search is done with 2 it first
searches the class methods, just like option 1, yet if none is found it
continues to search for instance methods in protocols which have been
marked as declared by a root class. If a match is found, it emits the
proposed diagnostics that the class method prototype wasn't found, yet
it will use the instance methods prototype. Even though there is only
one call site which explicitly uses 2 as the search option, this
mechanism cannot be special cased there as l_m_p_i_l calls itself
recursively with the current search option.
-> Note: This new warning implies that protocols like <NSObject> should
repeat their instance method declarations as class methods to avoid this
warning. This also implies that when root classes adopt such protocols,
the the compiler should not warn about the class variants not being
implemented if instance variants are. I think we should leave this
until after this patch though.
objc_finish_interface has been adapted to call the new
mark_protocols_adopted_by_root_class function to mark protocols which
will be considered by lookup_method_protocol_in_list so that the
fallback mechanism to instance prototypes is not unduly invoked. For
marked protocols which where previously merely forward declared, we
register the incorporated/inherited protocols. We also register the
instance methods of the marked protocol directly with the global class
method list to avoid creating a method list merely to call
mark_protocols_adopted_by_root_class for the current protocol.
static void
mark_protocols_adopted_by_root_class (tree rprotos)
/* Iterates over the protocol interface list RPROTOS marking each as
PROTOCOL_ADOPTED_BY_ROOT_CLASS. Registers the instance methods
prototypes of each protocol and their incorporated protocols
recursively as potential class methods. */
-> Note: I'm aware that you mentioned that you do not believe this is
necessary, but after considering that this will allow us to better
differentiate the diagnostics for categories on root classes like
NSObject, also considering that few of the "root class categories"
currently repeat their instance methods as class methods and considering
the maintenance and processing overhead which I find minimal, I think it
is legitimate. If you feel very strongly about it, I would remove this
and do the extra lookup in lookup_method_protocol_in_list independent of
whether a protocol is adopted by a root class.
objc_comptypes has been adapted to handle protocol qualified 'Class'
type. For comments about the structure of the previous and new
implementation, may I refer you to about the middle of:
http://gcc.gnu.org/ml/gcc-patches/2004-09/msg03022.html
I hope that this shows that extracting the protocol comparison into the new:
static inline
int objc_comptypes_proto_proto(tree lhs, tree rhs, int reflexive)
/* Return 1 if LHS and RHS are compatible types for assignment or
various other operations. Return 0 if they are incompatible.
When the operation is REFLEXIVE (typically comparisons), check
for compatibility in either direction; when it's not (typically
assignments), don't.
This is a helper function for objc_comptypes to be able to test
two protocol qualified types of the same basic type to insure
protocol conformance and to emit the necessary warnings. */
is the least invasive approach to objc_comptypes.
-> Note: Please let me know if you agree or whether the structure I
think you wanted is indeed what you are looking for and I'll add the
special case handling inline.
Yet if you agree with this structure then please indicate whether you'd
prefer me to:
a) remove the IS_PROTOCOL_QUALIFIED_ID macro
b) add a IS_PROTOCOL_QUALIFIED_CLASS macro
c) leave the IS_PROTOCOL_QUALIFIED_ID macro untouched and handle
IS_PROTOCOL_QUALIFIED_CLASS 'inline'
d) replace IS_PROTOCOL_QUALIFIED_ID by IS_PROTOCOL_QUALIFIED_UNTYPED and
add extra IS_ID, IS_CLASS tests 'inline'.
objc_finish_method_expr has been adapted to handle protocol qualified
'Class' types. As you requested, the hack to process 'Class' as a named
class has been removed and it emits a new diagnostic "no '%c%s' method
found" when no appropriate prototype has been found. It calls
lookup_method_protocol_in_list with search option '2' for protocol
qualified 'Class' references. The other calls to
lookup_method_protocol_in_list have been updated to make the search flag
explicit.
lookup_method_static has been updated to make the search flag used for
calls to lookup_method_protocol_in_list explicit.
In some cases I've used the word 'incorporate' instead of 'inheritance'
with respect to protocols as I'm still partial to that word now. If you
feel strongly about it, I will revert that.
I offer to follow up with the identifier/naming cleanup to:
s/reflexive/symmetric/g
s/implemented by protocol/declared by protocol/g
insure that lhs and rhs identifier in objc_comptypes(_proto_proto) are
properly named.
After the branch we can go for the following issues:
- ensure that the warning "does not fully implement the '%s' protocol"
is not emitted for class methods of a protocol in a root class when an
instance variant is implemented.
- have digest_init call objc_comptypes to emit diagnostics.
- cleanup digest_init to respect lhs/rhs when calling comptypes.
- make protocol qualified types their own true types
- cleanup objc_comptypes as needed
- reactivate Alexander Malmberg's patch wrt tracking conflicting prototypes
- adding objc support to the pretty printer functions (well maybe this
should be moved up to ease doing the others :-) )
How does that sound?
Cheers,
David