Is 'update(float dt)' threaded?

Hi everyone, I was wondering is the update(float dt) function found in CCLayer and several other classes work as if they were multi-threaded, or if any functions that make use of them are threaded.

Are mutex needed if a value is changed in an update(float dt) function?

Whole cocos2dx is single-threaded, update just called before next frame. There is main loop that looks like this:

until CCDirector::end() called:
    1. poll input devices
    2. perform sheduled selectors, actions, update()
    3. draw scene
    4. swap buffers and wait vertical synchronization
    5. repeat

One loop iteration normally takes 0.016 sec, because typical devices show 60 FPS so game should perform steps 1-2-3 and then wait rest of time portion on step 4.

I have some code that runs the exact same code every several frame, but after a random amount of frames(roughly 30+) it crashes, it looks like a race condition, do you think you can help me if I post the code here?

This code runs on every update(float dt) call, if a sprite is touched:
dialogBoxSprite and dialogBoxText are declared but not defined/ initialized, the initialization happens in this method itself.

void MenuController::dialogBox(std::string string) {
    interfaceIsUp = true;
    dialogBoxIsUp = true;
    dialogBoxSprite = CCSprite::create("DialogBox2.png");
    dialogBoxText = CCTypingLabelBMFont::create(string.c_str(), "west_england-64.fnt", dialogBoxSprite->boundingBox().size.width -16, kCCTextAlignmentLeft);
    this->addChild(dialogBoxSprite);
    dialogBoxSprite->setPosition( ccp(this->boundingBox().size.width /2, this->boundingBox().size.height /5) );
    dialogBoxSprite->addChild(dialogBoxText);
    dialogBoxText->setAnchorPoint( ccp(0, 1) );
    dialogBoxText->setPosition( ccp(8, dialogBoxSprite->boundingBox().size.height -8) );
    dialogBoxText->setScale(0.3f);
    dialogBoxText->setColor(ccBLACK);

    isTyping = true;
    dialogBoxText->startTyping();
}

dialogBoxSprite and dialogBoxText are cleaned up in this function, and reinitialized again the next time void MenuController::dialogBox(std::string string) is called again.

void MenuController::stopTyping() {
    if (dialogBoxSprite != NULL) {
        if (dialogBoxText->numberOfRunningActions() > 0) {
            dialogBoxText->stopTyping();
//            dialogBoxSprite->runAction( CCDelayTime::create(3.0f) );
        }
        else {
            if (dialogBoxSprite->numberOfRunningActions() <= 0) {
                std::cout << dialogBoxSprite->getPositionX()<< " " << dialogBoxSprite->getPositionY() <removeChild(dialogBoxText, true);
                this->removeChild(dialogBoxSprite, true);
                interfaceIsUp = false;
                dialogBoxIsUp = false;
            }
        }
    }
    isTyping = false;
}

The app randomly crashes with a Thread1: EXC_BAD_ACCESS at

dialogBoxSprite->removeChild(dialogBoxText, true);

And sometimes at a few other lines, I’m completely out of ideas on how to debug something like this, as the code only crashes very rarely.

You didn’t set dialogBoxSprite to nullptr when removed it from scene. But it was deleted right after removal.

P.S. And general answer: check again that you track reference count correctly and don’t use node after it destroyed, initialize all variables with nullptr and set member variables pointed destroyed nodes to nullptr. There are no race conditions in actions/update/scheduled functions execution.

I just changed the code to this, but it still crashed randomly:

void MenuController::dialogBox(std::string string) {
    interfaceIsUp = true;
    dialogBoxIsUp = true;
    dialogBoxSprite = nullptr;
    dialogBoxSprite = CCSprite::create("DialogBox2.png");
    CC_SAFE_RETAIN(dialogBoxSprite);
    dialogBoxText = nullptr;
    dialogBoxText = CCTypingLabelBMFont::create(string.c_str(), "west_england-64.fnt", dialogBoxSprite->boundingBox().size.width -16, kCCTextAlignmentLeft);
    CC_SAFE_RETAIN(dialogBoxText);
    this->addChild(dialogBoxSprite);
    dialogBoxSprite->setPosition( ccp(this->boundingBox().size.width /2, this->boundingBox().size.height /5) );
    dialogBoxSprite->addChild(dialogBoxText);
    dialogBoxText->setAnchorPoint( ccp(0, 1) );
    dialogBoxText->setPosition( ccp(8, dialogBoxSprite->boundingBox().size.height -8) );
    dialogBoxText->setScale(0.3f);
    dialogBoxText->setColor(ccBLACK);

    isTyping = true;
    dialogBoxText->startTyping();
}

I was told that reassigning/ initializing a pointer like dialogBoxSprite* or dialogBoxText* was perfectly ok in c++ as it only points to a value and are not the value themselves, is that wrong?

I finally fixed the crashes, thanks for your advice!

There was 2 parts in the random crashes, your advice helped me solve one part, the other part was solved by declaring an std::string in the header file as static.

Assigning them as nullptr at the start of the assigning method wasn’t enough, they had to be assigned immediately after they are removed as a child from the scene:

void MenuController::stopTyping() {
    if (dialogBoxSprite != NULL) {
        if (dialogBoxText->numberOfRunningActions() > 0) {
            dialogBoxText->stopTyping();
//            dialogBoxSprite->runAction( CCDelayTime::create(3.0f) );
        }
        else {
            if (dialogBoxSprite->numberOfRunningActions() == 0) {
                std::cout << dialogBoxSprite->getPositionX()<< " " << dialogBoxSprite->getPositionY() <removeChild(dialogBoxText, true);
                dialogBoxText = nullptr;
                this->removeChild(dialogBoxSprite, true);
                dialogBoxSprite = nullptr;
                interfaceIsUp = false;
                dialogBoxIsUp = false;
            }
        }
    }
    isTyping = false;
}