|
|
1.1 ! root 1: /* ! 2: * Example of DOSSUSPENDTHREAD/DOSRESUMETHREAD usage. ! 3: * ! 4: * DOSSUSPENDTHREAD can be used to ensure mutual exclusion when a thread ! 5: * knows by number all the other thread which might try to access the ! 6: * shared resource. ! 7: * ! 8: * In this example the main thread can call printf() freely because it ! 9: * knows that the only other thread has been suspended, so the main ! 10: * thread will not be interrupted, and because it knows that the ! 11: * subthread must have been suspended while outside of a critical ! 12: * section, and so the main thread will not be interrupting the ! 13: * subthread's call to vio. ! 14: * ! 15: * Any thread may suspend any other thread in its process, including the ! 16: * main thread and itself. If a thread suspends all the threads in a ! 17: * process, including itself, then deadlock will result, and the process ! 18: * will have to be killed externally. ! 19: * ! 20: * Note that there are three methods for managing critical sections ! 21: * amongst threads in a process: ! 22: * ! 23: * 1. Semaphores - this is almost always the right solution ! 24: * 2. DosEnterCritSec ! 25: * 3. DosSuspendThread ! 26: * ! 27: * compile as: cl -Gs -AL -G2 -Lp suspend.c ! 28: * ! 29: */ ! 30: ! 31: #include <doscalls.h> ! 32: #include <subcalls.h> ! 33: #include "stdio.h" ! 34: #include "malloc.h" ! 35: #define STACK_SIZE 1024 ! 36: ! 37: extern void f_thread(void); ! 38: int flag; ! 39: ! 40: void main() ! 41: { ! 42: char *stkptr; ! 43: unsigned thread_id; ! 44: register int i; ! 45: ! 46: /* obtain pointer to the END of a block of memory */ ! 47: stkptr = (char *)malloc(STACK_SIZE) + STACK_SIZE - 1; ! 48: ! 49: /* create another thread */ ! 50: DOSCREATETHREAD(f_thread, &thread_id, stkptr); ! 51: ! 52: for(i = 0; i < 20; i++) { ! 53: DOSSUSPENDTHREAD(thread_id); /* suspend the subthread */ ! 54: ! 55: printf("the main thread has suspended thread %u\n", thread_id); ! 56: DOSSLEEP(3000L); ! 57: ! 58: /* resume the subthread */ ! 59: printf("now resuming the suspended thread\n"); ! 60: DOSRESUMETHREAD(thread_id); ! 61: ! 62: DOSSLEEP(3000L); ! 63: } ! 64: DOSEXIT(1, 0); /* exit all threads */ ! 65: } ! 66: ! 67: void f_thread() ! 68: { ! 69: while (1) { ! 70: DOSENTERCRITSEC(); ! 71: VIOWRTTTY("subthread running\r\n", 19, 0); ! 72: DOSEXITCRITSEC(); ! 73: DOSSLEEP(300L); ! 74: } ! 75: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.