mirror of
https://git.code.sf.net/p/quake/quakeforge
synced 2024-11-29 07:32:02 +00:00
[qfcc] Add a failing test case for if-super calls
The common idiom for self init (below) causes a double-call when compiling with --advanced, resulting in an incorrect retain count. if (!(self = [super init])) { return nil; }
This commit is contained in:
parent
2d3c2da64d
commit
bfda4e776f
3 changed files with 69 additions and 0 deletions
|
@ -29,6 +29,7 @@ test_progs_dat=\
|
|||
tools/qfcc/test/func-expr2.dat \
|
||||
tools/qfcc/test/func-static.dat \
|
||||
tools/qfcc/test/gcd.dat \
|
||||
tools/qfcc/test/ifsuper.dat \
|
||||
tools/qfcc/test/infloop.dat \
|
||||
tools/qfcc/test/iterfunc.dat \
|
||||
tools/qfcc/test/ivar-struct-return.dat \
|
||||
|
@ -369,6 +370,16 @@ tools/qfcc/test/gcd.run: $(qfcc_test_run_deps)
|
|||
include $(gcd_dep) # am--include-marker
|
||||
pas_depfiles_remade += $(gcd_dep)
|
||||
|
||||
tools_qfcc_test_ifsuper_dat_SOURCES=tools/qfcc/test/ifsuper.r
|
||||
ifsuper_obj=$(tools_qfcc_test_ifsuper_dat_SOURCES:.r=.o)
|
||||
ifsuper_dep=$(call qcautodep,$(tools_qfcc_test_ifsuper_dat_SOURCES))
|
||||
tools/qfcc/test/ifsuper.dat$(EXEEXT): $(ifsuper_obj) $(QFCC_DEP)
|
||||
$(V_QFCCLD)$(QLINK) --advanced -o $@ $(ifsuper_obj)
|
||||
tools/qfcc/test/ifsuper.run: $(qfcc_test_run_deps)
|
||||
@$(top_srcdir)/tools/qfcc/test/build-run $@
|
||||
include $(ifsuper_dep) # am--include-marker
|
||||
r_depfiles_remade += $(ifsuper_dep)
|
||||
|
||||
tools_qfcc_test_infloop_dat_SOURCES=tools/qfcc/test/infloop.r
|
||||
infloop_obj=$(tools_qfcc_test_infloop_dat_SOURCES:.r=.o)
|
||||
infloop_dep=$(call qcautodep,$(tools_qfcc_test_infloop_dat_SOURCES))
|
||||
|
|
56
tools/qfcc/test/ifsuper.r
Normal file
56
tools/qfcc/test/ifsuper.r
Normal file
|
@ -0,0 +1,56 @@
|
|||
#pragma advanced
|
||||
#include "test-harness.h"
|
||||
|
||||
int obj_increment_retaincount (id object) = #0;
|
||||
int obj_get_retaincount (id object) = #0;
|
||||
id (Class class) class_create_instance = #0;
|
||||
id obj_msgSend_super (Super *class, SEL op, ...) = #0;
|
||||
|
||||
@interface Object
|
||||
{
|
||||
Class isa;
|
||||
}
|
||||
+(id) alloc;
|
||||
-(id) init;
|
||||
@end
|
||||
|
||||
@interface Foo : Object
|
||||
-(id) init;
|
||||
@end
|
||||
|
||||
@implementation Object
|
||||
+(id) alloc
|
||||
{
|
||||
return class_create_instance (self);
|
||||
}
|
||||
-(id) init
|
||||
{
|
||||
obj_increment_retaincount (self);
|
||||
return self;
|
||||
}
|
||||
@end
|
||||
|
||||
@implementation Foo
|
||||
-(id) init
|
||||
{
|
||||
if (!(self = [super init])) {
|
||||
return nil;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
@end
|
||||
|
||||
int main ()
|
||||
{
|
||||
Foo *foo = [[Foo alloc] init];
|
||||
if (!foo) {
|
||||
printf ("foo is nil\n");
|
||||
return 1;
|
||||
}
|
||||
int retain = obj_get_retaincount (foo);
|
||||
if (retain != 1) {
|
||||
printf ("retain count != 1: %d\n", retain);
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
|
@ -3,6 +3,8 @@ void printf (string fmt, ...) = #0;
|
|||
int errno (void) = #0;
|
||||
string strerror (int err) = #0;
|
||||
void exit (int code) = #0;
|
||||
void traceon (void) = #0;
|
||||
void traceoff (void) = #0;
|
||||
entity spawn (void) = #0;
|
||||
void remove (entity e) = #0;
|
||||
id obj_msgSend (id receiver, SEL op, ...) = #0;
|
||||
|
|
Loading…
Reference in a new issue