Thread View: comp.os.os2.programmer
2 messages
2 total messages
Started by D G Booth
Tue, 12 Mar 1991 15:20
Re: Making a non exclusive semaphore (like on Unix)
Author: D G Booth
Date: Tue, 12 Mar 1991 15:20
Date: Tue, 12 Mar 1991 15:20
104 lines
3390 bytes
3390 bytes
Christophe Wolfhugel asks whether OS/2 had any mechanism similar to
the classic counting semaphores. There is no such mechanism built-in
to OS/2, but I have used the code below quite successfully.
The code defines a new structure type COUNTSEM which is a counting
semaphore, and functions P and V that operate on it. P decrements the
counter, but blocks if the counter is 0 until it is non-zero. V
increments the counter (and unblocks any blocked threads).
The code can be in an application managing mutual exclusion between
threads. It may also be in a DLL to manage semaphores between
processes, but in this case the MutualExclusion semaphore, and the
COUNTSEM structures should all be put in shared memory.
Duncan Booth <duncanb@ibmpcug.co.uk>
======= File: SEM.H ============
typedef struct COUNTSEM {
long countSem;
USHORT count;
} COUNTSEM, far *PCOUNTSEM;
void P (PCOUNTSEM s); /* Wait till non-zero then decrement. */
BOOL P_timeout (PCOUNTSEM s, LONG timeout); /* as P - may time out. */
void V (PCOUNTSEM s); /* Increment */
======== End of SEM.H ==========
======= File: SEM.C ============
/*
* Useful code using semaphores.
*
* Author: Duncan Booth
*/
#define INCL_DOSPROCESS
#include <os2.h>
#include "sem.h"
/*
* This semaphore is local to this file. It is used to control requests
* to the counting semaphore structures.
*/
static long MutualExclusion = 0L;
#define GET_SEM() (DosSemRequest (&MutualExclusion, SEM_INDEFINITE_WAIT))
#define RLS_SEM() (DosSemClear (&MutualExclusion))
void P (PCOUNTSEM s)
{
int blocked=1;
while (blocked)
{
DosSemWait (&s->countSem, SEM_INDEFINITE_WAIT); /* wait til maybe ok */
GET_SEM();
if (s->count == 0) /* not ready yet */
DosSemSet (&s->countSem); /* set up block */
else
{
s->count--; /* decrement count */
blocked = 0; /* set up loop exit */
}
RLS_SEM();
}
}
BOOL P_timeout (PCOUNTSEM s, LONG timeout)
{
int blocked=1;
while (blocked == 1)
{
if (DosSemWait (&s->countSem, timeout) != 0)
return FALSE; /* wait til maybe ok */
if (GET_SEM() != 0) return FALSE;
if (s->count == 0) /* not ready yet */
DosSemSet (&s->countSem); /* set up block */
else
{
s->count--; /* decrement count */
blocked = 0; /* set up loop exit */
}
RLS_SEM();
}
return TRUE;
}
void V (PCOUNTSEM s)
{
GET_SEM(); /* mutual excl */
s->count++; /* increment count */
DosSemClear (&s->countSem); /* free waiters */
RLS_SEM(); /* mutual excl */
}
======== End of SEM.C ==========
--
Automatic Disclaimer:
The views expressed above are those of the author alone and may not
represent the views of the IBM PC User Group.
--
Duncan Booth, RCP Ltd. Didcot, Oxon, UK
duncanb@ibmpcug.co.uk Bix: jrichards
Re: Making a non exclusive semaphore (like on Unix)
Author: Gary Kushner
Date: Mon, 08 Apr 1991 02:25
Date: Mon, 08 Apr 1991 02:25
78 lines
1984 bytes
1984 bytes
Your code uses polling which should be avoided if at all possible. Here
is the code I use:
----------
pv.h:
----------
/*------------
Type for PVsems
------------*/
typedef struct _pvsem {
long count;
long more; // sem clear if count > 0
long mutex;
} _far PVSEM;
/*-----------
Protos
-----------*/
PVSEM _far *PVSemCreate(void);
void _far _fastcall P(PVSEM _far *s);
void _far _fastcall V(PVSEM _far *s);
--------
pv.c
---------
#define INCL_DOSSEMAPHORES
#include <os2.h>
#include <malloc.h>
#include "pv.h"
/**************
* PVSEMCREATE - allocate sem
**************/
PVSEM _far *PVSemCreate(void)
{
PVSEM *s;
if ( (s=calloc(1, sizeof(PVSEM))) != NULL)
s->count=0;
return s;
}
/**************
* P -
**************/
void _far _fastcall P(PVSEM _far *s)
{
// any V's pending? if not then wait...
DosSemRequest(&s->more, SEM_INDEFINITE_WAIT);
DosSemRequest(&s->mutex, SEM_INDEFINITE_WAIT);
// if there are still more V's, then leave more clear
if (--(s->count) > 0)
DosSemClear(&s->more);
DosSemClear(&s->mutex);
}
/**************
* V - count them up
**************/
void _far _fastcall V(PVSEM _far *s)
{
DosSemRequest(&s->mutex, SEM_INDEFINITE_WAIT);
s->count++;
DosSemClear(&s->more); // ok guys, come and get it
DosSemClear(&s->mutex);
}
Thread Navigation
This is a paginated view of messages in the thread with full content displayed inline.
Messages are displayed in chronological order, with the original post highlighted in green.
Use pagination controls to navigate through all messages in large threads.
Back to All Threads