static otto DaoPF10002( int *_cs, DaoMethod *_ro, DaoObject *_ob, const otto& value ) { DaoValue *_dp[1] = { NULL }; DaoValue *_res; DaoCdata *_cd; DaoProcess *_vmp; otto _test = 0; if( _ro == NULL ) goto EndCall; _dp[0] = DaoValue_WrapCdata( dao_otto_Typer, (void*) &value ); _ro = DaoMethod_Resolve( _ro, (DaoValue*)_ob, _dp, 1 ); if( DaoValue_CastRoutine( (DaoValue*)_ro ) == NULL ) goto EndCall; _vmp = DaoVmSpace_AcquireProcess( __daoVmSpace ); if( (*_cs = DaoProcess_Call( _vmp, _ro, (DaoValue*)_ob, _dp, 1 )) ==0 ) goto EndCall; _res = DaoProcess_GetReturned( _vmp ); DaoVmSpace_ReleaseProcess( __daoVmSpace, _vmp ); if( DaoValue_CastObject(_res) ) _res = (DaoValue*)DaoObject_MapCdata( (DaoObject*)_res, dao_otto_Typer ); if( DaoValue_CastCdata(_res) && DaoCdata_IsType( (DaoCdata*)_res, dao_otto_Typer ) ){ _test = *(otto*) DaoValue_TryCastCdata( _res, dao_otto_Typer ); } EndCall: DaoValue_ClearAll( _dp, 1 ); return _test; }
void DaoCallServer_AddCall( DaoProcess *caller ) { DaoProcess *callee = DaoVmSpace_AcquireProcess( caller->vmSpace ); DaoStackFrame *frame = caller->topFrame; DaoTaskEvent *event = DaoCallServer_MakeEvent(); DaoType *type = (DaoType*) frame->routine->routType->aux; DaoFuture *future = DaoFuture_New( type, 1 ); DaoValue **params = caller->stackValues + caller->topFrame->stackBase; int i, count = caller->topFrame->parCount; future->state = DAO_CALL_PAUSED; future->actor = caller->topFrame->object; GC_IncRC( future->actor ); GC_ShiftRC( future, callee->future ); callee->future = future; future->process = callee; GC_IncRC( future->process ); callee->parCount = count; for(i=0; i<count; ++i) DaoValue_Copy( params[i], & callee->paramValues[i] ); DaoProcess_PushRoutine( callee, caller->topFrame->routine, future->actor ); DaoTaskEvent_Init( event, DAO_EVENT_RESUME_TASKLET, DAO_EVENT_RESUME, future, NULL ); DaoProcess_PopFrame( caller ); DaoProcess_PutValue( caller, (DaoValue*) future ); DaoCallServer_Add( event ); }
static void DaoPF10001( int *_cs, DaoMethod *_ro, DaoObject *_ob ) { if( _ro == NULL ) return; _ro = DaoMethod_Resolve( _ro, (DaoValue*)_ob, NULL, 0 ); if( DaoValue_CastRoutine( (DaoValue*)_ro ) == NULL ) return; DaoProcess *_vmp = DaoVmSpace_AcquireProcess( __daoVmSpace ); *_cs = DaoProcess_Call( _vmp, _ro, (DaoValue*)_ob, NULL, 0 ); DaoVmSpace_ReleaseProcess( __daoVmSpace, _vmp ); }
void DaoCxxVirt_otto::vtest( int &_cs ) { DaoObject *_obj = NULL; DaoMethod *_ro = Dao_Get_Object_Method( cdata, & _obj, "vtest" ); if( _ro == NULL || _obj == NULL ) return; _ro = DaoMethod_Resolve( _ro, (DaoValue*)_obj, NULL, 0 ); if( DaoValue_CastRoutine( (DaoValue*)_ro ) == NULL ) return; DaoProcess *_vmp = DaoVmSpace_AcquireProcess( __daoVmSpace ); DaoProcess_Call( _vmp, _ro, (DaoValue*)_obj, NULL, 0 ); DaoVmSpace_ReleaseProcess( __daoVmSpace, _vmp ); }
static void DaoPF10004( int *_cs, DaoMethod *_ro, DaoObject *_ob, const Greeting& g ) { DaoValue *_dp[1] = { NULL }; if( _ro == NULL ) return; _dp[0] = DaoValue_WrapCdata( dao_Greeting_Typer, (void*) &g ); _ro = DaoMethod_Resolve( _ro, (DaoValue*)_ob, _dp, 1 ); if( DaoValue_CastRoutine( (DaoValue*)_ro ) == NULL ) return; DaoProcess *_vmp = DaoVmSpace_AcquireProcess( __daoVmSpace ); *_cs = DaoProcess_Call( _vmp, _ro, (DaoValue*)_ob, _dp, 1 ); DaoVmSpace_ReleaseProcess( __daoVmSpace, _vmp ); DaoValue_ClearAll( _dp, 1 ); }
DAO_DLL int DaoCGI_OnLoad( DaoVmSpace *vmSpace, DaoNamespace *ns ) { DaoProcess *process = DaoVmSpace_AcquireProcess( vmSpace ); DaoMap *httpENV, *httpGET, *httpPOST, *httpFILE, *httpCOOKIE; DaoMap *httpGETS, *httpPOSTS; srand( time(NULL) ); vmMaster = vmSpace; ns = DaoNamespace_GetNamespace( ns, "cgi" ); daox_type_namestream = DaoNamespace_DefineType( ns, "tuple<file:string,size:int,data:io::FileStream>", "HttpUpload" ); daox_type_filemap = DaoNamespace_DefineType( ns, "map<string,HttpUpload>", NULL ); DaoNamespace_WrapFunctions( ns, cgiMeths ); httpENV = DaoMap_New(1+rand()); httpGET = DaoMap_New(1+rand()); httpPOST = DaoMap_New(1+rand()); httpFILE = DaoMap_New(1+rand()); httpCOOKIE = DaoMap_New(1+rand()); httpGETS = DaoMap_New(1+rand()); httpPOSTS = DaoMap_New(1+rand()); DaoNamespace_AddValue( ns, "HTTP_ENV", (DaoValue*)httpENV, "map<string,string>" ); DaoNamespace_AddValue( ns, "HTTP_GET", (DaoValue*)httpGET, "map<string,string>" ); DaoNamespace_AddValue( ns, "HTTP_POST", (DaoValue*)httpPOST, "map<string,string>" ); DaoNamespace_AddValue( ns, "HTTP_FILE", (DaoValue*)httpFILE, "map<string,HttpUpload>" ); DaoNamespace_AddValue( ns, "HTTP_COOKIE", (DaoValue*)httpCOOKIE, "map<string,string>"); DaoNamespace_AddValue( ns,"HTTP_GETS",(DaoValue*)httpGETS,"map<string,list<string>>"); DaoNamespace_AddValue( ns,"HTTP_POSTS",(DaoValue*)httpPOSTS,"map<string,list<string>>"); // Prepare HTTP_ENV: ParseKeyValueStringArray( process, httpENV, environ ); // Prepare HTTP_GET: char *query = getenv( "QUERY_STRING" ); if( query == NULL ) { /* lighttpd does not set "QUERY_STRING": */ query = getenv( "REQUEST_URI" ); if( query ) query = strchr( query, '?' ); if( query ) query += 1; } if( query ) ParseKeyValueString( process, httpGETS, httpGET, query ); query = getenv( "HTTP_COOKIE" ); if( query ) ParseKeyValueString( process, NULL, httpCOOKIE, query ); PreparePostData( process, httpPOSTS, httpPOST, httpFILE ); DaoVmSpace_ReleaseProcess( vmSpace, process ); return 0; }
void DaoCstruct_CallMethod( DaoCstruct *cdata, const char *method ) { DaoObject *obj = NULL; DaoRoutine *rout = Dao_Get_Object_Method( cdata, & obj, method ); DaoValue *render = (DaoValue*) daox_current_renderer; DaoProcess *proc; if( rout == NULL || obj == NULL ) return; proc = DaoVmSpace_AcquireProcess( __daoVmSpace ); rout = DaoRoutine_Resolve( rout, (DaoValue*) obj, NULL, & render, NULL, 1, 0 ); if( rout == NULL ) goto Finalize; DaoProcess_Call( proc, rout, (DaoValue*) obj, & render, 1 ); Finalize: DaoVmSpace_ReleaseProcess( __daoVmSpace, proc ); }
static void DaoMT_Start( DaoProcess *proc, DaoValue *p[], int n ) { DaoProcess *clone; DaoVmCode *vmc, *end; DaoVmCode *sect = DaoGetSectionCode( proc->activeCode ); DaoType *type = DaoProcess_GetReturnType( proc ); DaoFuture *future = DaoFuture_New( type, 0 ); int entry, nop = proc->activeCode[1].code == DVM_NOP; DaoProcess_PutValue( proc, (DaoValue*) future ); if( sect == NULL || DaoMT_PushSectionFrame( proc ) == 0 ) return; entry = proc->topFrame->entry; end = proc->activeRoutine->body->vmCodes->data.codes + proc->activeCode[nop+1].b; clone = DaoVmSpace_AcquireProcess( proc->vmSpace ); DaoProcess_PopFrame( proc ); DaoProcess_SetActiveFrame( proc, proc->topFrame ); DaoMT_InitProcess( proc, clone ); clone->topFrame->entry = entry; /* // Use the cloned process instead of the parent process, in case that // the cloned process will not be joined by the parent process: */ clone->topFrame->outer = clone; future->process = clone; GC_IncRC( clone ); GC_ShiftRC( future, clone->future ); clone->future = future; future->state = DAO_CALL_RUNNING; for(vmc=sect; vmc!=end; vmc++){ int i = -1, code = vmc->code; if( code == DVM_GETVH || (code >= DVM_GETVH_I && code <= DVM_GETVH_C) ){ i = vmc->b; }else if( code == DVM_SETVH || (code >= DVM_SETVH_II && code <= DVM_SETVH_CC) ){ i = vmc->b; } if( i >= 0 ){ /* These values should be shared with the parent thread: */ GC_ShiftRC( proc->activeValues[i], clone->activeValues[i] ); clone->activeValues[i] = proc->activeValues[i]; } } DaoCallServer_AddTask( DaoMT_Start0, clone, p[0]->xEnum.value ); }
DaoCstruct* DaoxResource_CallMethod( DaoxResource *self, const char *method, DaoType *ctype ) { DaoValue *res = NULL; DaoObject *obj = NULL; DaoRoutine *rout = Dao_Get_Object_Method( (DaoCstruct*) self, & obj, method ); DaoProcess *proc; if( rout == NULL || obj == NULL ) return NULL; proc = DaoVmSpace_AcquireProcess( dao_vmspace_graphics ); rout = DaoRoutine_Resolve( rout, (DaoValue*) obj, NULL, NULL, NULL, 0, 0 ); if( rout == NULL ) goto Finalize; DaoProcess_Call( proc, rout, (DaoValue*) obj, NULL, 0 ); res = DaoProcess_GetReturned( proc ); if( res == NULL || res->type != DAO_OBJECT ) return NULL; return DaoObject_CastCstruct( (DaoObject*)res, ctype ); Finalize: DaoVmSpace_ReleaseProcess( dao_vmspace_graphics, proc ); return NULL; }
int DaoCstruct_CallKeyboardMethod( DaoCstruct *cdata, const char *method, int key, int x, int y ) { DaoObject *obj = NULL; DaoRoutine *rout = Dao_Get_Object_Method( cdata, & obj, method ); DaoProcess *proc; DaoValue **params; if( rout == NULL || obj == NULL ) return 0; proc = DaoVmSpace_AcquireProcess( __daoVmSpace ); DaoProcess_NewInteger( proc, (daoint) key ); DaoProcess_NewInteger( proc, (daoint) x ); DaoProcess_NewInteger( proc, (daoint) y ); params = DaoProcess_GetLastValues( proc, 3 ); rout = DaoRoutine_Resolve( rout, (DaoValue*) obj, NULL, params, NULL, 3, 0 ); if( rout == NULL ) goto Finalize; DaoProcess_Call( proc, rout, (DaoValue*) obj, params, 3 ); Finalize: DaoVmSpace_ReleaseProcess( __daoVmSpace, proc ); return rout != NULL; }
static int DaoPF10293( int *_cs, DaoRoutine *_ro, DaoObject *_ob, double t, const double* y, double* dydt, DaoValue *params ) { DaoProcess *_proc = DaoVmSpace_AcquireProcess( __daoVmSpace ); DaoValue *_res, **_dp; DaoCdata *_cd; int X = (int) 0; if( _ro == NULL ) goto EndCall; DaoProcess_NewFloat( _proc, (dao_float) t ); DaoProcess_NewVectorFloat64( _proc, (double*) y, 0 ); DaoProcess_NewVectorFloat64( _proc, (double*) dydt, 0 ); DaoProcess_CacheValue( _proc, params ); _dp = DaoProcess_GetLastValues( _proc, 4 ); _ro = DaoRoutine_ResolveByValue( _ro, (DaoValue*) _ob, _dp, 4 ); if( _ro == NULL || DaoRoutine_IsWrapper( _ro ) ) goto EndCall; if( (*_cs = DaoProcess_Call( _proc, _ro, (DaoValue*)_ob, _dp, 4 )) ) goto EndCall; _res = DaoProcess_GetReturned( _proc ); if(DaoValue_CastInteger(_res)) X=(int)DaoValue_TryGetInteger(_res); EndCall: DaoVmSpace_ReleaseProcess( __daoVmSpace, _proc ); return X; }
static void DaoMT_Start( DaoProcess *proc, DaoValue *p[], int n ) { DaoProcess *clone; DaoVmCode *vmc, *end, *sect; DaoType *type = DaoProcess_GetReturnType( proc ); DaoFuture *future = DaoFuture_New( type, 0 ); int entry, nop = proc->activeCode[1].code == DVM_NOP; DaoProcess_PutValue( proc, (DaoValue*) future ); sect = DaoProcess_InitCodeSection( proc, 0 ); if( sect == NULL ) return; entry = proc->topFrame->entry; end = proc->activeRoutine->body->vmCodes->data.codes + proc->activeCode[nop+1].b; clone = DaoVmSpace_AcquireProcess( proc->vmSpace ); DaoProcess_PopFrame( proc ); DaoMT_InitProcess( proc, clone, 0 ); clone->topFrame->entry = entry; /* // Use the cloned process instead of the parent process, in case that // the cloned process will not be joined by the parent process: */ clone->topFrame->outer = clone; future->process = clone; GC_IncRC( clone ); GC_Assign( & clone->future, future ); future->state = DAO_CALL_RUNNING; for(vmc=sect; vmc!=end; vmc++){ int i = -1, code = vmc->code; if( code == DVM_GETVH || (code >= DVM_GETVH_I && code <= DVM_GETVH_C) ){ i = vmc->b; }else if( code == DVM_SETVH || (code >= DVM_SETVH_II && code <= DVM_SETVH_CC) ){ i = vmc->b; } if( i >= 0 ) DaoValue_Move( proc->activeValues[i], & clone->activeValues[i], NULL ); } DaoCallServer_AddTask( DaoMT_Start0, clone, p[0]->xEnum.value ? clone : NULL ); }
void DaoCallServer_AddCall( DaoProcess *caller ) { DaoFuture *future; DaoTaskEvent *event; DaoProcess *callee = DaoVmSpace_AcquireProcess( caller->vmSpace ); DaoStackFrame *frame = caller->topFrame; DaoRoutine *routine = frame->routine; DaoType *type = (DaoType*) routine->routType->aux; DaoValue **params = caller->stackValues + caller->topFrame->stackBase; int i, count = caller->topFrame->parCount; if( caller->activeCode->b & DAO_CALL_BLOCK ){ DaoValue **calleeValues, **callerValues = caller->activeValues; DaoStackFrame *sectFrame = DaoProcess_FindSectionFrame( caller ); DaoStackFrame *callerFrame = caller->topFrame->prev; DaoVmCode *vmc, *end, *sect; if( sectFrame != callerFrame ){ DaoVmSpace_ReleaseProcess( caller->vmSpace, callee ); DaoProcess_RaiseError( caller, NULL, "Invalid code section" ); return; } if( routine->body ){ DaoProcess_PushRoutine( callee, callerFrame->routine, callerFrame->object ); callerValues = caller->stackValues + callerFrame->stackBase; }else{ DaoProcess_PushRoutine( callee, caller->activeRoutine, caller->activeObject ); } DaoProcess_SetActiveFrame( callee, callee->topFrame ); calleeValues = callee->stackValues + callee->topFrame->stackBase; callee->activeCode = caller->activeCode; vmc = callerFrame->routine->body->vmCodes->data.codes + callerFrame->entry; end = callerFrame->routine->body->vmCodes->data.codes + vmc->b; sect = vmc + 1; for(vmc=sect; vmc!=end; vmc++){ int i = -1, code = vmc->code; if( code == DVM_GETVH || (code >= DVM_GETVH_I && code <= DVM_GETVH_C) ){ i = vmc->b; }else if( code == DVM_SETVH || (code >= DVM_SETVH_II && code <= DVM_SETVH_CC) ){ i = vmc->b; } if( i >= 0 ) DaoValue_Move( callerValues[i], & calleeValues[i], NULL ); } } future = DaoFuture_New( type, 1 ); future->state = DAO_CALL_PAUSED; future->actor = caller->topFrame->object; GC_IncRC( future->actor ); GC_Assign( & future->process, callee ); GC_Assign( & callee->future, future ); callee->parCount = count; /* Use routine->parCount instead of caller->topFrame->parCount, for default parameters: */ for(i=0; i<routine->parCount; ++i) DaoValue_Copy( params[i], & callee->paramValues[i] ); if( routine->body ){ DaoProcess_PushRoutine( callee, routine, future->actor ); }else{ DaoProcess_PushFunction( callee, routine ); callee->activeNamespace = caller->activeNamespace; } if( caller->activeCode->b & DAO_CALL_BLOCK ){ callee->topFrame->host = callee->topFrame; callee->topFrame->retmode = DVM_RET_PROCESS; callee->topFrame->returning = 0; } #ifdef DAO_WITH_CONCURRENT DaoCallServer_TryInit( mainVmSpace ); event = DaoCallServer_MakeEvent(); DaoTaskEvent_Init( event, DAO_EVENT_RESUME_TASKLET, DAO_EVENT_RESUME, future, NULL ); DaoProcess_PopFrame( caller ); DaoProcess_PutValue( caller, (DaoValue*) future ); DaoCallServer_Add( event ); #else DaoProcess_PopFrame( caller ); DaoProcess_PutValue( caller, (DaoValue*) future ); DaoProcess_InterceptReturnValue( callee ); DaoProcess_Execute( callee ); DaoProcess_ReturnFutureValue( callee, future ); DaoVmSpace_ReleaseProcess( caller->vmSpace, callee ); #endif }
static void DaoMT_Functional( DaoProcess *proc, DaoValue *P[], int N, int F ) { DMutex mutex; DCondVar condv; DaoTaskData *tasks; DaoValue *param = P[0]; DaoValue *result = NULL; DaoList *list = NULL; DaoArray *array = NULL; DaoVmCode *sect = DaoGetSectionCode( proc->activeCode ); int i, entry, threads = P[1]->xInteger.value; daoint index = -1, status = 0, joined = 0; DNode *node = NULL; switch( F ){ case DVM_FUNCT_MAP : if( param->type == DAO_ARRAY ){ array = DaoProcess_PutArray( proc ); result = (DaoValue*) array; }else{ list = DaoProcess_PutList( proc ); result = (DaoValue*) list; } break; case DVM_FUNCT_APPLY : DaoProcess_PutValue( proc, param ); break; case DVM_FUNCT_FIND : DaoProcess_PutValue( proc, dao_none_value ); break; } if( threads <= 0 ) threads = 2; if( sect == NULL || DaoMT_PushSectionFrame( proc ) == 0 ) return; if( list ){ DArray_Clear( & list->items ); if( param->type == DAO_LIST ) DArray_Resize( & list->items, param->xList.items.size, NULL ); if( param->type == DAO_MAP ) DArray_Resize( & list->items, param->xMap.items->size, NULL ); #ifdef DAO_WITH_NUMARRAY }else if( array && F == DVM_FUNCT_MAP ){ DaoArray_GetSliceShape( (DaoArray*) param, & array->dims, & array->ndim ); DaoArray_ResizeArray( array, array->dims, array->ndim ); #endif } DMutex_Init( & mutex ); DCondVar_Init( & condv ); entry = proc->topFrame->entry; tasks = (DaoTaskData*) dao_calloc( threads, sizeof(DaoTaskData) ); DaoProcess_PopFrame( proc ); for(i=0; i<threads; i++){ DaoTaskData *task = tasks + i; task->param = param; task->result = result; task->proto = proc; task->sect = sect; task->funct = F; task->entry = entry; task->first = i; task->step = threads; task->index = & index; task->node = & node; task->joined = & joined; task->condv = & condv; task->mutex = & mutex; task->clone = DaoVmSpace_AcquireProcess( proc->vmSpace ); task->clone->mutex = & mutex; if( i ) DaoCallServer_AddTask( DaoMT_RunFunctional, task, 1 ); } DaoMT_RunFunctional( tasks ); DMutex_Lock( & mutex ); while( joined < threads ) DCondVar_TimedWait( & condv, & mutex, 0.01 ); DMutex_Unlock( & mutex ); for(i=0; i<threads; i++){ DaoTaskData *task = tasks + i; DaoVmSpace_ReleaseProcess( proc->vmSpace, task->clone ); status |= task->status; } if( F == DVM_FUNCT_FIND ){ DaoTuple *tuple = DaoProcess_PutTuple( proc, 0 ); if( param->type == DAO_LIST && index != -1 ){ DaoValue **items = param->xList.items.items.pValue; GC_ShiftRC( items[index], tuple->items[1] ); tuple->items[1] = items[index]; tuple->items[0]->xInteger.value = index; }else if( param->type == DAO_MAP && node ){ GC_ShiftRC( node->key.pValue, tuple->items[0] ); GC_ShiftRC( node->value.pValue, tuple->items[1] ); tuple->items[0] = node->key.pValue; tuple->items[1] = node->value.pValue; } } if( status ) DaoProcess_RaiseException( proc, DAO_ERROR, "code section execution failed!" ); DMutex_Destroy( & mutex ); DCondVar_Destroy( & condv ); dao_free( tasks ); }