SDL_QueryTexture() Segmentation Fault in some cases.

I have created a wrapper object for the SDL_ttf font. This object I created has a string for the message to be displayed and also an SDL_Texture. I will update the string and then re-create the texture from the new string passed in and I noticed that this causes a memory leak. I’m trying to call SDL_DestroyTexture to resolve the memory leak. Sometimes though when I call SDL_QueryTexture(Message, NULL, NULL, NULL, NULL) I get a segmentation fault, but not in all cases. I’m calling SDL_QueryTexture to see if the Texture has already been set and if it is, destroy it and then create a new one.

    SDL_Surface* surfaceMessage;
    surfaceMessage = TTF_RenderText_Solid(Classic, textMessage.c_str(), White); 
    Message = SDL_CreateTextureFromSurface(renderer, surfaceMessage);
//  SDL_DestroyTexture(Message); // Adding this line will resolve the memory leak but obviously wont display the font anymore.
    SDL_FreeSurface(surfaceMessage);

I’m trying something like this to remove the old texture before creating the new one.

if(SDL_QueryTexture(Message, NULL, NULL, NULL ,NULL) == 0) {
        SDL_DestroyTexture(Message);
    }

    SDL_Surface* surfaceMessage;
    surfaceMessage = TTF_RenderText_Solid(Classic, textMessage.c_str(), White); 
    Message = SDL_CreateTextureFromSurface(renderer, surfaceMessage);
    SDL_FreeSurface(surfaceMessage);

I’m initializing this Font object that I created like this:

//initialize the fonts for line, level, score
    fontOne = { renderer, LINES_POS_X_PX, LINES_POS_Y_PX, 100, 35 };
    ptrFont = { &fontOne };
    fontLvl = { renderer, LVL_POS_X_PX, LVL_POS_Y_PX, 100, 35 };
    ptrFontLvl = { &fontLvl };
    fontScore = { renderer, SCORE_POS_X_PX, SCORE_POS_Y_PX, 100, 35 }; //Seg fault here!!!
    ptrFontScore = { &fontScore };
    mRenderables.push_back(&fontOne);
    mRenderables.push_back(&fontLvl);
    mRenderables.push_back(&fontScore);
    updateScores();

The pointers are used to update the font later.

The problem is for some reason I get a Segmentation Fault when creating the fontScore. The other cases before that seem to work ok. I notice that when I get the Segmentation Fault the Message is 0x6, I would either expect 0x0 or a valid Message, but can’t figure out why I’m seeing 0x6.

I hope you may be able to provide some insight into how I can create an updateable font without causing a memory leak.

Electrosys

I think you should use null for this instead. SDL_QueryTexture can probably handle null pointers but not uninitialized or dangling pointers.

If you set Message to null when you first create it, and after calling SDL_DestroyTexture, then you can later use that to check if the texture has been set.

if (Message != nullptr)
{
	SDL_DestroyTexture(Message);
	Message = nullptr;
}

Nice! Thanks for the suggestion. I actually tried this but failed to init Message to nullptr in both of my constructors. Your confirmation helped me realize that I had missed one of the initializations.

Previously I had the following and was using the second constructor.

ley::Font::Font() 
: 
Renderable(nullptr),
Message(nullptr)

ley::Font::Font(SDL_Renderer* r, int x, int y, int w, int h)
: Renderable(r)

I should try and minimize this code duplication so I don’t make a silly mistake like this again. I should be able to find a way to remove the default constructor. Or have one constructor call the other one so I don’t have code duplication.

As you’re using C++11 or newer anyway, you can just NULL-initialize them in the class definition, like

class Font {
    SDL_Renderer* Renderable = nullptr;
    Whatever* Message = nullptr;
    // etc
public:
    Font();
    // and all your other code
};

That way you can’t forget to set something to nullptr when adding a new constructor

Good point, thanks for pointing that out.