Attempt to link in ObjC2 compatibility code if we have an older runtime.

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@29670 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
rfm 2010-02-19 12:51:02 +00:00
parent d605c6f7b5
commit 97e7df0ac3
11 changed files with 1246 additions and 863 deletions

View file

@ -1,3 +1,18 @@
2010-02-19 Richard Frith-Macdonald <rfm@gnu.org>
* configure.ac: Add check for ObjC2 support in runtime.
* config.mak.in: define OBJC2RUNTIME to yes or no
* configure: regenerate
* Source/GNUmakefile: Build/link ObjectiveC2 compat code if needed
* Source/ObjectiveC2/Availability.h:
* Source/ObjectiveC2/runtime.c:
* Source/ObjectiveC2/GNUmakefile:
* Source/ObjectiveC2/properties.m:
* Source/ObjectiveC2/sync.m:
* Source/ObjectiveC2/blocks_runtime.m:
Attempt to build in ObjectiveC2 compatibility functions when we don't
have an ObjC2 runtime.
2010-02-19 Richard Frith-Macdonald <rfm@gnu.org>
Simplify header imports with common headers handled in the correct

View file

@ -65,8 +65,13 @@ ifneq ($(base),no)
LIBRARY_NAME += libgnustep-base
endif
libgnustep-base_SUBPROJECTS = Additions
libgnustep-baseadd_SUBPROJECTS = Additions
ifeq ($(OBJC2RUNTIME),no)
libgnustep-base_SUBPROJECTS = ObjectiveC2
libgnustep-baseadd_SUBPROJECTS += Additions
endif
libgnustep-base_SUBPROJECTS += Additions
libgnustep-baseadd_SUBPROJECTS += Additions
ifeq ($(GNUSTEP_TARGET_OS), mingw32)
libgnustep-base_SUBPROJECTS+=win32
@ -473,7 +478,10 @@ libgnustep-baseadd_NEEDS_GUI = NO
# build Additions as a subproject, causing concurrency issues). If it
# can be guaranteed that they'll never be built together, this could
# be removed.
SUBPROJECTS = Additions
ifeq ($(OBJC2RUNTIME),no)
SUBPROJECTS = ObjectiveC2
endif
SUBPROJECTS += Additions
-include Makefile.preamble

View file

@ -0,0 +1,12 @@
#ifdef STRICT_MACOS_X
# define OBJC_NONPORTABLE __attribute__((error("Function not supported by the Apple runtime")))
#else
# define OBJC_NONPORTABLE
#endif
#if !defined(__DEPRECATE_DIRECT_ACCESS) || defined(__OBJC_LEGACY_GNU_MODE__) || defined(__OBJC_RUNTIME_INTERNAL__)
# define OBJC_DEPRECATED
#else
# define OBJC_DEPRECATED __attribute__((deprecated))
#endif

View file

@ -1,22 +1,41 @@
#
# src makefile for the GNUstep Base Library
#
# Copyright (C) 2010 Free Software Foundation, Inc.
#
# Written by: Richard Frith-Macdonald <rfm@gnu.org>
#
# This file is part of the GNUstep Base Library.
#
# 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
# Library 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 02111 USA.
#
PACKAGE_NAME = gnustep-base
GNUSTEP_LOCAL_ADDITIONAL_MAKEFILES=../../base.make
include $(GNUSTEP_MAKEFILES)/common.make
include ../../config.mak
#
# Application
#
VERSION = 0.1
FRAMEWORK_NAME = ObjectiveC2
#
# Resource files
#
ObjectiveC2_LANGUAGES = English
SUBPROJECT_NAME = ObjectiveC2
ObjectiveC2_OBJC_FILES = \
blocks_runtime.m\
properties.m\
sync.m
ObjectiveC2_C_FILES = \
runtime.c
@ -25,9 +44,6 @@ ObjectiveC2_HEADER_FILES = \
blocks_runtime.h\
runtime.h
ADDITIONAL_CFLAGS = -std=c99 -fexceptions
ADDITIONAL_OBJCFLAGS = -fobjc-exceptions -fexceptions
ifeq ($(CC), clang)
ADDITIONAL_OBJCFLAGS = -fblocks
endif
@ -35,7 +51,9 @@ ifeq ($(GNUSTEP_TARGET_CPU), ix86)
ADDITIONAL_OBJCFLAGS += -march=i686
endif
ObjectiveC2_OBJCFLAGS += -std=c99
-include Makefile.preamble
include $(GNUSTEP_MAKEFILES)/subproject.make
-include Makefile.postamble
include $(GNUSTEP_MAKEFILES)/framework.make
-include ../../etoile.make

View file

@ -23,8 +23,8 @@
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
* OTHER DEALINGS IN THE SOFTWARE.
*/
#import "objc/blocks_runtime.h"
#import "objc/runtime.h"
#import "blocks_runtime.h"
#import "runtime.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
@ -88,16 +88,17 @@ struct psy_block_byref_obj {
* the other choices which are mutually exclusive. Only in a Block copy helper
* will one see BLOCK_FIELD_IS_BYREF.
*/
void _Block_object_assign(void *destAddr, void *object, const int flags)
void
_Block_object_assign(void *destAddr, void *object, const int flags)
{
//printf("Copying %x to %x with flags %x\n", object, destAddr, flags);
// FIXME: Needs to be implemented
if(flags & BLOCK_FIELD_IS_WEAK)
if (flags & BLOCK_FIELD_IS_WEAK)
{
}
else
{
if(flags & BLOCK_FIELD_IS_BYREF)
if (flags & BLOCK_FIELD_IS_BYREF)
{
struct psy_block_byref_obj *src = object;
struct psy_block_byref_obj **dst = destAddr;
@ -106,7 +107,7 @@ void _Block_object_assign(void *destAddr, void *object, const int flags)
* represent the refcount but it still contains real flag, so this
* is a little hack...
*/
if((src->flags & ~BLOCK_HAS_COPY_DISPOSE) == 0)
if ((src->flags & ~BLOCK_HAS_COPY_DISPOSE) == 0)
{
*dst = malloc(src->size);
memcpy(*dst, src, src->size);
@ -114,26 +115,30 @@ void _Block_object_assign(void *destAddr, void *object, const int flags)
{
(*dst)->forwarding = *dst;
}
if(src->size >= sizeof(struct psy_block_byref_obj))
if (src->size >= sizeof(struct psy_block_byref_obj))
{
src->byref_keep(*dst, src);
}
}
else *dst = src;
else
{
*dst = src;
}
(*dst)->flags++;
}
else if((flags & BLOCK_FIELD_IS_BLOCK) == BLOCK_FIELD_IS_BLOCK)
else if ((flags & BLOCK_FIELD_IS_BLOCK) == BLOCK_FIELD_IS_BLOCK)
{
struct psy_block_literal *src = object;
struct psy_block_literal **dst = destAddr;
*dst = Block_copy(src);
}
else if((flags & BLOCK_FIELD_IS_OBJECT) == BLOCK_FIELD_IS_OBJECT)
else if ((flags & BLOCK_FIELD_IS_OBJECT) == BLOCK_FIELD_IS_OBJECT)
{
id src = object;
id *dst = destAddr;
*dst = [src retain];
}
}
@ -145,33 +150,34 @@ void _Block_object_assign(void *destAddr, void *object, const int flags)
* The same flags used in the copy helper should be used for each call
* generated to this function:
*/
void _Block_object_dispose(void *object, const int flags)
void
_Block_object_dispose(void *object, const int flags)
{
// FIXME: Needs to be implemented
if(flags & BLOCK_FIELD_IS_WEAK)
if (flags & BLOCK_FIELD_IS_WEAK)
{
}
else
{
if(flags & BLOCK_FIELD_IS_BYREF)
if (flags & BLOCK_FIELD_IS_BYREF)
{
struct psy_block_byref_obj *src = object;
src->flags--;
if((src->flags & ~BLOCK_HAS_COPY_DISPOSE) == 0)
if ((src->flags & ~BLOCK_HAS_COPY_DISPOSE) == 0)
{
if(src->size >= sizeof(struct psy_block_byref_obj))
if (src->size >= sizeof(struct psy_block_byref_obj))
src->byref_dispose(src);
free(src);
}
}
else if((flags & ~BLOCK_BYREF_CALLER) == BLOCK_FIELD_IS_BLOCK)
else if ((flags & ~BLOCK_BYREF_CALLER) == BLOCK_FIELD_IS_BLOCK)
{
struct psy_block_literal *src = object;
Block_release(src);
}
else if((flags & ~BLOCK_BYREF_CALLER) == BLOCK_FIELD_IS_OBJECT)
else if ((flags & ~BLOCK_BYREF_CALLER) == BLOCK_FIELD_IS_OBJECT)
{
id src = object;
[src release];
@ -195,8 +201,11 @@ struct StackBlockClass {
};
// Copy a block to the heap if it's still on the stack or increments its retain count.
void *_Block_copy(void *src)
/* Copy a block to the heap if it's still on the stack or
* increments its retain count.
*/
void *
_Block_copy(void *src)
{
struct StackBlockClass *self = src;
struct StackBlockClass *ret = self;
@ -204,13 +213,14 @@ void *_Block_copy(void *src)
extern void _NSConcreteStackBlock __attribute__((weak));
// If the block is Global, there's no need to copy it on the heap.
if(self->isa == &_NSConcreteStackBlock && self->flags & BLOCK_HAS_DESCRIPTOR)
if (self->isa == &_NSConcreteStackBlock
&& self->flags & BLOCK_HAS_DESCRIPTOR)
{
if(self->reserved == 0)
if (self->reserved == 0)
{
ret = malloc(self->descriptor->size);
memcpy(ret, self, self->descriptor->size);
if(self->flags & BLOCK_HAS_COPY_DISPOSE)
if (self->flags & BLOCK_HAS_COPY_DISPOSE)
self->descriptor->copy_helper(ret, self);
memcpy(self, ret, self->descriptor->size);
}
@ -220,27 +230,32 @@ void *_Block_copy(void *src)
}
// Release a block and frees the memory when the retain count hits zero.
void _Block_release(void *src)
void
_Block_release(void *src)
{
struct StackBlockClass *self = src;
extern void _NSConcreteStackBlock __attribute__((weak));
if(self->isa == &_NSConcreteStackBlock && // A Global block doesn't need to be released
self->flags & BLOCK_HAS_DESCRIPTOR && // Should always be true...
self->reserved > 0) // If false, then it's not allocated on the heap, we won't release auto memory !
if (self->isa == &_NSConcreteStackBlock
// A Global block doesn't need to be released
&& self->flags & BLOCK_HAS_DESCRIPTOR
// Should always be true...
&& self->reserved > 0)
// If false, then it's not allocated on the heap, we won't release auto memory !
{
self->reserved--;
if(self->reserved == 0)
if (self->reserved == 0)
{
if(self->flags & BLOCK_HAS_COPY_DISPOSE)
if (self->flags & BLOCK_HAS_COPY_DISPOSE)
self->descriptor->dispose_helper(self);
free(self);
}
}
}
const char *_Block_get_types(void *blk)
const char *
_Block_get_types(void *blk)
{
struct psy_block_literal *block = blk;
return block->types;

View file

@ -8,25 +8,36 @@
- (void)release;
@end
id objc_getProperty(id obj, SEL _cmd, ptrdiff_t offset, BOOL isAtomic)
id
objc_getProperty(id obj, SEL _cmd, ptrdiff_t offset, BOOL isAtomic)
{
char *addr;
id ret;
if (isAtomic)
{
@synchronized(obj) {
@synchronized(obj)
{
return objc_getProperty(obj, _cmd, offset, NO);
}
}
char *addr = (char*)obj;
addr = (char*)obj;
addr += offset;
id ret = *(id*)addr;
ret = *(id*)addr;
return [[ret retain] autorelease];
}
void objc_setProperty(id obj, SEL _cmd, ptrdiff_t offset, id arg, BOOL isAtomic, BOOL isCopy)
void
objc_setProperty(id obj, SEL _cmd, ptrdiff_t offset, id arg, BOOL isAtomic,
BOOL isCopy)
{
char *addr;
id old;
if (isAtomic)
{
@synchronized(obj) {
@synchronized(obj)
{
objc_setProperty(obj, _cmd, offset, arg, NO, isCopy);
return;
}
@ -39,9 +50,9 @@ void objc_setProperty(id obj, SEL _cmd, ptrdiff_t offset, id arg, BOOL isAtomic,
{
arg = [arg retain];
}
char *addr = (char*)obj;
addr = (char*)obj;
addr += offset;
id old = *(id*)addr;
old = *(id*)addr;
*(id*)addr = arg;
[old release];
}

View file

@ -82,21 +82,26 @@ extern objc_mutex_t __objc_runtime_mutex;
* Looks up the instance method in a specific class, without recursing into
* superclasses.
*/
static Method class_getInstanceMethodNonrecursive(Class aClass, SEL aSelector)
static Method
class_getInstanceMethodNonrecursive(Class aClass, SEL aSelector)
{
struct objc_method_list *methods;
const char *name = sel_get_name(aSelector);
const char *types = sel_get_type(aSelector);
for (struct objc_method_list *methods = aClass->methods;
methods != NULL ; methods = methods->method_next)
for (methods = aClass->methods;
methods != NULL; methods = methods->method_next)
{
for (int i=0 ; i<methods->method_count ; i++)
int i;
for (i = 0; i < methods->method_count; i++)
{
Method_t method = &methods->method_list[i];
if (strcmp(sel_get_name(method->method_name), name) == 0)
{
if (NULL == types ||
strcmp(types, method->method_types) == 0)
if (NULL == types
|| strcmp(types, method->method_types) == 0)
{
return method;
}
@ -109,11 +114,13 @@ static Method class_getInstanceMethodNonrecursive(Class aClass, SEL aSelector)
return NULL;
}
static void objc_updateDtableForClassContainingMethod(Method m)
static void
objc_updateDtableForClassContainingMethod(Method m)
{
Class nextClass = Nil;
void *state;
SEL sel = method_getName(m);
while (Nil != (nextClass = objc_next_class(&state)))
{
if (class_getInstanceMethodNonrecursive(nextClass, sel) == m)
@ -125,20 +132,27 @@ static void objc_updateDtableForClassContainingMethod(Method m)
}
BOOL class_addIvar(Class cls,
BOOL
class_addIvar(Class cls,
const char *name,
size_t size,
uint8_t alignment,
const char *types)
{
struct objc_ivar_list *ivarlist;
Ivar ivar;
if (CLS_ISRESOLV(cls) || CLS_ISMETA(cls))
{
return NO;
}
struct objc_ivar_list *ivarlist = cls->ivars;
if (class_getInstanceVariable(cls, name) != NULL)
{
return NO;
}
if (class_getInstanceVariable(cls, name) != NULL) { return NO; }
ivarlist = cls->ivars;
if (NULL == ivarlist)
{
@ -153,7 +167,7 @@ BOOL class_addIvar(Class cls,
+ (ivarlist->ivar_count - 1) * sizeof(struct objc_ivar));
}
Ivar ivar = &cls->ivars->ivar_list[cls->ivars->ivar_count - 1];
ivar = &cls->ivars->ivar_list[cls->ivars->ivar_count - 1];
ivar->ivar_name = strdup(name);
ivar->ivar_type = strdup(types);
// Round up the offset of the ivar so it is correctly aligned.
@ -163,15 +177,20 @@ BOOL class_addIvar(Class cls,
return YES;
}
BOOL class_addMethod(Class cls, SEL name, IMP imp, const char *types)
BOOL
class_addMethod(Class cls, SEL name, IMP imp, const char *types)
{
const char *methodName = sel_get_name(name);
struct objc_method_list *methods;
for (methods=cls->methods; methods!=NULL ; methods=methods->method_next)
for (methods = cls->methods; methods != NULL; methods = methods->method_next)
{
for (int i=0 ; i<methods->method_count ; i++)
int i;
for (i = 0; i < methods->method_count; i++)
{
Method_t method = &methods->method_list[i];
if (strcmp(sel_get_name(method->method_name), methodName) == 0)
{
return NO;
@ -184,7 +203,8 @@ BOOL class_addMethod(Class cls, SEL name, IMP imp, const char *types)
cls->methods = methods;
methods->method_count = 1;
methods->method_list[0].method_name = sel_register_typed_name(methodName, types);
methods->method_list[0].method_name
= sel_register_typed_name(methodName, types);
methods->method_list[0].method_types = strdup(types);
methods->method_list[0].method_imp = (objc_imp_gnu)imp;
@ -196,12 +216,21 @@ BOOL class_addMethod(Class cls, SEL name, IMP imp, const char *types)
return YES;
}
BOOL class_addProtocol(Class cls, Protocol *protocol)
BOOL
class_addProtocol(Class cls, Protocol *protocol)
{
if (class_conformsToProtocol(cls, protocol)) { return NO; }
struct objc_protocol_list *protocols = cls->protocols;
struct objc_protocol_list *protocols;
if (class_conformsToProtocol(cls, protocol))
{
return NO;
}
protocols = cls->protocols;
protocols = objc_malloc(sizeof(struct objc_protocol_list));
if (protocols == NULL) { return NO; }
if (protocols == NULL)
{
return NO;
}
protocols->next = cls->protocols;
protocols->count = 1;
protocols->list[0] = protocol;
@ -210,12 +239,17 @@ BOOL class_addProtocol(Class cls, Protocol *protocol)
return YES;
}
BOOL class_conformsToProtocol(Class cls, Protocol *protocol)
BOOL
class_conformsToProtocol(Class cls, Protocol *protocol)
{
for (struct objc_protocol_list *protocols = cls->protocols;
protocols != NULL ; protocols = protocols->next)
struct objc_protocol_list *protocols;
for (protocols = cls->protocols;
protocols != NULL; protocols = protocols->next)
{
for (int i=0 ; i<protocols->count ; i++)
int i;
for (i = 0; i < protocols->count; i++)
{
if (strcmp(protocols->list[i]->protocol_name,
protocol->protocol_name) == 0)
@ -227,10 +261,14 @@ BOOL class_conformsToProtocol(Class cls, Protocol *protocol)
return NO;
}
Ivar * class_copyIvarList(Class cls, unsigned int *outCount)
Ivar *
class_copyIvarList(Class cls, unsigned int *outCount)
{
struct objc_ivar_list *ivarlist = cls->ivars;
unsigned int count = 0;
unsigned int i;
Ivar *list;
if (ivarlist != NULL)
{
count = ivarlist->ivar_count;
@ -244,19 +282,23 @@ Ivar * class_copyIvarList(Class cls, unsigned int *outCount)
return NULL;
}
Ivar *list = malloc(count * sizeof(struct objc_ivar *));
for (unsigned int i=0; i<ivarlist->ivar_count; i++)
list = malloc(count * sizeof(struct objc_ivar *));
for (i = 0; i < ivarlist->ivar_count; i++)
{
list[i] = &(ivarlist->ivar_list[i]);
}
return list;
}
Method * class_copyMethodList(Class cls, unsigned int *outCount)
Method *
class_copyMethodList(Class cls, unsigned int *outCount)
{
unsigned int count = 0;
for (struct objc_method_list *methods = cls->methods;
methods != NULL ; methods = methods->method_next)
Method *list;
Method *copyDest;
struct objc_method_list *methods;
for (methods = cls->methods; methods != NULL; methods = methods->method_next)
{
count += methods->method_count;
}
@ -269,13 +311,14 @@ Method * class_copyMethodList(Class cls, unsigned int *outCount)
return NULL;
}
Method *list = malloc(count * sizeof(struct objc_method *));
Method *copyDest = list;
list = malloc(count * sizeof(struct objc_method *));
copyDest = list;
for (struct objc_method_list *methods = cls->methods;
methods != NULL ; methods = methods->method_next)
for (methods = cls->methods; methods != NULL; methods = methods->method_next)
{
for (unsigned int i=0; i<methods->method_count; i++)
unsigned int i;
for (i = 0; i < methods->method_count; i++)
{
copyDest[i] = &(methods->method_list[i]);
}
@ -285,13 +328,16 @@ Method * class_copyMethodList(Class cls, unsigned int *outCount)
return list;
}
Protocol ** class_copyProtocolList(Class cls, unsigned int *outCount)
Protocol **
class_copyProtocolList(Class cls, unsigned int *outCount)
{
struct objc_protocol_list *protocolList = cls->protocols;
struct objc_protocol_list *list;
int listSize = 0;
for (struct objc_protocol_list *list = protocolList ;
list != NULL ;
list = list->next)
Protocol **protocols;
int index;
for (list = protocolList; list != NULL; list = list->next)
{
listSize += list->count;
}
@ -301,11 +347,9 @@ Protocol ** class_copyProtocolList(Class cls, unsigned int *outCount)
return NULL;
}
Protocol **protocols = calloc(listSize, sizeof(Protocol*) + 1);
int index = 0;
for (struct objc_protocol_list *list = protocolList ;
list != NULL ;
list = list->next)
protocols = calloc(listSize, sizeof(Protocol*) + 1);
index = 0;
for (list = protocolList; list != NULL; list = list->next)
{
memcpy(&protocols[index], list->list, list->count * sizeof(Protocol*));
index += list->count;
@ -315,20 +359,24 @@ Protocol ** class_copyProtocolList(Class cls, unsigned int *outCount)
return protocols;
}
id class_createInstance(Class cls, size_t extraBytes)
id
class_createInstance(Class cls, size_t extraBytes)
{
id obj = objc_malloc(cls->instance_size + extraBytes);
obj->isa = cls;
return obj;
}
Method class_getInstanceMethod(Class aClass, SEL aSelector)
Method
class_getInstanceMethod(Class aClass, SEL aSelector)
{
Method method = class_getInstanceMethodNonrecursive(aClass, aSelector);
if (method == NULL)
{
// TODO: Check if this should be NULL or aClass
Class superclass = class_getSuperclass(aClass);
if (superclass == NULL)
{
return NULL;
@ -338,30 +386,40 @@ Method class_getInstanceMethod(Class aClass, SEL aSelector)
return method;
}
Method class_getClassMethod(Class aClass, SEL aSelector)
Method
class_getClassMethod(Class aClass, SEL aSelector)
{
return class_getInstanceMethod(aClass->class_pointer, aSelector);
}
Ivar class_getClassVariable(Class cls, const char* name)
Ivar
class_getClassVariable(Class cls, const char* name)
{
assert(0 && "Class variables not implemented");
return NULL;
}
size_t class_getInstanceSize(Class cls)
size_t
class_getInstanceSize(Class cls)
{
return cls->instance_size;
}
Ivar class_getInstanceVariable(Class cls, const char* name)
Ivar
class_getInstanceVariable(Class cls, const char* name)
{
struct objc_ivar_list *ivarlist = cls->ivars;
if (NULL == ivarlist) { return NULL; }
int i;
for (int i=0 ; i<ivarlist->ivar_count ; i++)
if (NULL == ivarlist)
{
return NULL;
}
for (i = 0; i < ivarlist->ivar_count; i++)
{
Ivar ivar = &ivarlist->ivar_list[i];
if (strcmp(ivar->ivar_name, name) == 0)
{
return ivar;
@ -372,30 +430,36 @@ Ivar class_getInstanceVariable(Class cls, const char* name)
// The format of the char* is undocumented. This function is only ever used in
// conjunction with class_setIvarLayout().
const char *class_getIvarLayout(Class cls)
const char *
class_getIvarLayout(Class cls)
{
return (char*)cls->ivars;
}
IMP class_getMethodImplementation(Class cls, SEL name)
IMP
class_getMethodImplementation(Class cls, SEL name)
{
struct objc_object_gnu obj = { cls };
return (IMP)objc_msg_lookup((id)&obj, name);
}
IMP class_getMethodImplementation_stret(Class cls, SEL name)
IMP
class_getMethodImplementation_stret(Class cls, SEL name)
{
struct objc_object_gnu obj = { cls };
return (IMP)objc_msg_lookup((id)&obj, name);
}
const char * class_getName(Class cls)
const char *
class_getName(Class cls)
{
return class_get_class_name(cls);
}
void __objc_resolve_class_links(void);
Class class_getSuperclass(Class cls)
Class
class_getSuperclass(Class cls)
{
if (!CLS_ISRESOLV(cls))
{
@ -404,42 +468,50 @@ Class class_getSuperclass(Class cls)
return cls->super_class;
}
int class_getVersion(Class theClass)
int
class_getVersion(Class theClass)
{
return class_get_version(theClass);
}
const char *class_getWeakIvarLayout(Class cls)
const char *
class_getWeakIvarLayout(Class cls)
{
assert(0 && "Weak ivars not supported");
return NULL;
}
BOOL class_isMetaClass(Class cls)
BOOL
class_isMetaClass(Class cls)
{
return CLS_ISMETA(cls);
}
IMP class_replaceMethod(Class cls, SEL name, IMP imp, const char *types)
IMP
class_replaceMethod(Class cls, SEL name, IMP imp, const char *types)
{
Method method = class_getInstanceMethodNonrecursive(cls, name);
IMP old;
if (method == NULL)
{
class_addMethod(cls, name, imp, types);
return NULL;
}
IMP old = (IMP)method->method_imp;
old = (IMP)method->method_imp;
method->method_imp = (objc_imp_gnu)imp;
return old;
}
BOOL class_respondsToSelector(Class cls, SEL sel)
BOOL
class_respondsToSelector(Class cls, SEL sel)
{
return __objc_responds_to(cls, sel);
}
void class_setIvarLayout(Class cls, const char *layout)
void
class_setIvarLayout(Class cls, const char *layout)
{
struct objc_ivar_list *list = (struct objc_ivar_list*)layout;
size_t listsize = sizeof(struct objc_ivar_list) +
@ -449,57 +521,76 @@ void class_setIvarLayout(Class cls, const char *layout)
}
__attribute__((deprecated))
Class class_setSuperclass(Class cls, Class newSuper)
Class
class_setSuperclass(Class cls, Class newSuper)
{
Class oldSuper = cls->super_class;
cls->super_class = newSuper;
return oldSuper;
}
void class_setVersion(Class theClass, int version)
void
class_setVersion(Class theClass, int version)
{
class_set_version(theClass, version);
}
void class_setWeakIvarLayout(Class cls, const char *layout)
void
class_setWeakIvarLayout(Class cls, const char *layout)
{
assert(0 && "Not implemented");
}
const char * ivar_getName(Ivar ivar)
const char *
ivar_getName(Ivar ivar)
{
return ivar->ivar_name;
}
ptrdiff_t ivar_getOffset(Ivar ivar)
ptrdiff_t
ivar_getOffset(Ivar ivar)
{
return ivar->ivar_offset;
}
const char * ivar_getTypeEncoding(Ivar ivar)
const char *
ivar_getTypeEncoding(Ivar ivar)
{
return ivar->ivar_type;
}
static size_t lengthOfTypeEncoding(const char *types)
static size_t
lengthOfTypeEncoding(const char *types)
{
const char *end = objc_skip_argspec(types);
size_t length;
end--;
while (isdigit(*end)) { end--; }
size_t length = end - types + 1;
while (isdigit(*end))
{
end--;
}
length = end - types + 1;
return length;
}
static char *copyTypeEncoding(const char *types)
static char *
copyTypeEncoding(const char *types)
{
size_t length = lengthOfTypeEncoding(types);
char *copy = malloc(length + 1);
memcpy(copy, types, length);
copy[length] = '\0';
return copy;
}
static const char * findParameterStart(const char *types, unsigned int index)
static const char *
findParameterStart(const char *types, unsigned int index)
{
for (unsigned int i=0 ; i<index ; i++)
unsigned int i;
for (i = 0; i < index; i++)
{
types = objc_skip_argspec(types);
if ('\0' == *types)
@ -510,9 +601,11 @@ static const char * findParameterStart(const char *types, unsigned int index)
return types;
}
char * method_copyArgumentType(Method method, unsigned int index)
char *
method_copyArgumentType(Method method, unsigned int index)
{
const char *types = findParameterStart(method->method_types, index);
if (NULL == types)
{
return NULL;
@ -520,31 +613,39 @@ char * method_copyArgumentType(Method method, unsigned int index)
return copyTypeEncoding(types);
}
char * method_copyReturnType(Method method)
char *
method_copyReturnType(Method method)
{
return copyTypeEncoding(method->method_types);
}
void method_exchangeImplementations(Method m1, Method m2)
void
method_exchangeImplementations(Method m1, Method m2)
{
IMP tmp = (IMP)m1->method_imp;
m1->method_imp = m2->method_imp;
m2->method_imp = (objc_imp_gnu)tmp;
objc_updateDtableForClassContainingMethod(m1);
objc_updateDtableForClassContainingMethod(m2);
}
void method_getArgumentType(Method method,
void
method_getArgumentType(Method method,
unsigned int index,
char *dst,
size_t dst_len)
{
const char *types = findParameterStart(method->method_types, index);
const char *types;
size_t length;
types = findParameterStart(method->method_types, index);
if (NULL == types)
{
strncpy(dst, "", dst_len);
return;
}
size_t length = lengthOfTypeEncoding(types);
length = lengthOfTypeEncoding(types);
if (length < dst_len)
{
memcpy(dst, types, length);
@ -556,20 +657,24 @@ void method_getArgumentType(Method method,
}
}
IMP method_getImplementation(Method method)
IMP
method_getImplementation(Method method)
{
return (IMP)method->method_imp;
}
SEL method_getName(Method method)
SEL
method_getName(Method method)
{
return method->method_name;
}
unsigned method_getNumberOfArguments(Method method)
unsigned
method_getNumberOfArguments(Method method)
{
const char *types = method->method_types;
unsigned int count = 0;
while('\0' != *types)
{
types = objc_skip_argspec(types);
@ -578,11 +683,13 @@ unsigned method_getNumberOfArguments(Method method)
return count - 1;
}
void method_getReturnType(Method method, char *dst, size_t dst_len)
void
method_getReturnType(Method method, char *dst, size_t dst_len)
{
//TODO: Coped and pasted code. Factor it out.
const char *types = method->method_types;
size_t length = lengthOfTypeEncoding(types);
if (length < dst_len)
{
memcpy(dst, types, length);
@ -594,27 +701,33 @@ void method_getReturnType(Method method, char *dst, size_t dst_len)
}
}
const char * method_getTypeEncoding(Method method)
const char *
method_getTypeEncoding(Method method)
{
return method->method_types;
}
IMP method_setImplementation(Method method, IMP imp)
IMP
method_setImplementation(Method method, IMP imp)
{
IMP old = (IMP)method->method_imp;
method->method_imp = (objc_imp_gnu)old;
objc_updateDtableForClassContainingMethod(method);
return old;
}
id objc_getClass(const char *name)
id
objc_getClass(const char *name)
{
return (id)objc_get_class(name);
}
int objc_getClassList(Class *buffer, int bufferLen)
int
objc_getClassList(Class *buffer, int bufferLen)
{
int count = 0;
if (buffer == NULL)
{
void *state = NULL;
@ -627,6 +740,7 @@ int objc_getClassList(Class *buffer, int bufferLen)
{
Class nextClass;
void *state = NULL;
while (Nil != (nextClass = objc_next_class(&state)) && bufferLen > 0)
{
count++;
@ -637,15 +751,18 @@ int objc_getClassList(Class *buffer, int bufferLen)
return count;
}
id objc_getMetaClass(const char *name)
id
objc_getMetaClass(const char *name)
{
Class cls = (Class)objc_getClass(name);
return cls == Nil ? nil : (id)cls->class_pointer;
}
id objc_getRequiredClass(const char *name)
id
objc_getRequiredClass(const char *name)
{
id cls = objc_getClass(name);
if (nil == cls)
{
abort();
@ -653,35 +770,48 @@ id objc_getRequiredClass(const char *name)
return cls;
}
id objc_lookUpClass(const char *name)
id
objc_lookUpClass(const char *name)
{
// TODO: Check these are the right way around.
return (id)objc_lookup_class(name);
}
static void freeMethodLists(Class aClass)
static void
freeMethodLists(Class aClass)
{
struct objc_method_list *methods = aClass->methods;
while(methods != NULL)
struct objc_method_list *current;
while (methods != NULL)
{
for (int i=0 ; i<methods->method_count ; i++)
int i;
for (i = 0; i < methods->method_count; i++)
{
free((void*)methods->method_list[i].method_types);
}
struct objc_method_list *current = methods;
current = methods;
methods = methods->method_next;
free(current);
}
}
static void freeIvarLists(Class aClass)
static void
freeIvarLists(Class aClass)
{
struct objc_ivar_list *ivarlist = aClass->ivars;
if (NULL == ivarlist) { return; }
int i;
for (int i=0 ; i<ivarlist->ivar_count ; i++)
if (NULL == ivarlist)
{
return;
}
for (i = 0; i < ivarlist->ivar_count; i++)
{
Ivar ivar = &ivarlist->ivar_list[i];
free((void*)ivar->ivar_type);
free((void*)ivar->ivar_name);
}
@ -692,9 +822,11 @@ static void freeIvarLists(Class aClass)
* Removes a class from the subclass list found on its super class.
* Must be called with the objc runtime mutex locked.
*/
static inline void safe_remove_from_subclass_list(Class cls)
static inline void
safe_remove_from_subclass_list(Class cls)
{
Class sub = cls->super_class->subclass_list;
if (sub == cls)
{
cls->super_class->subclass_list = cls->sibling_class;
@ -713,9 +845,11 @@ static inline void safe_remove_from_subclass_list(Class cls)
}
}
void objc_disposeClassPair(Class cls)
void
objc_disposeClassPair(Class cls)
{
Class meta = ((id)cls)->isa;
// Remove from the runtime system so nothing tries updating the dtable
// while we are freeing the class.
objc_mutex_lock(__objc_runtime_mutex);
@ -733,17 +867,27 @@ void objc_disposeClassPair(Class cls)
free(cls);
}
Class objc_allocateClassPair(Class superclass, const char *name, size_t extraBytes)
Class
objc_allocateClassPair(Class superclass, const char *name, size_t extraBytes)
{
Class newClass;
Class metaClass;
// Check the class doesn't already exist.
if (nil != objc_lookUpClass(name)) { return Nil; }
if (nil != objc_lookUpClass(name))
{
return Nil;
}
Class newClass = calloc(1, sizeof(struct objc_class) + extraBytes);
newClass = calloc(1, sizeof(struct objc_class) + extraBytes);
if (Nil == newClass) { return Nil; }
if (Nil == newClass)
{
return Nil;
}
// Create the metaclass
Class metaClass = calloc(1, sizeof(struct objc_class));
metaClass = calloc(1, sizeof(struct objc_class));
// Initialize the metaclass
metaClass->class_pointer = superclass->class_pointer->class_pointer;
@ -766,7 +910,8 @@ Class objc_allocateClassPair(Class superclass, const char *name, size_t extraByt
return newClass;
}
void *object_getIndexedIvars(id obj)
void *
object_getIndexedIvars(id obj)
{
if (class_isMetaClass(obj->isa))
{
@ -775,7 +920,8 @@ void *object_getIndexedIvars(id obj)
return ((char*)obj) + obj->isa->instance_size;
}
Class object_getClass(id obj)
Class
object_getClass(id obj)
{
if (nil != obj)
{
@ -784,18 +930,21 @@ Class object_getClass(id obj)
return Nil;
}
Class object_setClass(id obj, Class cls)
Class
object_setClass(id obj, Class cls)
{
if (nil != obj)
{
Class oldClass = obj->isa;
obj->isa = cls;
return oldClass;
}
return Nil;
}
const char *object_getClassName(id obj)
const char *
object_getClassName(id obj)
{
return class_getName(object_getClass(obj));
}
@ -803,7 +952,8 @@ const char *object_getClassName(id obj)
void __objc_add_class_to_hash(Class cls);
void __objc_resolve_class_links(void);
void objc_registerClassPair(Class cls)
void
objc_registerClassPair(Class cls)
{
Class metaClass = cls->class_pointer;
@ -815,44 +965,53 @@ void objc_registerClassPair(Class cls)
__objc_resolve_class_links();
}
static id objectNew(id cls)
static id
objectNew(id cls)
{
static SEL newSel = NULL;
IMP newIMP;
if (NULL == newSel)
{
newSel = sel_get_uid("new");
}
IMP newIMP = (IMP)objc_msg_lookup((void*)cls, newSel);
newIMP = (IMP)objc_msg_lookup((void*)cls, newSel);
return newIMP((id)cls, newSel);
}
Protocol *objc_getProtocol(const char *name)
Protocol *
objc_getProtocol(const char *name)
{
// Protocols are not centrally registered in the GNU runtime.
Protocol *protocol = (Protocol*)(objectNew(objc_getClass("Protocol")));
protocol->protocol_name = (char*)name;
return protocol;
}
BOOL protocol_conformsToProtocol(Protocol *p, Protocol *other)
BOOL
protocol_conformsToProtocol(Protocol *p, Protocol *other)
{
return NO;
}
struct objc_method_description *protocol_copyMethodDescriptionList(Protocol *p,
struct objc_method_description *
protocol_copyMethodDescriptionList(Protocol *p,
BOOL isRequiredMethod, BOOL isInstanceMethod, unsigned int *count)
{
*count = 0;
return NULL;
}
Protocol **protocol_copyProtocolList(Protocol *p, unsigned int *count)
Protocol **
protocol_copyProtocolList(Protocol *p, unsigned int *count)
{
*count = 0;
return NULL;
}
const char *protocol_getName(Protocol *p)
const char *
protocol_getName(Protocol *p)
{
if (NULL != p)
{
@ -861,37 +1020,41 @@ const char *protocol_getName(Protocol *p)
return NULL;
}
BOOL protocol_isEqual(Protocol *p, Protocol *other)
BOOL
protocol_isEqual(Protocol *p, Protocol *other)
{
if (NULL == p || NULL == other)
{
return NO;
}
if (p == other ||
0 == strcmp(p->protocol_name, other->protocol_name))
if (p == other
|| 0 == strcmp(p->protocol_name, other->protocol_name))
{
return YES;
}
return NO;
}
const char *sel_getName(SEL sel)
const char *
sel_getName(SEL sel)
{
return sel_get_name(sel);
}
SEL sel_getUid(const char *selName)
SEL
sel_getUid(const char *selName)
{
return sel_get_uid(selName);
}
BOOL sel_isEqual(SEL sel1, SEL sel2)
BOOL
sel_isEqual(SEL sel1, SEL sel2)
{
// FIXME: Is this correct?
return (0 == strcmp(sel_get_name(sel1), sel_get_name(sel2)));
return sel_eq(sel1, sel2) ? YES : NO;
}
SEL sel_registerName(const char *selName)
SEL
sel_registerName(const char *selName)
{
return sel_register_name(selName);
}

View file

@ -2,7 +2,7 @@
/* Ensure Unix98 compatible pthreads for glibc */
#if defined __GLIBC__
#define __USE_UNIX98 1
# define __USE_UNIX98 1
#endif
#include <pthread.h>
@ -20,44 +20,53 @@ IMP objc_msg_lookup(id, SEL);
static void deallocLockClass(id obj, SEL _cmd);
static inline Class findLockClass(id obj)
static inline Class
findLockClass(id obj)
{
struct objc_object object = { obj->isa };
SEL dealloc = @selector(dealloc);
Class lastClass;
// Find the first class where this lookup is correct
if (objc_msg_lookup((id)&object, dealloc) != (IMP)deallocLockClass)
{
do {
object.isa = class_getSuperclass(object.isa);
} while (Nil != object.isa &&
objc_msg_lookup((id)&object, dealloc) != (IMP)deallocLockClass);
} while (Nil != object.isa
&& objc_msg_lookup((id)&object, dealloc) != (IMP)deallocLockClass);
}
if (Nil == object.isa) { return Nil; }
// object->isa is now either the lock class, or a class which inherits from
// the lock class
Class lastClass;
if (Nil == object.isa)
{
return Nil;
}
/* object->isa is now either the lock class, or a class which inherits from
* the lock class
*/
do {
lastClass = object.isa;
object.isa = class_getSuperclass(object.isa);
} while (Nil != object.isa &&
objc_msg_lookup((id)&object, dealloc) == (IMP)deallocLockClass);
} while (Nil != object.isa
&& objc_msg_lookup((id)&object, dealloc) == (IMP)deallocLockClass);
return lastClass;
}
static inline Class initLockObject(id obj)
static inline Class
initLockObject(id obj)
{
char nameBuffer[40];
Class lockClass;
const char *types;
pthread_mutex_t *lock;
snprintf(nameBuffer, 39, "hiddenlockClass%lld", lockClassId++);
Class lockClass = objc_allocateClassPair(obj->isa, nameBuffer,
lockClass = objc_allocateClassPair(obj->isa, nameBuffer,
sizeof(pthread_mutex_t));
const char *types =
method_getTypeEncoding(class_getInstanceMethod(obj->isa,
types = method_getTypeEncoding(class_getInstanceMethod(obj->isa,
@selector(dealloc)));
class_addMethod(lockClass, @selector(dealloc), (IMP)deallocLockClass,
types);
class_addMethod(lockClass, @selector(dealloc), (IMP)deallocLockClass, types);
objc_registerClassPair(lockClass);
pthread_mutex_t *lock = object_getIndexedIvars(lockClass);
lock = object_getIndexedIvars(lockClass);
pthread_mutexattr_t attr;
pthread_mutexattr_init(&attr);
pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE);
@ -68,12 +77,14 @@ static inline Class initLockObject(id obj)
return lockClass;
}
static void deallocLockClass(id obj, SEL _cmd)
static void
deallocLockClass(id obj, SEL _cmd)
{
Class lockClass = findLockClass(obj);
Class realClass = class_getSuperclass(lockClass);
// Free the lock
pthread_mutex_t *lock = object_getIndexedIvars(lockClass);
pthread_mutex_destroy(lock);
// Free the class
objc_disposeClassPair(lockClass);
@ -82,9 +93,12 @@ static void deallocLockClass(id obj, SEL _cmd)
[obj dealloc];
}
void objc_sync_enter(id obj)
void
objc_sync_enter(id obj)
{
Class lockClass = findLockClass(obj);
pthread_mutex_t *lock;
if (Nil == lockClass)
{
pthread_mutex_lock(&at_sync_init_lock);
@ -96,10 +110,12 @@ void objc_sync_enter(id obj)
}
pthread_mutex_unlock(&at_sync_init_lock);
}
pthread_mutex_t *lock = object_getIndexedIvars(lockClass);
lock = object_getIndexedIvars(lockClass);
pthread_mutex_lock(lock);
}
void objc_sync_exit(id obj)
void
objc_sync_exit(id obj)
{
Class lockClass = findLockClass(obj);
pthread_mutex_t *lock = object_getIndexedIvars(lockClass);

View file

@ -18,6 +18,7 @@ WITH_FFI=@WITH_FFI@
NX_CONST_STRING_CLASS=@NX_CONST_STRING_CLASS@
OBJCFLAGS=@OBJCFLAGS@
OBJC2RUNTIME=@OBJC2RUNTIME@
HAVE_INET_PTON=@HAVE_INET_PTON@
HAVE_INET_NTOP=@HAVE_INET_NTOP@

115
configure vendored
View file

@ -310,7 +310,7 @@ ac_includes_default="\
#endif"
ac_subdirs_all="$ac_subdirs_all Source/pathconfig Source/mframe SSL"
ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS build build_cpu build_vendor build_os host host_cpu host_vendor host_os target target_cpu target_vendor target_os CC CFLAGS LDFLAGS CPPFLAGS ac_ct_CC EXEEXT OBJEXT CPP WHOAMI EGREP OBJC_WITH_GC GS_WORDS_BIGENDIAN GS_SINT8 GS_UINT8 ac_cv_sizeof_short ac_cv_sizeof_int ac_cv_sizeof_long ac_cv_sizeof_long_long ac_cv_sizeof_float ac_cv_sizeof_double ac_cv_sizeof_voidp GS_SADDR GS_UADDR GS_SINT16 GS_UINT16 GS_SINT32 GS_UINT32 GS_SINT64 GS_UINT64 GS_HAVE_I64 GS_SINT128 GS_UINT128 GS_HAVE_I128 GS_FLT32 GS_FLT64 _GSC_S_SHT _GSC_S_INT _GSC_S_LNG _GSC_S_LNG_LNG DYNAMIC_LINKER NX_CONST_STRING_OBJCFLAGS NX_CONST_STRING_CLASS HAVE_OBJC_SYNC_ENTER GS_SIZEOF_MUTEX_T GS_SIZEOF_COND_T HAVE_PTS_STREAM_MODULES INCLUDE_STDINT DEFINE_INT8_T DEFINE_UINT8_T DEFINE_INT16_T DEFINE_UINT16_T DEFINE_INT32_T DEFINE_UINT32_T DEFINE_INT64_T DEFINE_UINT64_T DEFINE_INTPTR_T DEFINE_UINTPTR_T USE_ZLIB HAVE_INET_PTON HAVE_INET_NTOP GS_PASS_ARGUMENTS GS_FAKE_MAIN OBJCFLAGS WITH_FFI XML2_CONFIG XML_CONFIG XML_CFLAGS XML_LIBS HAVE_LIBXSLT HAVE_LIBXML TLS_CONFIG TLS_CFLAGS TLS_LIBS HAVE_GNUTLS HAVE_MDNS USE_GMP INCLUDE_FLAGS LDIR_FLAGS subdirs VERSION MAJOR_VERSION MINOR_VERSION SUBMINOR_VERSION GCC_VERSION LIBOBJS LTLIBOBJS'
ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS build build_cpu build_vendor build_os host host_cpu host_vendor host_os target target_cpu target_vendor target_os CC CFLAGS LDFLAGS CPPFLAGS ac_ct_CC EXEEXT OBJEXT CPP WHOAMI EGREP OBJC_WITH_GC GS_WORDS_BIGENDIAN GS_SINT8 GS_UINT8 ac_cv_sizeof_short ac_cv_sizeof_int ac_cv_sizeof_long ac_cv_sizeof_long_long ac_cv_sizeof_float ac_cv_sizeof_double ac_cv_sizeof_voidp GS_SADDR GS_UADDR GS_SINT16 GS_UINT16 GS_SINT32 GS_UINT32 GS_SINT64 GS_UINT64 GS_HAVE_I64 GS_SINT128 GS_UINT128 GS_HAVE_I128 GS_FLT32 GS_FLT64 _GSC_S_SHT _GSC_S_INT _GSC_S_LNG _GSC_S_LNG_LNG DYNAMIC_LINKER NX_CONST_STRING_OBJCFLAGS NX_CONST_STRING_CLASS OBJC2RUNTIME HAVE_OBJC_SYNC_ENTER GS_SIZEOF_MUTEX_T GS_SIZEOF_COND_T HAVE_PTS_STREAM_MODULES INCLUDE_STDINT DEFINE_INT8_T DEFINE_UINT8_T DEFINE_INT16_T DEFINE_UINT16_T DEFINE_INT32_T DEFINE_UINT32_T DEFINE_INT64_T DEFINE_UINT64_T DEFINE_INTPTR_T DEFINE_UINTPTR_T USE_ZLIB HAVE_INET_PTON HAVE_INET_NTOP GS_PASS_ARGUMENTS GS_FAKE_MAIN OBJCFLAGS WITH_FFI XML2_CONFIG XML_CONFIG XML_CFLAGS XML_LIBS HAVE_LIBXSLT HAVE_LIBXML TLS_CONFIG TLS_CFLAGS TLS_LIBS HAVE_GNUTLS HAVE_MDNS USE_GMP INCLUDE_FLAGS LDIR_FLAGS subdirs VERSION MAJOR_VERSION MINOR_VERSION SUBMINOR_VERSION GCC_VERSION LIBOBJS LTLIBOBJS'
ac_subst_files=''
# Initialize some variables set by options.
@ -8647,6 +8647,118 @@ fi
done
#--------------------------------------------------------------------
# Check for ObjC2 support in runtime
#--------------------------------------------------------------------
for ac_func in objc_setProperty
do
as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh`
echo "$as_me:$LINENO: checking for $ac_func" >&5
echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6
if eval "test \"\${$as_ac_var+set}\" = set"; then
echo $ECHO_N "(cached) $ECHO_C" >&6
else
cat >conftest.$ac_ext <<_ACEOF
/* confdefs.h. */
_ACEOF
cat confdefs.h >>conftest.$ac_ext
cat >>conftest.$ac_ext <<_ACEOF
/* end confdefs.h. */
/* Define $ac_func to an innocuous variant, in case <limits.h> declares $ac_func.
For example, HP-UX 11i <limits.h> declares gettimeofday. */
#define $ac_func innocuous_$ac_func
/* System header to define __stub macros and hopefully few prototypes,
which can conflict with char $ac_func (); below.
Prefer <limits.h> to <assert.h> if __STDC__ is defined, since
<limits.h> exists even on freestanding compilers. */
#ifdef __STDC__
# include <limits.h>
#else
# include <assert.h>
#endif
#undef $ac_func
/* Override any gcc2 internal prototype to avoid an error. */
#ifdef __cplusplus
extern "C"
{
#endif
/* We use char because int might match the return type of a gcc2
builtin and then its argument prototype would still apply. */
char $ac_func ();
/* The GNU C library defines this for functions which it implements
to always fail with ENOSYS. Some functions are actually named
something starting with __ and the normal name is an alias. */
#if defined (__stub_$ac_func) || defined (__stub___$ac_func)
choke me
#else
char (*f) () = $ac_func;
#endif
#ifdef __cplusplus
}
#endif
int
main ()
{
return f != $ac_func;
;
return 0;
}
_ACEOF
rm -f conftest.$ac_objext conftest$ac_exeext
if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5
(eval $ac_link) 2>conftest.er1
ac_status=$?
grep -v '^ *+' conftest.er1 >conftest.err
rm -f conftest.er1
cat conftest.err >&5
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); } &&
{ ac_try='test -z "$ac_c_werror_flag"
|| test ! -s conftest.err'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; } &&
{ ac_try='test -s conftest$ac_exeext'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; }; then
eval "$as_ac_var=yes"
else
echo "$as_me: failed program was:" >&5
sed 's/^/| /' conftest.$ac_ext >&5
eval "$as_ac_var=no"
fi
rm -f conftest.err conftest.$ac_objext \
conftest$ac_exeext conftest.$ac_ext
fi
echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5
echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6
if test `eval echo '${'$as_ac_var'}'` = yes; then
cat >>confdefs.h <<_ACEOF
#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1
_ACEOF
fi
done
if test $ac_cv_func_objc_setProperty = yes ; then
OBJC2RUNTIME=yes
else
OBJC2RUNTIME=no
fi
# Don't revert any Objective-C flags as they are used in the next test
#--------------------------------------------------------------------
@ -21401,6 +21513,7 @@ s,@_GSC_S_LNG_LNG@,$_GSC_S_LNG_LNG,;t t
s,@DYNAMIC_LINKER@,$DYNAMIC_LINKER,;t t
s,@NX_CONST_STRING_OBJCFLAGS@,$NX_CONST_STRING_OBJCFLAGS,;t t
s,@NX_CONST_STRING_CLASS@,$NX_CONST_STRING_CLASS,;t t
s,@OBJC2RUNTIME@,$OBJC2RUNTIME,;t t
s,@HAVE_OBJC_SYNC_ENTER@,$HAVE_OBJC_SYNC_ENTER,;t t
s,@GS_SIZEOF_MUTEX_T@,$GS_SIZEOF_MUTEX_T,;t t
s,@GS_SIZEOF_COND_T@,$GS_SIZEOF_COND_T,;t t

View file

@ -658,6 +658,17 @@ fi
#--------------------------------------------------------------------
AC_CHECK_FUNCS(objc_thread_add)
#--------------------------------------------------------------------
# Check for ObjC2 support in runtime
#--------------------------------------------------------------------
AC_CHECK_FUNCS(objc_setProperty)
if test $ac_cv_func_objc_setProperty = yes ; then
OBJC2RUNTIME=yes
else
OBJC2RUNTIME=no
fi
AC_SUBST(OBJC2RUNTIME)
# Don't revert any Objective-C flags as they are used in the next test
#--------------------------------------------------------------------