Sign in to follow this  
Mizipzor

...has exited with code 1 (0x1).

Recommended Posts

My project worked just fine then after Ive edited some (nothing critical) it did just stop working. Im getting this line at the end of the output: The program '[2088] TileSystem.exe: Native' has exited with code 1 (0x1). Anyone knows what that means? That number 2088 differs a little for everytime I try to run. I started the debugger (havent really used a compilers debugger function until now) but I "stepped in" in all the function main executed in order. All went well until I hit this line: m_pInstance = new Game(); Which is a part of the singleton pattern so I have only one instance of the class.
	// Singleton ---
	static Game* GetInstance( void ) {
		if ( !m_pInstance )
			m_pInstance = new Game();
		return m_pInstance;
	};
When I hit that line the debugger stops and I get the same result as before, I see no windows created, I get no compiler errors, the log is empty (the game class is created first, then the log and the rest). The only thing I have to go on is that little line the ouput gives me. Im using Microsoft Visual .Net, anyone knows any good documentation for how to use the debugger? Or a debugger in general, as I guess thats what I need to use if I want to solve this one. Anyone knows what could be wrong?

Share this post


Link to post
Share on other sites
Yes if the variable also is static (i think thats the rule) here my entire game class anyways:


class Game {
protected:
// Singleton class
static Game* m_pInstance;
Game( void ); // constructor, sets up the pointers to all the other classes

SdlHandle* Sdl; // for the graphics
AsciiMap* AsciiMap; // tilesystem
FontSystem* Font; // for printing text on the screen

private:
// variables and functions

public:
// Singleton ---
static Game* GetInstance( void ) {
if ( !m_pInstance )
m_pInstance = new Game();
return m_pInstance;
};

// interface functions
};




Then in main, I create a game class. In game's constructor, game sets up its pointers to all the other singleton classes.

main.cpp

#include "Game.h"
#include "Log.h"
#undef main

int main (int argc, char *argv[]) {
// just to be sure
atexit(SDL_Quit);

Game* Game;

try {
Game = Game->GetInstance(); // main game class
} catch(...) {
Log::Write("CRITICAL ERROR! Termination application");
cout << "CRITICAL ERROR! Termination application"; // if the log class didnt manage to load
getch();
return -1;
}

Game->MainLoop(); // if all the loading went ok, enter main loop

Log::Write("Back in main.cpp, exiting program");
// program successful
return 0;
}

Share this post


Link to post
Share on other sites
Quote:
Original post by Mizipzor
The program '[2088] TileSystem.exe: Native' has exited with code 1 (0x1).

Anyone knows what that means? That number 2088 differs a little for everytime I try to run.


2088 seems to be the process id, you can check this with the task manager, if you make sure that the pid column is displayed.

Exit code 1 means, that your main function (or another function that calls the exit() function) returns 1. This is usually done to indicate an error.

Quote:

I started the debugger (havent really used a compilers debugger function until now) but I "stepped in" in all the function main executed in order. All went well until I hit this line:

m_pInstance = new Game();

Which is a part of the singleton pattern so I have only one instance of the class.


// Singleton ---
static Game* GetInstance( void ) {
if ( !m_pInstance )
m_pInstance = new Game();
return m_pInstance;
};


When I hit that line the debugger stops and I get the same result as before, I see no windows created, I get no compiler errors, the log is empty (the game class is created first, then the log and the rest). The only thing I have to go on is that little line the ouput gives me.

Im using Microsoft Visual .Net, anyone knows any good documentation for how to use the debugger? Or a debugger in general, as I guess thats what I need to use if I want to solve this one.

Anyone knows what could be wrong?


What does the constructor of Game do ? Maybe it tries to allocate some resources, load files, etc. which is not available, then calls exit(1).
Usually exceptions are used to handle those errors, since they give more control over the reaction to the error.

Share this post


Link to post
Share on other sites
Quote:
Original post by Pipo DeClown
Can a static function access membervariables? Please enlighten me.


Yes, it can. Static functions don't have an (implicit) this pointer, but if they have a pointer to an instance of the type they are from, they can access the members, no matter of the protection of those members (i.e. public/protected/private).

Share this post


Link to post
Share on other sites
Yes the constructor tries to get some resources:


Game::Game() {
// find out where the one and only instance of the classes are
try {
Sdl = Sdl->GetInstance();
AsciiMap = AsciiMap->GetInstance();
Font = Font->GetInstance();
Console = Console->GetInstance();
} catch (...) {throw;} // throw back to main


Sdl->SetScreenProperties( RESX, RESY, 32 ); // set screen res

// setup initial player position
Player.SetPos(30, 20);

// the app is running
running = true;

// write to log
Log::Write("Main game class created");
}




As you can see, Im using exception handling, if any of the other classes fails (and throws) I just exit... I dont want to run if everything isnt working. But as you probarly can see to, Im not very experienced with exception handling, I just catch and throws on :P. The constructors write to a global log file all the time so I look there what went wrong. Thing is... the logs empty now :S Dunno why...

[EDIT] Hmm main shouldnt be able to return a 1, look in my main.cpp that I posted *points upwards*, it returns -1 on failure and 0 on success...

Share this post


Link to post
Share on other sites
Is the class Sdl a wrapper for the SDL library ? Does it contain a call to exit(), or do the other classes AsciiMap, Font, Console contain such a call ?

The exception handling you have done is correct. Your main function should not return 1. I don't think that -1 would be converted to +1, but just to make sure you can return -2 instead.

Edit:
Another such function is abort().

Share this post


Link to post
Share on other sites
Yes its a wrapper, so I can say just "loadimage" or "drawimage" and do not have to worry about loading, storing and drawing them properly. That atexit(SDL_Quit); line in main is supposed to close sdl in the right way, its that what you meant?

Share this post


Link to post
Share on other sites
No, the functions registered with atexit() are called after the call to exit(), and they don't have a return value.

I meant a call like

exit(1);

or

abort(1);

Share this post


Link to post
Share on other sites
No nothing like that... I wanted the application to have the only way to shutdown to be through main (so all is logged).

No exit(1) stuff.

[EDIT] I tried to run the application a couple of times, the console window pops up but it closes instantly, I think there are two lines there. I open a command prompt to run it (so the window didnt close when the program was done). But when I ran it there it did just lock... :/ Those two lines may be a clue, any idea how to get them?

[EDIT2] I made my own way of trying to locate the error :P

main.cpp

int main (int argc, char *argv[]) {
// just to be sure
atexit(SDL_Quit);

getch();
Game* Game;
std::cout << "Game class created\n";

getch();
try {
Game = Game->GetInstance(); // main game class
} catch(...) {
Log::Write("CRITICAL ERROR! Termination application");
cout << "CRITICAL ERROR! Termination application"; // if the log class didnt manage to load
getch();
system("PAUSE");
return -2;
}
std::cout << "Game instance created\n";

getch();
if(!Game->LoadImages())
return -2; // failed to load bmp's

std::cout << "Images loaded\n";

getch();
Game->MainLoop(); // if all the loading went ok, enter main loop
std::cout << "Game loop entered\n";

getch();
Log::Write("Back in main.cpp, exiting program");
// program successful
std::cout << "Done\n";
return 0;
}





Getch() and cout hehe... I got it confirmed that it is in the line where the Game class is created (in its constructor). So I placed a line there cout << "Inside game constructor", to see if it did enter the constructor. When I ran the program that line filled the screen :S Like it ran the constructor one hundred times! I really dont know whats wrong, havent see anything like this before. And the constructor and everything used to work, I cant recall what Ive changed. :/

[EDIT3] Hehe here I am talking to myself :P I solved the problem. It was the console class. In console's constructor we got:

Console::Console() {
Font = Font->GetInstance(); // we want to draw text
Sdl = Sdl->GetInstance(); // graphic control
Game = Game->GetInstance();
}

It wants a game instance to send the console messages to. So Im calling game's constructor from within the constructor :P Hehe... Thats why that line filled the screen.

I changed to this:

Console::Console() {
Font = Font->GetInstance(); // we want to draw text
Sdl = Sdl->GetInstance(); // graphic control
Game = NULL; // were called from the game constructor, we cant run it again
}

And in the Console::Call(); function, which calls (shows) the console:

if(Game == NULL) // if we dont yet have the instance
Game = Game->GetInstance(); // create it

It works now but is that the best way to solve it?

[Edited by - Mizipzor on July 11, 2005 4:17:44 AM]

Share this post


Link to post
Share on other sites
Quote:
Original post by Mizipzor
It works now but is that the best way to solve it?


First of all, using cout to display debugging messages is bad, since cout buffers output. So either flush cout after the message, or use cerr (or clog) for debugging.

The next thing are global objects. Since the objects are available from everywhere, it is easy to create a cyclic dependency between those objects by accident. One thing to solve this is to have an init() function, that must be called before the object can be used. The constructor only initialises the internal state of the object, i.e. variables that depend in no way on other objects. So the initialisation is a two step approach, first create the object via its ctor, second initialise it via init().
(Singletons hide cyclic dependency between objects.)

Another way to manage those global objects is to put them into one single class, lets call it 'Globals'. The order of initialisation of objects in this class is determined by the standard, so you don't have to use singletons. Then there is only one instance of Globals, so you can use the objects in this class without a helper function like getInstance(). (BTW its always good to keep all global objects at one place.)

Its also possible to have no global objects at all (and no singletons). I think this will also lead to a better design. So if you can do it this way, go for it. Object dependency is like a tree. There is not a case such as the game needs the console to write messages, but the console needs the game to actually show them. You create your main class (you called it Game) either via new, or as a local object in main(). The ctor of that class then creates the other objects and so on.

Share this post


Link to post
Share on other sites
Ok... ill try to move all objects in a GlobalObjects class, then get rid of all the singleton stuff and make the Global class have functions to retrieve the instance of each object.

Thanks for all your help. :)

[edit] You mean like this? Quite ugly code though... I must say :P


#ifndef _GLOBAL_OBJECTS
#define _GLOBAL_OBJECTS

#include "AsciiMap.h"
#include "Console.h"
#include "FontSystem.h"
#include "SdlHandle.h"

class GlobalObjects {
private:
// all the objects needed for the game
AsciiMap AsciiMap;
Console Console;
FontSystem FoFontSystemnt;
SdlHandle SdlHandle;

public:
// get the instance of every class
AsciiMap* GetAsciiMapInstance (&AsciiMap );
Console* GetConsoleInstance (&Console );
FontSystem* GetFontSystemInstance (&FontSystem );
SdlHandle* GetSdlHandleInstance (&SdlHandle );
};

#endif


Share this post


Link to post
Share on other sites
Yes, something like that. But you may want to return references instead of pointers. (Or you can make those members public.) The functions for getting the global objects should be inline functions, so the compiler can optimise this, as if there wasn't any function call.

Another thing you need to do is how to obtain the instance of GlobalObjects. Either create an (inline) function, that returns a reference to the global object like this:

inline GlobalObjects& getGlobals() {
extern GlobalObjects globals; // define it in some .cc file
return globals;
}


Or you can just assume that it has a fixed name, and access it directly by this name.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this