1 // TEST_CFLAGS -framework Foundation
2 // need Foundation to get NSObject compatibility additions for class Protocol
3 // because ARC calls [protocol retain]
6 .*protocol_copyPropertyList.m:\d+:\d+: warning: null passed to a callee that requires a non-null argument \[-Wnonnull\]
7 .*protocol_copyPropertyList.m:\d+:\d+: warning: null passed to a callee that requires a non-null argument \[-Wnonnull\]
8 .*protocol_copyPropertyList.m:\d+:\d+: warning: null passed to a callee that requires a non-null argument \[-Wnonnull\]
9 .*protocol_copyPropertyList.m:\d+:\d+: warning: null passed to a callee that requires a non-null argument \[-Wnonnull\]
15 #include <malloc/malloc.h>
16 #include <objc/runtime.h>
21 @property(class) int prop1;
22 @property(class) int prop2;
25 @protocol SubProps <SuperProps>
28 @property(class) int prop3;
29 @property(class) int prop4;
39 @property(class) int prop1;
40 @property(class) int prop2;
41 @property(class) int prop3;
42 @property(class) int prop4;
45 @protocol NoProps @end
48 @property int instanceProp;
49 @property(class) int classProp;
53 static int isNamed(objc_property_t p, const char *name)
55 return (0 == strcmp(name, property_getName(p)));
58 void testfn(objc_property_t *(*copyPropertyList_fn)(Protocol*, unsigned int *),
59 const char *onePropName)
61 objc_property_t *props;
65 proto = @protocol(SubProps);
69 props = copyPropertyList_fn(proto, &count);
71 testassert(count == 2);
72 testassert((isNamed(props[0], "prop4") && isNamed(props[1], "prop3")) ||
73 (isNamed(props[0], "prop3") && isNamed(props[1], "prop4")));
74 // props[] should be null-terminated
75 testassert(props[2] == NULL);
78 proto = @protocol(SuperProps);
82 props = copyPropertyList_fn(proto, &count);
84 testassert(count == 2);
85 testassert((isNamed(props[0], "prop1") && isNamed(props[1], "prop2")) ||
86 (isNamed(props[0], "prop2") && isNamed(props[1], "prop1")));
87 // props[] should be null-terminated
88 testassert(props[2] == NULL);
91 // Check null-termination - this property list block would be 16 bytes
92 // if it weren't for the terminator
93 proto = @protocol(FourProps);
97 props = copyPropertyList_fn(proto, &count);
99 testassert(count == 4);
100 testassert(malloc_size(props) >= 5 * sizeof(objc_property_t));
101 testassert(props[3] != NULL);
102 testassert(props[4] == NULL);
105 // Check NULL count parameter
106 props = copyPropertyList_fn(proto, NULL);
108 testassert(props[4] == NULL);
109 testassert(props[3] != NULL);
112 // Check NULL protocol parameter
114 props = copyPropertyList_fn(NULL, &count);
116 testassert(count == 0);
118 // Check NULL protocol and count
119 props = copyPropertyList_fn(NULL, NULL);
122 // Check protocol with no properties
123 proto = @protocol(NoProps);
127 props = copyPropertyList_fn(proto, &count);
129 testassert(count == 0);
131 // Check instance vs class properties
132 proto = @protocol(OneProp);
136 props = copyPropertyList_fn(proto, &count);
138 testassert(count == 1);
139 testassert(0 == strcmp(property_getName(props[0]), onePropName));
143 objc_property_t *protocol_copyPropertyList2_YES_YES(Protocol *proto, unsigned int *outCount)
145 return protocol_copyPropertyList2(proto, outCount, YES, YES);
148 objc_property_t *protocol_copyPropertyList2_YES_NO(Protocol *proto, unsigned int *outCount)
150 return protocol_copyPropertyList2(proto, outCount, YES, NO);
155 // protocol_copyPropertyList(...) is identical to
156 // protocol_copyPropertyList2(..., YES, YES)
157 testfn(protocol_copyPropertyList, "instanceProp");
158 testfn(protocol_copyPropertyList2_YES_YES, "instanceProp");
160 // protocol_copyPropertyList2(..., YES, NO) is also identical
161 // with the protocol definitions above, except for protocol OneProp.
162 testfn(protocol_copyPropertyList2_YES_NO, "classProp");
164 // Check non-functionality of optional properties
167 objc_property_t *props;
170 props = protocol_copyPropertyList2(@protocol(FourProps), &count, NO, YES);
172 testassert(count == 0);
175 props = protocol_copyPropertyList2(@protocol(FourProps), &count, NO, NO);
177 testassert(count == 0);
179 // Check nil count parameter
180 props = protocol_copyPropertyList2(@protocol(FourProps), nil, NO, YES);
183 props = protocol_copyPropertyList2(@protocol(FourProps), nil, NO, NO);
186 // Check nil protocol parameter
188 props = protocol_copyPropertyList2(nil, &count, NO, YES);
190 testassert(count == 0);
193 props = protocol_copyPropertyList2(nil, &count, NO, NO);
195 testassert(count == 0);
197 // Check nil protocol and count
198 props = protocol_copyPropertyList2(nil, nil, NO, YES);
201 props = protocol_copyPropertyList2(nil, nil, NO, NO);