LinuxQuestions.org
Go Job Hunting at the LQ Job Marketplace
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices

Reply
 
Search this Thread
Old 12-18-2004, 04:49 AM   #1
george_mercury
LQ Newbie
 
Registered: Jun 2004
Location: Slovenia
Distribution: Gentoo
Posts: 27

Rep: Reputation: 15
Proper way of polling a device


Hi!
I have to read data from serial port, and so I have implement some kind for data polling rutene for the ttyS0. I know how to check if data has arrived in buffer, and I know how to read that data, but how do I write the data polling rutene to be as low CPU resource consuming as possible?

If I write a while loop and an ioctl in it to check if data has arrived, than this would probably consume almost all CPU resources. Plus I have no way of checking for a timeout ( in case the device isn't responding ). I could use the signal system call, but I don't know how it's suitable for data polling, although the man page says that it is.

Can anyone gime me some points how I should write my data polling rutene?

George
 
Old 12-18-2004, 08:23 AM   #2
Hko
Senior Member
 
Registered: Aug 2002
Location: Groningen, The Netherlands
Distribution: ubuntu
Posts: 2,530

Rep: Reputation: 108Reputation: 108
It's possible to have your program sleep completely (i.e. not using any CPU) until one of the control-lines of the serial port changes state from low-->high or high-->low (or a signal has arrived). So if you can use this in your program, you don't have to poll at all.

Assuming fd is a valid file descriptor that has /dev/ttyS0 (or another serial port) open for reading, you can do:
Code:
#include <stdio.h>
#include <stdlib.h>
#include <termios.h>
#include <sys/ioctl.h>
#include <sys/file.h>
#include <linux/serial.h>

/* .... */

int mask

/* We want to wait until either one of the following control lines changes state: */
mask = TIOCM_CAR | TIOCM_DSR | TIOCM_CTS | TIOCM_RNG;

/* The ioctl() call below sleeps and does not return until one of
 * the control lines metioned in mask changes state.
 * or a signal was received, or an error has ocurred.
 */
if (ioctl(fd, TIOCMIWAIT, mask) == -1) {
    if (errno == EINTR) {
        /*
         * Woken up by a signal, do something, maybe just
         * resume waiting again.
         */
    } else {
        /* Other error, report it and exit */
        perror("ioctl - TIOCMIWAIT");
        exit(1);
    }
}

/* Once we get here, one of the control lines in 'mask' has changed state */
/* Act accordingly from here */
Hope you can use this for your purpose.

Last edited by Hko; 12-18-2004 at 08:27 AM.
 
Old 12-18-2004, 01:31 PM   #3
bm17
Member
 
Registered: Sep 2004
Location: Santa Cruz, CA, USA
Distribution: Redhat 9.0
Posts: 104

Rep: Reputation: 15
Check out the functions cfmakeraw() and tcsetattr(). These should allow you to fine-tune the timing parameters of the serial line. I usually do serial communication in a subthread. This allows me to minimize scheduling latency in case the exact time of data arrival is important.
 
Old 12-18-2004, 01:48 PM   #4
krisi
LQ Newbie
 
Registered: Dec 2004
Location: Sofia,Bulgaria
Distribution: suse,debian
Posts: 11

Rep: Reputation: 0
If you like to wait and than to apply the loop again ,so put the sleep() function somwere in the loop and it's ok.
In the brackets use a number to set the number of seconds until the loop continue/start again.
Example:

#include <stdio.h>
#include <stdlib.h>
#include <sys/time.h>
int main()
{
struct timeval tv;
gettimeofday(&tv,NULL);
tv.tv_usec=(tv.tv_usec+500)/1000;
printf ("%u%u\n",tv.tv_sec,tv.tv_usec);
sleep(3); /* In this line the program will stop for 3 seconds and than it wil continue*/
gettimeofday(&tv,NULL);
tv.tv_usec=(tv.tv_usec+500)/1000;
printf ("%u%u\n",tv.tv_sec,tv.tv_usec);
exit(0);
}
 
Old 12-13-2008, 01:13 PM   #5
dovidhalevi
LQ Newbie
 
Registered: Sep 2008
Posts: 2

Rep: Reputation: 0
How to STOP the thing

I am working on a kde4-plasma applet that monitors a modem for telephony usage. So I have this very loop, lifted from xingd, waiting for rings. Works like a charm.

Problem is, when plasma or the test applet viewer want to close the program, this wait thread is still running. No very nice behavior indeed.

I tried placing a simple break in the EINTR code. Nothing changed.

xringd had set a lot of singals with handlers and such. Is this what I need to do? I do not need a specific handler as such if I can simply test the signal that triggered the EINTR. Question is was there such a signal when the program was closed, objects destroyed, or need I set it?
 
  


Reply


Thread Tools Search this Thread
Search this Thread:

Advanced Search

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
UART Polling/Interrupt jdhar Linux - Software 1 06-10-2010 02:55 PM
NAPI in linux with kernel 2.6 for device polling wangjinyi Linux - Networking 0 09-22-2005 02:36 AM
Mouse polling rates Diminished7th Linux - Hardware 2 05-11-2005 06:08 PM
about device polling wangjinyi Fedora 0 04-27-2005 02:22 AM
how to do socket polling in kernel? lylai Linux - Networking 2 06-05-2002 05:52 AM


All times are GMT -5. The time now is 07:45 PM.

Main Menu
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
identi.ca: @linuxquestions
Facebook: linuxquestions Google+: linuxquestions
Open Source Consulting | Domain Registration