Use of Semaphore

How does the CreateSemaphore(), ReleaseSemaphore() and WaitForSingleObject() works? And what are the pararmeters and conditions that are to be put in to implement Semaphore?
ho_cmAsked:
Who is Participating?

[Webinar] Streamline your web hosting managementRegister Today

x
 
940961slConnect With a Mentor Commented:
Those functions are usefull when you want to work with threads. A thread is a copy of a function that runs simultaniously with other treads of that function.
To say it in normal words  : your function works more than once at the same time.
Now lets say your function needs some variables from your main program. how does the main program tell which tread needs the variables, and how do the threads know that the variables are (not) for them??
thanks to semaphores :
1. All the treads have the same parameterlist.
2. Every thread has a unique semaphore, made with createsemaphore.

When the tread has nothing to do, it uses SetEvent to tell the main program. And it waits for a respons from the program using WaitForSingleObject.

3. The main program uses ReleaseSemaphore to tell the tread that the variables in the parameterlist are for him.

Check out the program I once have written to learn working with threads.
the main program starts 100 threads of the function "threadfunctie"
After that, the main program sends random numbers to random treads.

the treads receive the numbers and use them (sleep(number)), after that, they wait for a new number.

#include <memory.h>
#include <malloc.h>
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/timeb.h>
#include <time.h>

const int maxthread = 99;
const int maxdelay = 20000;

typedef void *HANDLE;

typedef long              *An_Item_Ptr;
typedef An_Item_Ptr       An_Item_List[];

typedef struct
{
    int            Number;
    An_Item_List  *Items;
} An_Array;

typedef struct
{
      HANDLE                  threadhandle;
      HANDLE                  semaphorehandle;
      int                        number;
      int                        Info;
      int                        bussy;
} A_Thread;

typedef A_Thread            * A_Thread_Ptr;

typedef struct
{
      int            *number;
      int            *info;
      int            *bussy;
      HANDLE      *semaphorehandle;
} A_Parameter_List;

char *GetTime()
{
      char static ActualTime[12];
      struct _timeb timebuffer;
      div_t result;
      int hun;

      _strtime(&ActualTime[0]);
      ActualTime[8] = '.';
      _ftime(&timebuffer);
      result = div(timebuffer.millitm, 10);
      (result.rem > 4 && result.quot < 99 ? hun = result.quot + 1 : hun = result.quot);
      _itoa(hun, &ActualTime[9], 10);
      if (hun < 10) ActualTime[10] = ' ';
      ActualTime[11] = '\0';
      return ActualTime;
}

void Append_Item ( An_Array * Array)
{
   An_Item_List    *Item_List;
   int              Current_Index = -1;
   int              Counter;

   if (Array->Number == 0)
   {
      Array->Number = 1;
      Current_Index = Array->Number - 1;
      Item_List = (An_Item_List *) malloc (Array->Number * sizeof(An_Item_Ptr));
      Array->Items = Item_List;
   }
   else
   {
      An_Item_List  *Old_Item_List;
      Item_List = Array->Items;
      Old_Item_List = Item_List;
      Current_Index = Array->Number;
      Array->Number++;
      Item_List = (An_Item_List *) malloc (Array->Number * sizeof(An_Item_Ptr));
      for (Counter = 0; Counter < Array->Number - 1; Counter ++)
        {
         (*Item_List)[Counter] = (*Old_Item_List)[Counter];
      }
      free   (Old_Item_List);
      Array->Items = Item_List;
   }
}

An_Array            threads;
int                        Job_Finished = 0;

void * threadfunctie(A_Parameter_List * Parameter_List)
{
      int            *info = Parameter_List->info;
      int            number = *(Parameter_List->number);  //number is altijd zelfde
      int            *bussy = Parameter_List->bussy;
      HANDLE      *semaphorehandle = Parameter_List->semaphorehandle;
      printf("%s Thread %2d : started\n", GetTime(), number);
      *semaphorehandle = CreateSemaphore ( NULL,0,100,NULL);
      for(;!Job_Finished;)
      {
            SetEvent(*semaphorehandle);
            WaitForSingleObject(*semaphorehandle, 300000);
            Sleep(*info);
            printf("%s Thread %2d : number %d received\n", GetTime(), number, *info);
            *bussy = 0;
      }
      return(0);
}

void main (void)
{
      
      DWORD            Id;
      A_Thread_Ptr      thread;
      A_Parameter_List                  * Parameter_List;
      int r, threadnr, info;
      div_t result;

      printf("%s Program   : started\n", GetTime());
      for (int i = 0; i < maxthread; i++)
      {
            Append_Item(&threads);
            thread = (A_Thread *) malloc (sizeof(A_Thread));
            memset (thread, 0, sizeof (A_Thread));
            (*threads.Items)[i] = (An_Item_Ptr) thread;
            thread->number = i;

            Parameter_List = (A_Parameter_List *)malloc (sizeof(A_Parameter_List));
            Parameter_List->number = &(thread->number);
            Parameter_List->semaphorehandle = &(thread->semaphorehandle);
            Parameter_List->info = &(thread->Info);
            Parameter_List->bussy=&(thread->bussy);
            thread->threadhandle=CreateThread (NULL, 32000, (LPTHREAD_START_ROUTINE) &threadfunctie, (LPVOID) Parameter_List, 0, &Id);
            
      }

      Sleep(1000);

      for(;!Job_Finished;)
      {
            r = rand();
            result = div(r, maxdelay);
            info = result.rem;
            result = div(r, maxthread);
            threadnr = result.rem;

            if (((A_Thread_Ptr) (*threads.Items)[threadnr])->bussy == 0)
            {
                  ((A_Thread_Ptr) (*threads.Items)[threadnr])->Info = info;
                  ((A_Thread_Ptr) (*threads.Items)[threadnr])->bussy = 1;
                  ReleaseSemaphore    (((A_Thread_Ptr) (*threads.Items)[threadnr])->semaphorehandle, 1, NULL );
                  printf("%s Program   : send number %d to thread %d\n", GetTime(), info, threadnr);
            }
            else
            {
                  printf("%s Program   : thread number %2d is bussy\n", GetTime(), threadnr);
            }

            Sleep(1000);
      }
}


hope this helps

Stefaan
0
 
ho_cmAuthor Commented:
I am new in this area.. So please explain in simpler terms! Thanx!
0
 
pinkiCommented:
I din't get clearly what do you want especially pertaining to the

functions .Are you using the function names in general sense ? or

with respect to any specific functions as such ( I don't think so as such functions you have named exist or not in terms of system calls ! )

If you want know how to use a semaphore -- I mean starting from creation , release and syncronisation w.r.t given resources,then
I can explain you.Please let me know.
0
 
ho_cmAuthor Commented:
If you want know how to use a semaphore -- I mean starting from creation , release and syncronisation w.r.t given resources,then
I can explain you.Please let me know...

Yup! Please explain to me in further details ..! thanx!

My application the use of Shared Memory.. to exchange data between applications.. and my client application is ran based on 6 phone lines ..sort of voice automated applications simultaneously... i.e calling the function to send message data... at unpredictable time... So how can it be implemented using semaphore.. thanx!
0
 
alexoCommented:
Using SetEvent() on a semaphore handle?  Wow...
0
All Courses

From novice to tech pro — start learning today.