Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Select() system call in threads?

I am reading data from multiple serial ports. At present I am using a custom signal handler (by setting sa_handler) to compare and wake threads based on file descriptor information. I was searching for a way out to have individual threads with unique signal handlers, in this regard I found that select system call is to be used.

Now I have following questions:

  1. If I am using a thread (Qt) then where do I put the select system call to monitor the serial port?
  2. Is the select system call thread safe?
  3. Is it CPU intensive because there are many things happening in my app including GUI update?

Please do not mind, if you find these questions ridiculous. I have never used such a mechanism for serial communication.

like image 227
rocknroll Avatar asked Jun 26 '09 09:06

rocknroll


1 Answers

The POSIX specification (select) is the place to look for the select definition. I personally recommend poll - it has a better interface and can handle any number of descriptors, rather than a system-defined limit.

If I understand correctly you're waking threads based on the state of certain descriptors. A better way would be to have each thread have its own descriptor and call select itself. You see, select does not modify the system state, and as long as you use thread-local variables it'll be safe. However, you will definitely want to ensure you do not close a descriptor that a thread depends on.

Using select/poll with a timeout leaves the "waiting" up to the kernel side, which means the thread is usually put to sleep. While the thread is sleeping it is not using any CPU time. A while/for loop on a select call without a timeout on the other hand will give you a higher CPU usage as you're constantly spinning in the loop.

Hope this helps.

EDIT: Also, select/poll can have unpredictable results when working with the same descriptor in multiple threads. The simple reason for this is that the first thread might be woken up because the descriptor is ready for reading, but the second thread has to wait for the next "available for reading" wakeup.

As long as you're not selecting on the same descriptor in multiple threads you should not have a problem.

like image 88
Matthew Iselin Avatar answered Sep 28 '22 09:09

Matthew Iselin