00001 00006 /* 00007 * The contents of this file are subject to the Mozilla Public License 00008 * Version 1.0 (the "License"); you may not use this file except in 00009 * compliance with the License. You may obtain a copy of the License at 00010 * http://www.mozilla.org/MPL/ 00011 * 00012 * Software distributed under the License is distributed on an "AS IS" 00013 * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the 00014 * License for the specific language governing rights and limitations 00015 * under the License. 00016 * 00017 * The Original Code is legOS code, released October 17, 1999. 00018 * 00019 * The Initial Developer of the Original Code is Markus L. Noga. 00020 * Portions created by Markus L. Noga are Copyright (C) 1999 00021 * Markus L. Noga. All Rights Reserved. 00022 * 00023 * Contributor(s): Markus L. Noga <markus@noga.de> 00024 */ 00025 00026 #include <semaphore.h> 00027 00028 #ifdef CONF_SEMAPHORES 00029 00030 #include <unistd.h> 00031 00033 // 00034 // Functions 00035 // 00037 00039 00041 wakeup_t sem_event_wait(wakeup_t data) { 00042 sem_t *sem=(sem_t*) ((unsigned)data); 00043 00044 // we're called by the scheduler, therefore in an IRQ handler, 00045 // so no worrying about IRQs. 00046 // 00047 if(*sem) { 00048 (*sem)--; 00049 return 1; // sem!=0 -> wakeup 00050 } 00051 return 0; 00052 } 00053 00055 00063 int sem_wait(sem_t * sem) { 00064 // check if semaphore is available, if not, go to sleep 00065 00066 if(sem_trywait(sem)) 00067 if (wait_event(sem_event_wait,(unsigned long) ((unsigned)sem)) == 0) 00068 return -1; 00069 00070 return 0; 00071 } 00072 00073 typedef struct { 00074 sem_t *sem; 00075 time_t abs_timeout; 00076 } timeout_sem_data_t; 00077 00078 static wakeup_t sem_event_timeout_wait(wakeup_t data) { 00079 timeout_sem_data_t *tsem = (timeout_sem_data_t*) ((unsigned)data); 00080 00081 // we're called by the scheduler, therefore in an IRQ handler, 00082 // so no worrying about IRQs. 00083 // 00084 if (*tsem->sem) { 00085 (*tsem->sem)--; 00086 return 1; // sem!=0 -> wakeup 00087 } 00088 00089 if (tsem->abs_timeout <= get_system_up_time()) { 00090 return 2; // timeout reached -> wakeup 00091 } 00092 00093 return 0; 00094 } 00095 00096 int sem_timedwait(sem_t *sem, 00097 const time_t abs_timeout) { 00098 timeout_sem_data_t data; 00099 data.sem = sem; 00100 data.abs_timeout = abs_timeout; 00101 00102 if (sem_trywait(sem)) { 00103 if (wait_event(sem_event_timeout_wait, 00104 (wakeup_t) ((unsigned) &data)) != 1) { 00105 return -1; // timeout reached. 00106 } 00107 } 00108 return 0; 00109 } 00110 00112 00122 int sem_trywait(sem_t * sem); 00123 #ifndef DOXYGEN_SHOULD_SKIP_THIS 00124 __asm__("\n\ 00125 .text\n\ 00126 .align 1\n\ 00127 .globl _sem_trywait\n\ 00128 _sem_trywait:\n\ 00129 stc ccr,r1h ; save flags \n\ 00130 orc #0x80,ccr ; block all but NMI\n\ 00131 mov.b @r0,r1l\n\ 00132 beq sem_fail ; !=0 -> decrease, return 0\n\ 00133 dec r1l\n\ 00134 mov.b r1l,@r0\n\ 00135 sub.w r0,r0 ; return 0\n\ 00136 bra sem_ok\n\ 00137 \n\ 00138 sem_fail:\n\ 00139 mov #0xffff,r0 ; else return 0xffff\n\ 00140 \n\ 00141 sem_ok:\n\ 00142 ldc r1h,ccr ; restore flags\n\ 00143 rts\n\ 00144 "); 00145 #endif // DOXYGEN_SHOULD_SKIP_THIS 00146 00147 #endif // CONF_SEMAPHORES
brickOS is released under the
Mozilla Public License.
Original code copyright 1998-2002 by the authors. |