static int idbg_setstackitem( SGS_CTX ) { sgs_Bool full = 0; sgs_Int off, cnt; sgs_Variable* a, *b, *x, tmp; SGS_IDBG = (sgs_IDbg*) C->msg_ctx; SGSFN( "dbg_setstackitem" ); if( !sgs_LoadArgs( C, "i?v|b", &off, &full ) ) return 0; a = full ? C->stack_base : C->stack_base + D->stkoff; b = C->stack_base + D->stksize; cnt = b - a; if( off >= cnt || -off > cnt ) { sgs_Msg( C, SGS_WARNING, "index %d out of bounds, count = %d\n", (int) off, (int) cnt ); return 0; } x = off >= 0 ? a + off : b + off; tmp = *x; sgs_Acquire( C, &tmp ); sgs_GetStackItem( C, 1, x ); sgs_Release( C, &tmp ); return 0; }
int ss_Free() { SGS_CTX = g_C; /* clean the application */ if( SGS_FAILED( sgs_GlobalCall( C, "cleanup", 0, 0 ) ) ) { sgs_Msg( C, SGS_ERROR, "Failed to clean the application." ); return -1; } sgs_membuf_destroy( &g_tmpbuf, C ); if( GEnabledProfiler ) { sgs_ProfDump( C, &P ); sgs_ProfClose( C, &P ); } if( GEnabledDebugging ) sgs_CloseIDbg( C, &D ); sgs_DestroyEngine( C ); ss_FreeGraphics( C ); return 0; }
sgsVariable BulletDynamicsWorld::rayTestAll( const btVector3& from, const btVector3& to, int group, int mask ) { if( from == to ) { sgs_Msg( C, SGS_WARNING, "from / to positions cannot match" ); return sgsVariable(); } int ssz = sgs_StackSize( C ); if( ssz < 3 ) group = btBroadphaseProxy::DefaultFilter; if( ssz < 4 ) mask = btBroadphaseProxy::AllFilter; btCollisionWorld::AllHitsRayResultCallback ahrrc( from, to ); ahrrc.m_collisionFilterGroup = group; ahrrc.m_collisionFilterMask = mask; m_world->rayTest( from, to, ahrrc ); if( ahrrc.hasHit() ) { int i = 0; for( ; i < ahrrc.m_collisionObjects.size(); ++i ) { sgs_PushVar( C, ahrrc.m_hitFractions[ i ] ); sgs_PushVar( C, (BulletCollisionObjectPointer) ahrrc.m_collisionObjects[ i ] ); sgs_PushVar( C, ahrrc.m_hitNormalWorld[ i ] ); sgs_PushVar( C, ahrrc.m_hitPointWorld[ i ] ); sgs_CreateArray( C, NULL, 4 ); } sgs_CreateArray( C, NULL, i ); return sgsVariable( C, -1 ); } return sgsVariable(); }
int ss_Frame() { SGS_CTX = g_C; if( sgs_GlobalInt( C, "sys_exit" ) ) return 1; { int wait = sgs_GlobalBool( C, "sys_wait_events" ); SDL_Event event; while( wait ? SDL_WaitEvent( &event ) : SDL_PollEvent( &event ) ) { int ssz = sgs_StackSize( C ); if( event.type == SDL_KEYDOWN && event.key.state == SDL_PRESSED && event.key.keysym.sym == SDLK_F4 && ( event.key.keysym.mod & KMOD_ALT ) ) { sgs_ExecString( C, "global sys_exit = true;" ); break; } ss_CreateSDLEvent( C, &event ); if( SGS_FAILED( sgs_GlobalCall( C, "on_event", 1, 0 ) ) ) { sgs_Msg( C, SGS_ERROR, "error in event creation" ); sgs_Pop( C, sgs_StackSize( C ) - ssz ); // provide default handler if( event.type == SDL_QUIT ) { sgs_ExecString( C, "global sys_exit = true;" ); return 1; } } } if( sgs_GlobalInt( C, "sys_exit" ) ) return 1; /* advance the application exactly one frame */ if( SGS_FAILED( sgs_GlobalCall( C, "update", 0, 0 ) ) ) { sgs_Msg( C, SGS_ERROR, "Failed to update the application." ); return -1; } } return 0; }
static int Bullet_CreateBVHTriangleMeshShape( SGS_CTX ) { sgs_Bool qbbc = 0, build = 1; SGSFN( "Bullet_CreateBVHTriangleMeshShape" ); if( !sgs_LoadArgs( C, ">|bb", &qbbc, &build ) ) return 0; BulletStridingMeshInterfaceHandle bsmih = sgs_GetVar<BulletStridingMeshInterfaceHandle>()( C, 0 ); if( !bsmih.obj ) return sgs_Msg( C, SGS_WARNING, "argument 1 must be a striding mesh interface object" ); SGS_CREATECLASS( C, NULL, BulletBVHTriangleMeshShape, ( bsmih, qbbc, build ) ); return 1; }
void BulletDynamicsWorld::removeRigidBody( BulletRigidBodyHandle rbh ) { if( !rbh.not_null() ) { sgs_Msg( C, SGS_WARNING, "argument 1 must be a rigid body" ); return; } if( rbh->m_world == this ) { m_world->removeRigidBody( rbh->rigidBody() ); rbh->m_world = NULL; } }
void BulletDynamicsWorld::updateSingleAABB( sgsVariable colObj ) { BulletCollisionObject* coptr = NULL; if( colObj.is_handle< BulletRigidBody >() ) coptr = colObj.get_object_data< BulletRigidBody >(); else if( colObj.is_handle< BulletGhostObject >() ) coptr = colObj.get_object_data< BulletGhostObject >(); else { sgs_Msg( C, SGS_WARNING, "argument 1 must be a rigid body / ghost object" ); return; } m_world->updateSingleAabb( coptr->m_colObj ); }
SGS_MULTRET BulletDynamicsWorld::convexSweepTestClosest( BulletConvexShapePointer bcsp, const BulletTransform& from, const BulletTransform& to, int group, int mask, float alcp ) { if( !bcsp ) return sgs_Msg( C, SGS_WARNING, "argument 1 must be a convex shape" ); if( from.getOrigin() == to.getOrigin() ) return sgs_Msg( C, SGS_WARNING, "from / to positions cannot match" ); int ssz = sgs_StackSize( C ); if( ssz < 4 ) group = btBroadphaseProxy::DefaultFilter; if( ssz < 5 ) mask = btBroadphaseProxy::AllFilter; btCollisionWorld::ClosestConvexResultCallback ccrc( from.getOrigin(), to.getOrigin() ); ccrc.m_collisionFilterGroup = group; ccrc.m_collisionFilterMask = mask; m_world->convexSweepTest( bcsp, from, to, ccrc, alcp ); if( ccrc.hasHit() ) { sgs_PushVar( C, ccrc.m_closestHitFraction ); sgs_PushVar( C, (BulletCollisionObjectPointer) ccrc.m_hitCollisionObject ); sgs_PushVar( C, ccrc.m_hitNormalWorld ); sgs_PushVar( C, ccrc.m_hitPointWorld ); return 4; } return 0; }
void BulletDynamicsWorld::addRigidBody( BulletRigidBodyHandle rbh, int group, int mask ) { int ssz = sgs_StackSize( C ); if( ssz < 2 ) group = btBroadphaseProxy::DefaultFilter; if( ssz < 3 ) mask = btBroadphaseProxy::AllFilter; if( !rbh.not_null() ) { sgs_Msg( C, SGS_WARNING, "argument 1 must be a rigid body" ); return; } if( rbh->m_world ) m_world->removeRigidBody( rbh->rigidBody() ); m_world->addRigidBody( rbh->rigidBody(), group, mask ); rbh->m_world = this; }
void BulletDynamicsWorld::removeCollisionObject( sgsVariable colObj ) { BulletCollisionObject* coptr = NULL; if( colObj.is_handle< BulletRigidBody >() ) coptr = colObj.get_object_data< BulletRigidBody >(); else if( colObj.is_handle< BulletGhostObject >() ) coptr = colObj.get_object_data< BulletGhostObject >(); else { sgs_Msg( C, SGS_WARNING, "argument 1 must be a rigid body / ghost object" ); return; } if( coptr->m_world == this ) { m_world->removeCollisionObject( coptr->m_colObj ); coptr->m_world = NULL; } }
void BulletDynamicsWorld::addCollisionObject( sgsVariable colObj, int group, int mask ) { int ssz = sgs_StackSize( C ); if( ssz < 2 ) group = btBroadphaseProxy::DefaultFilter; if( ssz < 3 ) mask = btBroadphaseProxy::AllFilter; BulletCollisionObject* coptr = NULL; if( colObj.is_handle< BulletRigidBody >() ) coptr = colObj.get_object_data< BulletRigidBody >(); else if( colObj.is_handle< BulletGhostObject >() ) coptr = colObj.get_object_data< BulletGhostObject >(); else { sgs_Msg( C, SGS_WARNING, "argument 1 must be a rigid body / ghost object" ); return; } if( coptr->m_world ) m_world->removeCollisionObject( coptr->m_colObj ); m_world->addCollisionObject( coptr->m_colObj, group, mask ); coptr->m_world = this; }
static int socket_geterrnobyname( SGS_CTX ) { const char** ekt = socket_errno_key_table; char* str; SGSFN( "socket_geterrnobyname" ); if( !sgs_LoadArgs( C, "s", &str ) ) return 0; while( *ekt ) { if( strcmp( *ekt, str ) == 0 ) { sgs_PushInt( C, (int) (size_t) ekt[1] ); return 1; } ekt += 2; } sgs_Msg( C, SGS_ERROR, "this socket errno value is unsupported on this platform" ); return 0; }
static int idbg_stackitem( SGS_CTX ) { sgs_Bool full = 0; sgs_Int off, cnt; sgs_Variable* a, *b; SGS_IDBG = (sgs_IDbg*) C->msg_ctx; SGSFN( "dbg_stackitem" ); if( !sgs_LoadArgs( C, "i|b", &off, &full ) ) return 0; a = full ? C->stack_base : C->stack_base + D->stkoff; b = C->stack_base + D->stksize; cnt = b - a; if( off >= cnt || -off > cnt ) { sgs_Msg( C, SGS_WARNING, "index %d out of bounds, count = %d\n", (int) off, (int) cnt ); return 0; } sgs_PushVariable( C, off >= 0 ? a + off : b + off ); return 1; }
static void skipcomment( SGS_CTX, MemBuf* out, LineNum* line, const char* code, int32_t* at, int32_t length ) { int32_t i = *at + 1; UNUSED( out ); if( code[ i ] == '/' ) { i++; while( i < length && code[ i ] != '\n' && code[ i ] != '\r' ) i++; if( code[ i ] == '\r' && code[ i + 1 ] == '\n' ) i++; (*line)++; *at = i; } else { LineNum init = *line; i++; while( i < length ) { if( detectline( code, i ) ) (*line)++; if( code[ i ] == '/' && i > 0 && code[ i - 1 ] == '*' ) break; else i++; } if( i == length ) { sgs_Msg( C, SGS_ERROR, "[line %d] Comment has no end", init ); *at = i - 1; } else *at = i; } }
static int sockaddr_getindex( SGS_CTX, sgs_VarObj* data, sgs_Variable* key, int prop ) { char* name; if( sgs_ParseStringP( C, key, &name, NULL ) ) { if( STREQ( name, "family" ) ){ sgs_PushInt( C, GET_SAF ); return SGS_SUCCESS; } if( STREQ( name, "port" ) ) { if( GET_SAF == AF_INET ){ sgs_PushInt( C, ntohs( GET_SAI->sin_port ) ); } else if( GET_SAF == AF_INET6 ){ sgs_PushInt( C, ntohs( GET_SAI6->sin6_port ) ); } else { sgs_PushNull( C ); sgs_Msg( C, SGS_WARNING, "port supported only for AF_INET[6]" ); } return SGS_SUCCESS; } if( STREQ( name, "addr_u32" ) ) { if( GET_SAF == AF_INET ){ sgs_PushInt( C, ntohl( GET_SAI->sin_addr.s_addr ) ); } else { sgs_PushNull( C ); sgs_Msg( C, SGS_WARNING, "addr_u32 supported only for AF_INET" ); } return SGS_SUCCESS; } if( STREQ( name, "addr_buf" ) ) { if( GET_SAF == AF_INET ){ sgs_PushStringBuf( C, (char*) &GET_SAI->sin_addr.s_addr, 4 ); } else if( GET_SAF == AF_INET6 ){ sgs_PushStringBuf( C, (char*) &GET_SAI6->sin6_addr.s6_addr, 16 ); } else { sgs_PushNull( C ); sgs_Msg( C, SGS_WARNING, "addr_buf supported only for AF_INET[6]" ); } return SGS_SUCCESS; } if( STREQ( name, "addr_bytes" ) ) { char* buf = NULL; int i, sz = 0; if( GET_SAF == AF_INET ) { buf = (char*) &GET_SAI->sin_addr.s_addr; sz = 4; } else if( GET_SAF == AF_INET6 ) { buf = (char*) &GET_SAI6->sin6_addr.s6_addr; sz = 16; } if( buf ) { for( i = 0; i < sz; ++i ) sgs_PushInt( C, buf[ i ] ); sgs_PushArray( C, sz ); } else { sgs_PushNull( C ); sgs_Msg( C, SGS_WARNING, "addr_bytes supported only for AF_INET[6]" ); } return SGS_SUCCESS; } if( STREQ( name, "addr_string" ) ) { char addr[ 64 ] = {0}; #ifdef _WIN32 DWORD ioasz = 64; WSAAddressToString( (LPSOCKADDR) data->data, sizeof(struct sockaddr_storage), NULL, addr, &ioasz ); *strrchr( addr, ':' ) = 0; #else if( GET_SAF == AF_INET ) inet_ntop( GET_SAF, &GET_SAI->sin_addr, addr, 64 ); else if( GET_SAF == AF_INET6 ) inet_ntop( GET_SAF, &GET_SAI6->sin6_addr, addr, 64 ); #endif addr[ 64-1 ] = 0; if( *addr ) sgs_PushString( C, addr ); else sgs_PushString( C, "-" ); return SGS_SUCCESS; } if( STREQ( name, "full_addr_string" ) ) { sockaddr_push_full_addr_string( C, data ); return SGS_SUCCESS; } } return SGS_ENOTFND; }
int ss_Initialize( int argc, char* argv[], int debug ) { int ret; SGS_CTX; GEnabledDebugging = debug; #if SS_STARTUP_PROFILING printf( "ss_Initialize called: %f\n", sgs_GetTime() ); #endif C = g_C = sgs_CreateEngine(); #if SS_STARTUP_PROFILING printf( "SGS engine created: %f\n", sgs_GetTime() ); #endif if( GEnabledDebugging ) sgs_InitIDbg( C, &D ); else sgs_SetMsgFunc( C, ss_MsgFunc, NULL ); #if SS_STARTUP_PROFILING printf( "debug printing initialized: %f\n", sgs_GetTime() ); #endif /* preinit first-use libs */ sgs_LoadLib_Fmt( C ); sgs_LoadLib_IO( C ); sgs_LoadLib_Math( C ); sgs_LoadLib_OS( C ); sgs_LoadLib_RE( C ); sgs_LoadLib_String( C ); #if SS_STARTUP_PROFILING printf( "SGS libraries loaded: %f\n", sgs_GetTime() ); #endif ss_InitDebug( C ); ss_InitExtMath( C ); ss_InitImage( C ); #if SS_STARTUP_PROFILING printf( "SS libraries loaded: %f\n", sgs_GetTime() ); #endif /* preinit tmp buffer */ g_tmpbuf = sgs_membuf_create(); sgs_membuf_reserve( &g_tmpbuf, C, 1024 ); /* load command line arguments */ { int i; for( i = 0; i < argc; ++i ) { sgs_PushString( C, argv[ i ] ); } sgs_CreateArray( C, NULL, argc ); sgs_SetGlobalByName( C, "sys_args", sgs_StackItem( C, -1 ) ); sgs_Pop( C, 1 ); } /* push some system info */ sgs_SetGlobalByName( C, "sys_scripting_engine", sgs_MakePtr( C ) ); #if SS_STARTUP_PROFILING printf( "system info pushed: %f\n", sgs_GetTime() ); #endif /* run the preconfig script */ sgs_ExecString( C, scr_preconfig ); #if SS_STARTUP_PROFILING printf( "preconfig done: %f\n", sgs_GetTime() ); #endif /* run the config file */ ret = sgs_Include( C, "core/config" ); if( !ret ) { sgs_Msg( C, SGS_ERROR, "Could not run core/config (configuration script)." ); return -2; } /* run the primary extensions */ ret = sgs_Include( C, "core/ext" ); if( !ret ) { sgs_Msg( C, SGS_ERROR, "Could not run core/ext." ); return -2; } #if SS_STARTUP_PROFILING printf( "configured engine scripts: %f\n", sgs_GetTime() ); #endif /* run the main file */ ret = sgs_Include( C, "main" ); if( !ret ) { sgs_Msg( C, SGS_ERROR, "Could not execute 'main'." ); return -3; } #if SS_STARTUP_PROFILING printf( "ran main script: %f\n", sgs_GetTime() ); #endif /* configure the framework (optional) */ sgs_GlobalCall( C, "configure", 0, 0 ); #if SS_STARTUP_PROFILING printf( "called 'configure': %f\n", sgs_GetTime() ); #endif /* check if already required to exit */ if( sgs_GlobalBool( C, "sys_exit" ) ) return 0; if( GEnabledProfiler ) sgs_ProfInit( C, &P, GEnabledProfiler ); #if SS_STARTUP_PROFILING printf( "pre-SDL init: %f\n", sgs_GetTime() ); #endif /* initialize SDL */ if( SDL_Init( SDL_INIT_TIMER | SDL_INIT_VIDEO | SDL_INIT_JOYSTICK | SDL_INIT_HAPTIC | SDL_INIT_GAMECONTROLLER | SDL_INIT_EVENTS | SDL_INIT_NOPARACHUTE ) < 0 ) { sgs_Msg( C, SGS_ERROR, "Couldn't initialize SDL: %s", SDL_GetError() ); return -5; } SDL_GL_SetAttribute( SDL_GL_RED_SIZE, 8 ); SDL_GL_SetAttribute( SDL_GL_GREEN_SIZE, 8 ); SDL_GL_SetAttribute( SDL_GL_BLUE_SIZE, 8 ); SDL_GL_SetAttribute( SDL_GL_DOUBLEBUFFER, 1 ); #if SS_STARTUP_PROFILING printf( "post-SDL init: %f\n", sgs_GetTime() ); #endif /* initialize script-space SDL API */ ss_InitSDL( C ); /* initialize script-space rendering API */ ss_InitGraphics( C ); #if SS_STARTUP_PROFILING printf( "initialized SDL/Graphics subsystems: %f\n", sgs_GetTime() ); #endif /* initialize the application */ if( SGS_FAILED( sgs_GlobalCall( C, "initialize", 0, 0 ) ) ) { sgs_Msg( C, SGS_ERROR, "Failed to initialize the application." ); return -8; } #if SS_STARTUP_PROFILING printf( "called 'initialize': %f\n", sgs_GetTime() ); #endif return 1; }
int SS3D_PushRenderer_GL( SGS_CTX ) { return sgs_Msg(C,SGS_ERROR,"TODO [GL renderer]"); }