I am making a C program to send AT commands to a mobile phone from my pc. In that, I want it to dial a number but after a delay of some time say 10 minutes. How should I do this(I am using WriteFile command to send the dial command ATD)? Also, during this time delay I want to be able to do something else & when the time is up, I want the program to interrupt my current task so that it can dial the given number. Please tell me how I can do this.

__Unix-specific answer; I've not tried this kind of thing in Windows before__

It sounds like you can just fork it, sleep the child process for however long you need, and then dial out; Depending on how you wrote it the parent process could just continue on happily or maybe wait for the next dial after a few steps?

in general, I'd advise googling/man'ing fork, wait, waitpid, and the other functions that let you play with concurrency.

pid_t cpid;
if(!(cpid = fork()))
{
/* child code */

exit(0); /* so as not to fork bomb ourselves unintentionally */
}

/* parent continues here */

waitpid(cpid, NULL, 0); /* wait on the child process, don't care about status returned */

/* more parent code */

naturally this is very rough code and could stand improvement, I hope it sends you in the right direction

In MS-Windows you will probably want to have two threads -- one thread for dialing and the other thread to do other things. The Sleep(int milliseconds) is available from windows.h

Or if your main program runs in a loop you could use the time() function to check the current time against somesort of timemark:

time_t seconds;
  seconds = time (NULL);
  while (1) //this would be your mainloop
  {
      // if > 10 minutes
      if (time(NULL) - seconds >= 600) 
      {
          //do something
      }
  }

(#include <time.h> for the time() function)

This is the simple and ugly solution.
Ancient Dragon's solution is the hard(er) but beautiful one ;)

In MS-Windows you will probably want to have two threads -- one thread for dialing and the other thread to do other things. The Sleep(int milliseconds) is available from windows.h

I am currently using CreateFile to open the port & perform read & write. Is CreateFile equivalent to using a CreateThread or will I have to explicitly give 2 CreateThread commands after the CreateFile for reading & writing? I would be highly obliged if you could give me a link with some samples of multi-threaded applications.

>>Is CreateFile equivalent to using a CreateThread
No. CreateFile() works with files and CreateThread() creates new threads. They are two completly different animals.


>>I would be highly obliged if you could give me a link with some samples of multi-threaded applications
There are billions of examples on the net. Here are some in DaniWeb.

>>or will I have to explicitly give 2 CreateThread commands after the CreateFile for reading & writing?

Only one CreateThread() function call. main() is alread in one thread so all you have to do is create another thread. In the new thread function you can put the code to open the file using CreatFile() and do all the phone dialing and other stuff.

Okay...so I have created a separate thread for dialling. Now this thread will be in a wait state since it has to dial only after some given time. But in the mean time how will the control return to my main thread so that I can perform some other tasks during the wait period. After all, once I enter the delayed dial thread, I will get blocked in that thread isn't it?

After calling CreateThread() the operating system will add the new thread to its thread scheduling list and give each thread CPU time. So thread1 will get a slice of CPU time, then when that time slice expires the os will halt the thread and give another thread some CPU time. It works like that for all threads running on the computer.

I still don't get it. The moment I issue a CreathThread command control will pass over to the thread, where I have put a sleep function of say 10 minutes. In my main function, immediately after this CreateThread command, I have given a WriteFile command to write to the serial port. Now, will this write be executed after the sleep period of 10 minutes or before that? On a side note, if I have a thread which reads an input from the serial port, is there a way to pass this input back to the main thread, while still ensuring that this thread continues monitoring for any other input?

I still don't get it. The moment I issue a CreathThread command control will pass over to the thread, where I have put a sleep function of say 10 minutes. In my main function, immediately after this CreateThread command, I have given a WriteFile command to write to the serial port. Now, will this write be executed after the sleep period of 10 minutes or before that?

Think of the two threads as if they are two completly different programs. They are executed independently of each other. So the Sleep() in one thread will be executed independently of the WriteFile() in the other thread.

On a side note, if I have a thread which reads an input from the serial port, is there a way to pass this input back to the main thread, while still ensuring that this thread continues monitoring for any other input?

Yes -- use global variables. All threads access the same global space. But you have to be careful to include thread synchonization techniques to prevent one thread from writing to the global variable at the same time that another thread tries to read or write to it. The simplest way to do this is with system mutex. See MSDN for CreateMutex() or google for examples.

I have read a lot on mutex but have still not been able to figure out how to use it. Can somebody please point out the error in the following code:

int i;
HANDLE mutex,hread;

DWORD WINAPI read(void* HCom)
{
while(1){
        WaitCommEvent(HCom, &dwCommEvent, &osRead);
        if ( WaitForSingleObject(osRead.hEvent,INFINITE) == WAIT_OBJECT_0)
        {
            char szBuf[100];
            do
            {
                memset(szBuf,0,sizeof(szBuf));
                ReadFile( HCom,szBuf,sizeof(szBuf),&dwRead,&osRead);    //Read buffer
                if(dwRead!=0)
                {
                       printf("Thread: %s\n",szBuf);
                       if (WaitForSingleObject(mutex,INFINITE)==WAIT_OBJECT_0)
                            i=10;
                       ReleaseMutex(mutex);
                }
            }while (dwRead > 0 );
       }
    }
}

int main()
{
//other initialisations done
mutex=CreateMutex(NULL,TRUE,NULL);
    if (mutex==NULL)
        printf("Creation of mutex failed with error no %d\n",GetLastError());
    operation=0;
    hread=CreateThread(NULL,0,read,hCom,0,&dwthread);
    if (hread==NULL)
    {
            printf("Creating thread failed with error no %d\n",GetLastError());
            return (1);
    }
    else
        printf("Thread activated\n");

while(1){
         if (WaitForSingleObject(mutex,INFINITE)==WAIT_OBJECT_0){
            if (i==10)
                 i=20;
         printf("%d\n",i);
         ReleaseMutex(mutex);
         }
   }
//Close handles & return
}

Here, I want that initially main should set value of i. But once I get an input, the read thread should set the value of i. After that based on that value, I want to do some stuff,like write to the port. All this while, the read thread should not change the value of i & if it does receive some input from the port during this time, it should be stored in a temporary variable.

As an alternative way, I have thought of using a global dynamic array to handle this problem. I can use the realloc function in the read thread to keep adding the integers to the array(I have shown only 1 assignment...the actual program has many alternates). The main thread can then use a local pointer to scan the global array from the start & after processing it,free the memory allocated for each element scanned. I have tried this using the 'free' function but it hasn't worked. But more importantly, is this the right way to solve this problem(in terms of memory issues,etc)?

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.