Search code examples
c++segmentation-faultcoredumptinyxml

TinyXML cant compare Attribute to the char


bool win::checkIfFScreen(sf::RenderWindow &window)
{
    TiXmlDocument doc;
    TiXmlElement * fullscreen;

    if(!doc.LoadFile("videoSettings.xml"))
    {
        fullscreen = new TiXmlElement( "Window" );
        fullscreen->SetAttribute("Fullscreen: ", 0);
        doc.LinkEndChild( fullscreen );
        fullscreen->Attribute("Fullscreen: ");

        std::cout << typeid(*fullscreen->Attribute("Fullscreen: ")).name() << std::endl;
        doc.SaveFile("videoSettings.xml");
        return false;
    }

    if(*(fullscreen->Attribute("Fullscreen: ")) == '0')
        return false;

    return true;


}

Idea:

So, I wanna store information about persons preference if he wants for the game to be fullscreen or windowed. I've created this bool function that checks if there is "videoSettings.xml" file and returns information about users preference. If the file doesn't exists it will be create with Fullscreen set to 0 (which basically means that the game will be windowed and the user could change it later in the game's settings).

Part that doesn't work:

if(*(fullscreen->Attribute("Fullscreen: ")) == '0')
    return false;

After adding this two lines I've got Segmentation fault (core dumped).

It seems that that value is stored as char.

EDIT: This lines solved everything :) .

TiXmlHandle docHandle ( &doc );
TiXmlElement *child = docHandle.FirstChild( "Window" ).ToElement();
if(child)
    if(*child->Attribute("fullscreen") == '1')
        return true;
    else if(*child->Attribute("fullscreen") == '0')
        return false;

Thank you @frasnian .


Solution

  • Your code has this:

    TiXmlElement * fullscreen;  // not initialized to anything here
    
    if(!doc.LoadFile("videoSettings.xml"))        // LoadFile returns true on success
    {
      fullscreen = new TiXmlElement( "Window" );  // okay
          ...
      return false;
    }
    
    // question: if doc.LoadFile() succeeds, what is this going to do-
    if(*(fullscreen->Attribute("Fullscreen: ")) == '0')
        return false;
    

    You are using fullscreen before it is initialized with anything.

    On edit In response to question in comment:

    If loading the document succeeds, you need to get the root element with something like:

    TiXmlElement* root = doc.FirstChildElement("Whatever");  // root element name
    if (root){
        TiXmlElement* el = root->FirstChildElement("Window"); // etc, etc,
    

    When you have walked the document hierarchy to wherever your "Window" element is, use TiXmlElement::Attribute() or TiXmlElement::QueryAttribute() to get the value of the attribute (if it exists).

    A better approach than walking the hierarchy with FirstChild/NextSibling, etc. (inherited by TiXmlElement from TiXmlNode) is probably to use handles. See the docs for TinyXML related to TiXmlHandle - the main docs page has an example that is pretty straightforward.

    As a side note, the colon after the attribute name in your posted code should be removed (i.e. "fullscreen", not "Fullscreen:").

    Also, this line:

    fullscreen->Attribute("Fullscreen: ");
    

    right after you call LinkEndChild() does not do anything.