1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210
|
/* Test the Modern GNU Objective-C Runtime API.
This is test 'sel', covering all functions starting with 'sel'. */
/* { dg-do run } */
/* { dg-skip-if "No API#2 pre-Darwin9" { *-*-darwin[5-8]* } { "-fnext-runtime" } { "" } } */
/* { dg-additional-options "-Wno-objc-root-class" } */
/* To get the modern GNU Objective-C Runtime API, you include
objc/runtime.h. */
#include <objc/runtime.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
@interface MyRootClass
{ Class isa; }
+ alloc;
- init;
+ initialize;
@end
@implementation MyRootClass
+ alloc { return class_createInstance (self, 0); }
- init { return self; }
+ initialize { return self; }
@end
@protocol MyProtocol
- (id) variable;
@end
@protocol MySecondProtocol
- (id) setVariable: (id)value;
@end
@interface MySubClass : MyRootClass <MyProtocol>
{ id variable_ivar; }
- (void) setVariable: (id)value;
- (id) variable;
- (void) method;
@end
@implementation MySubClass
- (void) setVariable: (id)value { variable_ivar = value; }
- (id) variable { return variable_ivar; }
- (void) method { return; }
@end
@interface ClassA : MyRootClass
- (id) conflictingSelectorMethod;
@end
@implementation ClassA
- (id) conflictingSelectorMethod { return nil; }
@end
@interface ClassB : MyRootClass
- (void) conflictingSelectorMethod;
@end
@implementation ClassB
- (void) conflictingSelectorMethod { return; }
@end
int main(int argc, void **args)
{
/* Functions are tested in alphabetical order. */
#ifdef __GNU_LIBOBJC__
printf ("Testing sel_copyTypedSelectorList ()...\n");
{
unsigned int count;
SEL * list = sel_copyTypedSelectorList ("method", &count);
/* There should only be two, since 'method' is referenced twice,
once with types and once without (in this very test). */
if (count != 2)
abort ();
/* Check that both selectors are not-NULL, and have the correct
name. We use @selector() here, which wouldn't really be
needed, just to register a second, untyped selector with name
'method'. */
if (strcmp (sel_getName (list[0]), sel_getName (@selector (method))) != 0)
abort ();
if (strcmp (sel_getName (list[1]), sel_getName (@selector (method))) != 0)
abort ();
if (list[2] != NULL)
abort ();
}
#endif
printf ("Testing sel_getName () ...\n");
{
if (strcmp (sel_getName (@selector (variable)), "variable") != 0)
abort ();
if (strcmp (sel_getName (NULL), "<null selector>") != 0)
abort ();
}
#ifdef __GNU_LIBOBJC__
printf ("Testing sel_getTypeEncoding () ...\n");
{
/* Get a selector from a real class, so it has interesting
types. */
Method method = class_getInstanceMethod (objc_getClass ("MySubClass"),
@selector (variable));
if (strcmp (sel_getTypeEncoding (method_getName (method)),
method_getTypeEncoding (method)) != 0)
abort ();
if (sel_getTypeEncoding (NULL) != NULL)
abort ();
}
#endif
#ifdef __GNU_LIBOBJC__
printf ("Testing sel_getTypedSelector () ...\n");
{
/* First try with a selector where we know that a typed one has
been registered. */
SEL selector = sel_getTypedSelector ("variable");
if (selector == NULL)
abort ();
if (sel_getTypeEncoding (selector) == NULL)
abort ();
/* Now try a selector which was never registered. */
selector = sel_getTypedSelector ("not_registered");
if (selector != NULL)
abort ();
/* Now try registering a selector with no types. The following
line is just a way to have an unused '@selector()' expression
without the compiler complaining. */
if (@selector (registered_with_no_types) == NULL)
abort ();
/* Try getting it. Nothing should be returned because it is
untyped. */
selector = sel_getTypedSelector ("registered_with_no_types");
if (selector != NULL)
abort ();
/* Now try a selector with multiple, conflicting types. NULL
should be returned. */
selector = sel_getTypedSelector ("conflictingSelectorMethod");
if (selector != NULL)
abort ();
}
#endif
printf ("Testing sel_getUid () ...\n");
{
if (strcmp (sel_getName (sel_getUid ("myMethod")), "myMethod") != 0)
abort ();
if (sel_getUid (NULL) != NULL)
abort ();
}
printf ("Testing sel_isEqual () ...\n");
{
if (! sel_isEqual (@selector (setVariable:), @selector (setVariable:)))
abort ();
}
printf ("Testing sel_registerName () ...\n");
{
if (strcmp (sel_getName (sel_registerName ("myMethod")), "myMethod") != 0)
abort ();
if (sel_registerName (NULL) != NULL)
abort ();
}
#ifdef __GNU_LIBOBJC__
printf ("Testing set_registerTypedName () ...\n");
{
const char *types = method_getTypeEncoding (class_getInstanceMethod
(objc_getClass ("MySubClass"),
@selector (variable)));
SEL selector = sel_registerTypedName ("aMethod", types);
if (strcmp (sel_getName (selector), "aMethod") != 0)
abort ();
if (strcmp (sel_getTypeEncoding (selector), types) != 0)
abort ();
if (sel_registerTypedName (NULL, NULL) != NULL)
abort ();
if (sel_registerTypedName (NULL, types) != NULL)
abort ();
}
#endif
return 0;
}
|