2 * selet.c - Example of using select() with Comedi
5 * Copyright (c) 1999,2000 David A. Schleef <ds@schleef.org>
7 * This file may be freely modified, distributed, and combined with
8 * other software, as long as proper attribution is given in the
13 * An example for using select() with asynchronous input. This
14 * example requires an asynchronous input subdevice that can
15 * handle TRIG_TIMER as a scan_begin_src.
19 #include <comedilib.h>
39 unsigned int chanlist[4];
43 void prepare_cmd(comedi_t *dev,comedi_cmd *cmd);
44 void do_cmd(comedi_t *dev,comedi_cmd *cmd);
46 #define sec_to_nsec(x) ((x)*1000000000)
47 #define sec_to_usec(x) ((x)*1000000)
48 #define sec_to_msec(x) ((x)*1000)
49 #define msec_to_nsec(x) ((x)*1000000)
50 #define msec_to_usec(x) ((x)*1000)
51 #define usec_to_nsec(x) ((x)*1000)
53 int main(int argc, char *argv[])
58 parse_options(argc,argv);
60 device = comedi_open(filename);
66 fcntl(comedi_fileno(device),F_SETFL,O_NONBLOCK);
68 for(i=0;i<n_chans;i++){
69 chanlist[i]=CR_PACK(channel+i,range,aref);
72 prepare_cmd(device,&cmd);
79 void do_cmd(comedi_t *dev,comedi_cmd *cmd)
85 struct timeval timeout;
87 ret=comedi_command_test(dev,cmd);
89 printf("test ret=%d\n",ret);
91 printf("errno=%d\n",errno);
92 comedi_perror("comedi_command_test");
98 ret=comedi_command_test(dev,cmd);
100 printf("test ret=%d\n",ret);
102 printf("errno=%d\n",errno);
103 comedi_perror("comedi_command_test");
107 dump_cmd(stdout,cmd);
109 ret=comedi_command(dev,cmd);
111 printf("ret=%d\n",ret);
113 printf("errno=%d\n",errno);
114 comedi_perror("comedi_command");
121 FD_SET(comedi_fileno(device),&rdset);
123 timeout.tv_usec = 50000;
124 ret = select(comedi_fileno(dev)+1,&rdset,NULL,NULL,&timeout);
125 printf("select returned %d\n",ret);
131 }else if(FD_ISSET(comedi_fileno(device),&rdset)){
132 /* comedi file descriptor became ready */
133 printf("comedi file descriptor ready\n");
134 ret=read(comedi_fileno(dev),buf,sizeof(buf));
135 printf("read returned %d\n",ret);
146 //printf("read %d %d\n",ret,total);
147 for(i=0;i<ret/sizeof(sampl_t);i++){
148 printf("%d\n",buf[i]);
152 /* unknown file descriptor became ready */
153 printf("unknown file descriptor ready\n");
159 * This part of the demo measures channels 1, 2, 3, 4 at a rate of
160 * 10 khz, with the inter-sample time at 10 us (100 khz). The number
161 * of scans measured is 10. This is analogous to the old mode2
164 void prepare_cmd(comedi_t *dev,comedi_cmd *cmd)
166 memset(cmd,0,sizeof(*cmd));
168 /* the subdevice that the command is sent to */
169 cmd->subdev = subdevice;
172 cmd->flags = TRIG_WAKE_EOS;
175 /* each event requires a trigger, which is specified
176 by a source and an argument. For example, to specify
177 an external digital line 3 as a source, you would use
178 src=TRIG_EXT and arg=3. */
180 /* In this case, we specify using TRIG_NOW to start
181 * acquisition immediately when the command is issued.
182 * The argument of TRIG_NOW is "number of nsec after
183 * NOW", but no driver supports it yet. Also, no driver
184 * currently supports using a start_src other than
186 cmd->start_src = TRIG_NOW;
189 /* The timing of the beginning of each scan is controlled
190 * by scan_begin. TRIG_TIMER specifies that scan_start
191 * events occur periodically at a rate of scan_begin_arg
192 * nanoseconds between scans. */
193 cmd->scan_begin_src = TRIG_TIMER;
194 cmd->scan_begin_arg = msec_to_nsec(100);
196 /* The timing between each sample in a scan is controlled
197 * by convert. Like above, TRIG_TIMER specifies that
198 * convert events occur periodically at a rate of convert_arg
199 * nanoseconds between scans. */
200 cmd->convert_src = TRIG_TIMER;
201 cmd->convert_arg = msec_to_nsec(1);
203 /* The end of each scan is almost always specified using
204 * TRIG_COUNT, with the argument being the same as the
205 * number of channels in the chanlist. You could probably
206 * find a device that allows something else, but it would
208 cmd->scan_end_src = TRIG_COUNT;
209 cmd->scan_end_arg = n_chans; /* number of channels */
211 /* The end of acquisition is controlled by stop_src and
212 * stop_arg. The src will typically be TRIG_COUNT or
213 * TRIG_NONE. Specifying TRIG_COUNT will stop acquisition
214 * after stop_arg number of scans, or TRIG_NONE will
215 * cause acquisition to continue until stopped using
216 * comedi_cancel(). */
217 cmd->stop_src = TRIG_COUNT;
218 cmd->stop_arg = n_scans;
220 /* the channel list determined which channels are sampled.
221 In general, chanlist_len is the same as scan_end_arg. Most
222 boards require this. */
223 cmd->chanlist = chanlist;
224 cmd->chanlist_len = n_chans;