Jump to content
  • Advertisement
Sign in to follow this  
wrt

Segmentation fault when using cdecl on linux

This topic is 4240 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

hi there, i'm trying to integrate angelscript into my robot simulation I'm doing as a project for school. When i try to use a function with cdecl my app crashes with a segfault. Generic works however. I'm propably doing something quite stupid ... here's my code:
RobotScript::RobotScript()
{
	engine = asCreateScriptEngine(ANGELSCRIPT_VERSION);
        if( engine == 0 )
        {
                cout << "Failed to create script engine." << endl;
        }
	
	// The script compiler will write any compiler messages to the callback.
        engine->SetMessageCallback(asFUNCTION(MessageCallback), 0, asCALL_CDECL);
	
	if( !strstr(asGetLibraryOptions(), "AS_MAX_PORTABILITY") )
	{
		cout << "a" << endl;
		RegisterScriptString(engine);
		engine->RegisterGlobalFunction("void printText(int &in)", asFUNCTION(printText_Generic), asCALL_GENERIC);
		engine->RegisterGlobalFunction("void printNumber(int &in)", asFUNCTION(printNumber), asCALL_CDECL);
	}
	else
	{
		cout << "b" << endl;
	}
}

RobotScript::~RobotScript()
{
	 // Release the engine
        engine->Release();
}

void RobotScript::addFunction(string code)
{
	engine->AddScriptSection(0, "test", code.c_str(), code.size());
	if (engine->Build(0) < 0)
	{
		cout << "couldnt compile" << endl;
	}
	cout << "Source added" << endl;
}

int RobotScript::runFunction(string id)
{
	ctx = engine->CreateContext();
	
	int funcId = engine->GetFunctionIDByDecl(0, id.c_str());
	if (funcId < 0)
	{
		cout << "Function not found" << endl;
		return -2;
	}
	
	int r = ctx->Prepare(funcId);
	if( r < 0 ) 
	{
		cout << "Failed to prepare the context." << endl;
		ctx->Release();
		return -1;
	}
	cout << "Executing:" << endl;
	r = ctx->Execute();
	if( r != asEXECUTION_FINISHED )
	{
		// The execution didn't finish as we had planned. Determine why.
		if( r == asEXECUTION_ABORTED )
			cout << "The script was aborted before it could finish. Probably it timed out." << endl;
		else if( r == asEXECUTION_EXCEPTION )
		{
			cout << "The script ended with an exception." << endl;

			// Write some information about the script exception
			int funcID = ctx->GetExceptionFunction();
			cout << "func: " << engine->GetFunctionDeclaration(funcID) << endl;
			cout << "modl: " << engine->GetFunctionModule(funcID) << endl;
			cout << "sect: " << engine->GetFunctionSection(funcID) << endl;
			cout << "line: " << ctx->GetExceptionLineNumber() << endl;
			cout << "desc: " << ctx->GetExceptionString() << endl;
		}
		else
			cout << "The script ended for some unforeseen reason (" << r << ")." << endl;
	}
	else
	{
		// Retrieve the return value from the context
		//float returnValue = ctx->GetReturnFloat();
		//cout << "The script function returned: " << returnValue << endl;
	}
	
	ctx->Release();
	
	return 0;
}

void RobotScript::deleteFunction(string id)
{
	/// \todo 1 implement this
}

void MessageCallback(const asSMessageInfo *msg, void *param)
{
	const char *type = "ERR ";
	if( msg->type == asMSGTYPE_WARNING ) 
		type = "WARN";
	else if( msg->type == asMSGTYPE_INFORMATION ) 
		type = "INFO";

	printf("%s (%d, %d) : %s : %s\n", msg->section, msg->row, msg->col, type, msg->message);
}

void printText(string &text)
{
	cout << "Script: "<< text << endl;
}

void printText()
{
	cout << "Script works ... " << endl;
}

// Function implementation with generic script interface
void printText_Generic(asIScriptGeneric *gen)
{
	int *str = (int*)gen->GetArgAddress(0);
	cout << "blub" << *str<< endl;
}

void printNumber(int &zahl)
{
	cout << "Script: " << zahl << endl;
}

the segmentation fault occurs at this place acording to gdb:
asm("pushl %ecx           \n"
                "movl  12(%ebp), %ecx \n" // paramSize
                "movl  8(%ebp), %eax  \n" // args
                "addl  %ecx, %eax     \n" // push arguments on the stack
                "cmp   $0, %ecx       \n"
                "je    endcopy        \n"
                "copyloop:            \n"
                "subl  $4, %eax       \n"
                "pushl (%eax)         \n"
                "subl  $4, %ecx       \n"
                "jne   copyloop       \n"
                "endcopy:             \n"
                "call  *16(%ebp)      \n"
                "addl  12(%ebp), %esp \n" // pop arguments
                "popl  %ecx           \n");

in this function: void CallCDeclFunction(const asDWORD *args, int paramSize, size_t func) I'm using CCux-linux, which is a i686 optimised distribution running on athlon XP prozessor. compiler flaggs are: -march=i686 -pipe -fomit-frame-pointer if any other informations could help you please don't hesitate to ask. cu and thanks for your time Simon

Share this post


Link to post
Share on other sites
Advertisement
Which function is the script calling when it crashes? printNumber?

Sounds like the calling conventions on your configuration is different from what AngelScript has been prepared for. The flag -fomit-frame-pointer is one likely cause, give it a try without this flag and see if it works.

Can you show me the disassembly of a call to the printNumber function made from the C++ code? It might give me some hints on what the difference is.

Share this post


Link to post
Share on other sites
thanks a lot

you were right about the "-fomit-frame-pointer", now it works just fine

cu Simon

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

Participate in the game development conversation and more when you create an account on GameDev.net!

Sign me up!