Greetings,

I've been trying to track down a peculiar bug reported by a customer, and I've narrowed it down to a problem returning a BOOL value via -[NSObject performSelector:] on a dual Quad-Core Intel Xeon processor running 64-bit code. It seems that the returned value contains random data, which obscures the BOOL.

I've included the relevant code from the project below for completeness, but the problem boils down to this statement:

    if ([condition performSelector:conditionSelector]!=NO)

The selector identifies a method that returns a BOOL, but sometimes the value returned by -performSelector contains odd data. I added some code to log the value (as an integer) returned by [condition performSelector:conditionSelector]; Most of the time it's 0 or 1, but sometimes it's 0x5400 or 0x2300 when the method returned NO. Note that I cannot reproduce this on the two 64-bit Intel systems I have, even though one of them is the same model of MacPro with the same dual-Quad-Core Intel Xeon as my customer's. All are running 10.6.3.

I thought that, in Objective-C, all pointer and integer scalar values were interchangeable in the return value of a method. Is this a bug in GCC, a bug in the Objective-C runtime, did this rule change in the 64-bit world, or is there possibly something strange about this particular user's system?

Anyway, I'm considering changing my code to read 'if (([condition performSelector:conditionSelector]&0x1)!=NO)' to work around this issue, but I'd like to get a fuller understanding of the problem for future reference (and so I don't say something stupid in my next book about Objective-C!).

--- code snippets ---

@implementation ActionCondition

...

- (BOOL)test
{
    // subclass overrides this method to test some condition
    return ( ... );
}

...

- (BOOL)shouldCancelAction
{
// if this condition causes actions to be skipped, apply the condition
    return ( [self canCancelAction] ? [self test] : NO );
}

- (BOOL)shouldHoldAction
{
    // if this condition causes actions to be held, apply the condition
    return ( [self canHoldAction] ? [self test] : NO );
}

- (BOOL)shouldStopAction
{
    // If this condition causes actions to abort, apply the condition
    return ( [self canStopAction] ? [self test] : NO );
}

@end

@implementation ActionItem

...

static ActionCondition* FindCondition( NSArray* conditions, SEL conditionSelector )
{
// Returns first ActionCondition that returns YES from the given condition message
    NSEnumerator* e = [conditions objectEnumerator];
    ActionCondition* condition;
    while ( (condition=[e nextObject]) != nil )
        {
if ([condition performSelector:conditionSelector]!=NO) <------- sometimes returns something other than 0 or 1
            return (condition);
        }
    return (nil);
}

- (ActionCondition*)cancelCondition
{
    return (FindCondition([self conditions],@selector(shouldCancelAction)));
}

- (ActionCondition*)holdCondition
{
    return (FindCondition([self conditions],@selector(shouldHoldAction)));
}

- (ActionCondition*)stopCondition
{
    return (FindCondition([self conditions],@selector(shouldStopAction)));
}

@end


--
James Bucanek

_______________________________________________

Cocoa-dev mailing list (Cocoa-dev@lists.apple.com)

Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com

Help/Unsubscribe/Update your Subscription:
http://lists.apple.com/mailman/options/cocoa-dev/archive%40mail-archive.com

This email sent to arch...@mail-archive.com

Reply via email to