void PythonThread(void *argl) { HAB hab; arglist *args; /* PM initialisation */ hab = WinInitialize(0); /* start Python */ args = (arglist *)argl; args->running = 1; PythonRC = Py_Main(args->argc, args->argv); /* enter a critical section and send the termination message */ DosEnterCritSec(); args->running = 0; WinPostMsg(args->Frame, WM_QUIT, NULL, NULL); /* shutdown PM and terminate thread */ WinTerminate(hab); _endthread(); }
VOID SetScreenColors(THREAD *pstThd) { VIOCELL Cell; VIOPS *pVio = &pstThd->stVio; WORD wRow; WORD wColumn; BYTE byBackground; BYTE byForeground; byBackground = ClrTable[pVio->wBackground].PSClr; byForeground = ClrTable[pVio->wForeground].PSClr; Cell.ExtAttr = Cell.Spare = 0; Cell.Attr = (byBackground << 4) | byForeground; DosEnterCritSec(); VioGetCurPos(&wRow,&wColumn,pVio->hpsVio); VioWrtNAttr((PBYTE)&Cell.Attr,pVio->usPsWidth * pVio->usPsDepth,0,0,pVio->hpsVio); VioSetCurPos(wRow,wColumn,pVio->hpsVio); DosExitCritSec(); }
void ICQAPI ishare_removeItem(ISHARED_LIST *ctl, ISHARED_LISTHEADER *reg) { #ifdef __OS2__ DosEnterCritSec(); #endif if(reg->up) (reg->up)->down = reg->down; else ctl->first = reg->down; if(reg->down) (reg->down)->up = reg->up; else ctl->last = reg->up; #ifdef __OS2__ DosExitCritSec(); #endif yield(); }
void ICQAPI ishare_insertItem(ISHARED_LIST *lst, ISHARED_LISTHEADER *itn) { #ifdef __OS2__ DosEnterCritSec(); #endif if(lst->first == NULL) { /* Empty list */ lst->first = lst->last = itn; itn->up = itn->down = NULL; } else { /* Insert in the end of the list */ lst->last->down = itn; itn->up = lst->last; itn->down = NULL; lst->last = itn; } #ifdef __OS2__ DosExitCritSec(); #endif yield(); }
void connectthread( void * parameters ) { struct connectthreadparameters * ctp; unsigned long curmax; HPIPE hpipe; struct messagequeue * msgq; unsigned char maxpipes; char pipename[CCHMAXPATH]; APIRET rc; long req; HEV shutdown; HEV terminated; /* Grab data from parameter block, and signal when done. */ ctp = ( struct connectthreadparameters * ) parameters; maxpipes = ctp->maxpipes; strcpy(pipename,ctp->pipename); shutdown = ctp->shutdown; msgq = ctp->msgq; terminated = ctp->terminated; DosPostEventSem(ctp->initialized); /* Clear the pipe handle ( this is checked for a non-NULLHANDLE ** ** value on thread exit ). */ hpipe = NULLHANDLE; create: /* Create a new instance of the pipe. */ rc = DosCreateNPipe( pipename, &hpipe, NP_NOINHERIT|NP_ACCESS_DUPLEX, NP_NOWAIT|NP_TYPE_BYTE|NP_READMODE_BYTE|maxpipes, inbuffersize, outbuffersize, 0 ); if ( rc != NO_ERROR && rc != ERROR_PIPE_BUSY && rc != ERROR_TOO_MANY_OPEN_FILES ) { /* Some unexpected error has occurred. Notify the ** ** application. */ DosRequestMutexSem(msgq->access,SEM_INDEFINITE_WAIT); *msgq->qtail = malloc( sizeof( struct message ) ); (*msgq->qtail)->id = cterror; (*msgq->qtail)->data.cterrordata.ec = apiret2ec(rc); (*msgq->qtail)->next = NULL; DosPostEventSem(msgq->available); DosReleaseMutexSem(msgq->access); goto completed; } if ( rc == ERROR_PIPE_BUSY ) /* Max pipes created. */ goto busy; if ( rc == ERROR_TOO_MANY_OPEN_FILES ) { req = 1; rc = DosSetRelMaxFH(&req,&curmax); if ( rc == NO_ERROR ) goto create; /* Can trigger a 'max connections reached' message here ... */ goto busy; } connect: /* Connect pipe ( allows client to connect ). */ rc = DosConnectNPipe(hpipe); if ( rc != NO_ERROR && rc != ERROR_PIPE_NOT_CONNECTED && rc != ERROR_BROKEN_PIPE ) { /* Unexpected error ... */ DosRequestMutexSem(msgq->access,SEM_INDEFINITE_WAIT); *msgq->qtail = malloc( sizeof( struct message ) ); (*msgq->qtail)->id = cterror; (*msgq->qtail)->data.cterrordata.ec = apiret2ec(rc); (*msgq->qtail)->next = NULL; DosPostEventSem(msgq->available); DosReleaseMutexSem(msgq->access); DosClose(hpipe); hpipe = NULLHANDLE; goto completed; } if ( rc == ERROR_PIPE_NOT_CONNECTED ) /* No client connected, so wait a while ... */ goto waiting; if ( rc == ERROR_BROKEN_PIPE ) { /* Client connected, but probably immediately closed. */ DosClose(hpipe); hpipe = NULLHANDLE; goto create; } /* Send handle of the newly connected pipe to the application. */ DosRequestMutexSem(msgq->access,SEM_INDEFINITE_WAIT); *msgq->qtail = malloc( sizeof( struct message ) ); (*msgq->qtail)->id = connected; (*msgq->qtail)->data.connecteddata.hpipe = hpipe; (*msgq->qtail)->next = NULL; DosPostEventSem(msgq->available); DosReleaseMutexSem(msgq->access); /* Create a new instance of the pipe for the next client. */ goto create; waiting: /* Wait to see if the application is ready to exit. */ rc = DosWaitEventSem(shutdown,connectpolltimeout); if ( rc != ERROR_TIMEOUT ) goto completed; /* Not shutting down, so wait for a client to connect. */ goto connect; busy: /* Pipe is busy. */ rc = DosWaitEventSem(shutdown,connectpolltimeout); if ( rc != ERROR_TIMEOUT ) goto completed; /* Not shutting down, but in this case, unlike waiting above, go ** ** and create a new pipe. */ goto create; completed: /* Processing completed. */ /* Close pipe if no client had connected. */ if ( hpipe != NULLHANDLE ) DosClose(hpipe); /* Notify application that the thread will not accept more ** ** connections. */ DosRequestMutexSem(msgq->access,SEM_INDEFINITE_WAIT); *msgq->qtail = malloc( sizeof( struct message ) ); (*msgq->qtail)->id = ctclosed; (*msgq->qtail)->next = NULL; DosPostEventSem(msgq->available); DosReleaseMutexSem(msgq->access); /* Shutdown processing completed. Signal owner. */ DosEnterCritSec(); DosPostEventSem(terminated); }
void clienthandlerthread( void * parameters ) { char buffer[32]; struct clienthandlerthreadparameters * chtp; struct clientinfo * ci; struct clientinfo * cilist; unsigned long count; int dataread; unsigned short i; struct message * msg; struct messagequeue * inmsgq; struct messagequeue * outmsgq; struct clientinfo ** pci; APIRET rc; int running; HEV terminated; struct tm * tm; time_t tt; /* Pull info from the parameter block. When done, signal the ** ** function which called _beginthread, allowing it to free up the ** ** parameter block, if necessary. */ chtp = ( struct clienthandlerthreadparameters * ) parameters; inmsgq = chtp->inmsgq; outmsgq = chtp->outmsgq; terminated = chtp->terminated; DosPostEventSem(chtp->initialized); /* Initialize the client info list. */ cilist = NULL; running = !0; /* Finite state machine begins ... */ waitq: /* Wait for input in the queue. */ rc = DosWaitEventSem(inmsgq->available,clientpolltimeout); if ( rc == ERROR_TIMEOUT ) goto checkclients; /* Fall through otherwise ... */ processq: /* Process input in the queue. */ /* Loops until all messages processed. The running switch is set ** ** if a shutdownreq message is pulled from the queue. */ while ( running ) { DosRequestMutexSem(inmsgq->access,SEM_INDEFINITE_WAIT); msg = inmsgq->q; if ( msg != NULL ) { inmsgq->q = msg->next; if ( inmsgq->q == NULL ) inmsgq->qtail = &inmsgq->q; } DosResetEventSem(inmsgq->available,&count); DosReleaseMutexSem(inmsgq->access); /* Last message dequeued. */ if ( msg == NULL ) break; switch ( msg->id ) { case connected: /* A new client has connected. Add a clientinfo to ** ** the head of the list ( easier than adding it to the ** ** tail ). */ ci = malloc( sizeof( struct clientinfo ) ); ci->hpipe = msg->data.connecteddata.hpipe; ci->cmdbufferlength = 0; ci->overflowed = 0; ci->next = cilist; cilist = ci; break; case shutdownreq: /* Need to shut down in preparation for program exit. */ running = 0; break; } free(msg); } if ( !running ) goto completed; /* Otherwise fall through ... */ checkclients: /* Check for incoming text in pipes. */ dataread = 0; pci = &cilist; while ( *pci != NULL ) { rc = DosRead( (*pci)->hpipe, &(*pci)->cmdbuffer[(*pci)->cmdbufferlength], sizeof( (*pci)->cmdbuffer ) - (*pci)->cmdbufferlength, &count ); if ( ( rc != NO_ERROR || count == 0 ) && rc != ERROR_NO_DATA ) { /* Some error has occurred, probably the client has closed ** ** his end of the pipe. Close this end, notify the ** ** application that the pipe/client has closed, and pull ** ** the clientinfo structure from the list. */ ci = *pci; *pci = (*pci)->next; DosClose(ci->hpipe); DosRequestMutexSem(outmsgq->access,SEM_INDEFINITE_WAIT); *outmsgq->qtail = malloc( sizeof( struct message ) ); (*outmsgq->qtail)->id = closed; (*outmsgq->qtail)->data.closeddata.hpipe = ci->hpipe; (*outmsgq->qtail)->next = NULL; DosPostEventSem(outmsgq->available); DosReleaseMutexSem(outmsgq->access); free(ci); continue; } if ( rc == NO_ERROR ) { (*pci)->cmdbufferlength += ( unsigned short ) count; dataread = !0; checkfornl: for ( i = 0; i < (*pci)->cmdbufferlength && (*pci)->cmdbuffer[i] != '\n'; ++i ) ; if ( i < (*pci)->cmdbufferlength ) { /* A \n has been found. Check for a valid command. */ if ( !(*pci)->overflowed ) { (*pci)->cmdbuffer[i] = '\0'; strip( (*pci)->cmdbuffer ); if ( stricmp( (*pci)->cmdbuffer, "time" ) == 0 ) { DosRequestMutexSem(outmsgq->access, SEM_INDEFINITE_WAIT); *outmsgq->qtail = malloc( sizeof( struct message ) ); (*outmsgq->qtail)->id = executing; (*outmsgq->qtail)->data.executingdata.hpipe = (*pci)->hpipe; strcpy( (*outmsgq->qtail)->data.executingdata.cmd, "time" ); (*outmsgq->qtail)->next = NULL; DosPostEventSem(outmsgq->available); DosReleaseMutexSem(outmsgq->access); time(&tt); tm = localtime(&tt); sprintf( buffer, "OK %02d:%02d:%02d\n", tm->tm_hour, tm->tm_min, tm->tm_sec ); } else if ( stricmp( (*pci)->cmdbuffer, "shutdown" ) == 0 ) { DosRequestMutexSem(outmsgq->access, SEM_INDEFINITE_WAIT); *outmsgq->qtail = malloc( sizeof( struct message ) ); (*outmsgq->qtail)->id = executing; (*outmsgq->qtail)->data.executingdata.hpipe = (*pci)->hpipe; strcpy( (*outmsgq->qtail)->data.executingdata.cmd, "shutdown" ); (*outmsgq->qtail)->next = malloc( sizeof( struct message ) ); (*outmsgq->qtail)->next->id = shutdownreq; (*outmsgq->qtail)->next->next = NULL; DosPostEventSem(outmsgq->available); DosReleaseMutexSem(outmsgq->access); strcpy(buffer,"OK\n"); } else strcpy(buffer,"EBADCMD\n"); DosWrite( (*pci)->hpipe, buffer, strlen(buffer), &count ); } else { /* \n found, but the overflow flag had been set ** ** earlier. Notify client that the command was ** ** too long. */ strcpy(buffer,"EOFLOW\n"); DosWrite( (*pci)->hpipe, buffer, strlen(buffer), &count ); (*pci)->overflowed = 0; /* Clear flag. */ } /* Shift buffer contents. There may be more text ** ** following the \n. If so, go back and check for ** ** another command. */ memmove( (*pci)->cmdbuffer, &(*pci)->cmdbuffer[i+1], (*pci)->cmdbufferlength - i - 1 ); (*pci)->cmdbufferlength -= i + 1; if ( (*pci)->cmdbufferlength != 0 ) goto checkfornl; } else /* \n not found. Check if the buffer is full. If so, ** ** set the overflow flag and clear out the buffer. */ if ( (*pci)->cmdbufferlength == sizeof( (*pci)->cmdbuffer ) ) { (*pci)->cmdbufferlength = 0; (*pci)->overflowed = !0; } } /* Move the pointer to the next clientinfo in the list. */ pci = &(*pci)->next; } /* If no data was read ( all clients are quiet ), go to waitq. ** ** Otherwise, go to checkq, which only checks if messages are ** ** available and does not wait. */ if ( !dataread ) goto waitq; checkq: /* Check queue, but don't wait. */ rc = DosWaitEventSem(inmsgq->available,SEM_IMMEDIATE_RETURN); if ( rc == ERROR_TIMEOUT ) goto checkclients; /* Messages available. Processes those. */ goto processq; completed: /* Thread has completed and needs to clean up. */ /* Close all clients. */ while ( cilist != NULL ) { ci = cilist; cilist = ci->next; DosClose(ci->hpipe); free(ci); } /* Signal owner that the thread has completed. */ DosEnterCritSec(); DosPostEventSem(terminated); }
bool Interlock::Request(long) // the wait parameter does not make any sense here { return DosEnterCritSec() == 0; }
void enter_critical_section(SECTION_CODE i) { DosEnterCritSec(); }
VOID FAR PMfrThread (VOID) { int sub_rc; habThread = WinInitialize(0); WinGetLastError(habThread); /* get the memory DC */ cp.hdcMemory = DevOpenDC (habThread, OD_MEMORY, "*", 0L, NULL, NULL) ; /* this says that we don't have a PS yet; not one to destroy */ cp.hpsMemory = (HPS) NULL; /* let each sub-driver have a crack at it now */ PrintDriverInit(); CalcDriverInit(); /* Initialization here is done. Post main thread that we are going to work */ WinPostMsg(cp.hwnd, WM_THRD_POST, MPFROM2SHORT(SUB_INIT_DONE, 0), MPFROMP(NULL) ); for (;;) { /* wait for something to do */ DosSemWait (&cp.ulSemTrigger, SEM_INDEFINITE_WAIT) ; /* take an early exit for Shutdown */ if (cp.sSubAction == SUB_ACT_TERM) break; /* posted out of wait. do something */ switch(cp.sSubAction) { case SUB_ACT_CALC: sub_rc = CalcDriver(); break; case SUB_ACT_PRINT: sub_rc = PrintDriver(); break; case SUB_ACT_SAVE: sub_rc = SaveDriver(); break; case SUB_ACT_LOAD: sub_rc = LoadDriver(); break; default: sub_rc = 0x9999; /* let the main task figure it out */ break; } /* test here for shutdown also */ if (cp.sSubAction == SUB_ACT_TERM) break; /* not shutdown. */ /* indicate ready for the next cycle */ DosSemSet (&cp.ulSemTrigger) ; WinPostMsg (cp.hwnd, WM_THRD_POST, MPFROM2SHORT(sub_rc, 0) , MPFROMP(NULL) ) ; } /* shutdown has been triggered. release resources obtained by us. NOTE: Serialize using DosEnterCritSec so that the main thread is dormant until we get everything cleaned up and go away. The main thread will be re-dispatched following our final DosExit. */ DosEnterCritSec(); if (cp.hpsMemory != (HPS) 0) { /* protection from a failed WM_CREATE or IDM_GO */ GpiSetBitmap(cp.hpsMemory, (HBITMAP) NULL); GpiDestroyPS(cp.hpsMemory); GpiDeleteBitmap (cp.hbmMemory); } cp.hpsMemory = (HPS) 0; if ( cp.pixels != NULL) hfree(cp.pixels); cp.pixels = NULL; if (cp.hdcMemory != (HDC) 0) DevCloseDC (cp.hdcMemory); cp.hdcMemory = (HDC) 0; /* say good-bye to PM */ WinTerminate(habThread); /* flag we done */ DosSemClear ((HSEM) &cp.ulSemSubEnded); /* and go away */ DosExit(EXIT_THREAD, 0); }
static VOID VManSetFullscreen(SDL_PrivateVideoData *pPVData, PVIDEOMODE pFSVideoMode) { static ULONG ulDesktopModeId = ((ULONG)(-1)); // -1 - in desktop HWSHOWPTRIN hwspi; ULONG ulRC; BOOL fInFullscreen = ulDesktopModeId != ((ULONG)(-1)); BOOL fGoToFullscreen = pFSVideoMode != NULL; if ( fInFullscreen == fGoToFullscreen ) { debug( "Already in %s", fInFullscreen ? "fullscreen" : "desktop" ); return; } debug( "Switch to %s", fGoToFullscreen ? "fullscreen" : "desktop" ); ulRC = DosSetPriority( PRTYS_PROCESS, PRTYC_FOREGROUNDSERVER, PRTYD_MAXIMUM, 0 ); if ( ulRC != NO_ERROR ) debug( "#1 DosSetPriority(), rc = %u" ); hwspi.ulLength = sizeof(HWSHOWPTRIN); if ( fGoToFullscreen ) { GDDMODEINFO sCurModeInfo; // debug( "Video mode id: 0x%X", pFSVideoMode->uiModeID ); ulRC = pfnVMIEntry( 0, VMI_CMD_QUERYCURRENTMODE, NULL, &sCurModeInfo ); if ( ulRC != RC_SUCCESS ) { debug( "Could not query desktop video mode." ); } else { ulDesktopModeId = sCurModeInfo.ulModeId; // Remember desktop mode id ulRC = DosEnterCritSec(); if ( ulRC != NO_ERROR ) debug( "DosEnterCritSec(), rc = %u" ); hwspi.fShow = FALSE; pfnVMIEntry( 0, VMI_CMD_SHOWPTR, &hwspi, NULL ); #ifdef __USE_GRE_CALLS_ // Tell the GRE that PM will die GreDeath( GetDesktopHWND() ); #endif pfnVMIEntry( 0, VMI_CMD_SETMODE, &pFSVideoMode->uiModeID, NULL ); if ( pPVData != NULL && pPVData->pSDLSurface != NULL ) { _VManClearFS( pPVData ); if ( pPVData->pSDLSurface != NULL && pPVData->pSDLSurface->format->palette != NULL ) VManSetPalette( pPVData, 0, pPVData->pSDLSurface->format->palette->ncolors, pPVData->pSDLSurface->format->palette->colors ); } ulRC = DosExitCritSec(); if ( ulRC != NO_ERROR ) debug( "DosExitCritSec(), rc = %u" ); } } else { ulRC = DosEnterCritSec(); if ( ulRC != NO_ERROR ) debug( "DosEnterCritSec(), rc = %u" ); pfnVMIEntry( 0, VMI_CMD_SETMODE, &ulDesktopModeId, NULL ); #ifdef USE_GRE_CALLS // Tell GRE that PM can come back GreResurrection( GetDesktopHWND(), 0, NULL ); #endif // Show mouse pointer hwspi.fShow = TRUE; pfnVMIEntry( 0, VMI_CMD_SHOWPTR, &hwspi, NULL ); ulRC = DosExitCritSec(); if ( ulRC != NO_ERROR ) debug( "DosExitCritSec(), rc = %u" ); ulDesktopModeId = ((ULONG)(-1)); // We are in desktop now } ulRC = DosSetPriority( PRTYS_PROCESS, PRTYC_REGULAR, 0, 0 ); if ( ulRC != NO_ERROR ) debug( "#2 DosSetPriority(), rc = %u" ); debug( "Done" ); }