nidas  v1.2-1520
usbtwod.h
Go to the documentation of this file.
1 /* -*- mode: C; indent-tabs-mode: nil; c-basic-offset: 8; tab-width: 8; -*- */
2 /* vim: set shiftwidth=8 softtabstop=8 expandtab: */
3 /*
4  ********************************************************************
5  ** NIDAS: NCAR In-situ Data Acquistion Software
6  **
7  ** 2007, Copyright University Corporation for Atmospheric Research
8  **
9  ** This program is free software; you can redistribute it and/or modify
10  ** it under the terms of the GNU General Public License as published by
11  ** the Free Software Foundation; either version 2 of the License, or
12  ** (at your option) any later version.
13  **
14  ** This program is distributed in the hope that it will be useful,
15  ** but WITHOUT ANY WARRANTY; without even the implied warranty of
16  ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17  ** GNU General Public License for more details.
18  **
19  ** The LICENSE.txt file accompanying this software contains
20  ** a copy of the GNU General Public License. If it is not found,
21  ** write to the Free Software Foundation, Inc.,
22  ** 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
23  **
24  ********************************************************************
25 */
26 
27 #ifndef _nidas_usbtwod_h_
28 #define _nidas_usbtwod_h_
29 
30 #include <nidas/linux/types.h>
31 
32 #ifndef __KERNEL__
33 /* User programs need this for the _IO macros, but kernel
34  * modules get their's elsewhere.
35  */
36 #include <sys/ioctl.h>
37 #include <sys/types.h>
38 #include <errno.h>
39 #endif
40 
41 #include <nidas/linux/util.h>
42 
48 {
50  unsigned int numImages;
51  unsigned int lostImages;
53  unsigned int numSORs;
54  unsigned int lostSORs;
55  unsigned int lostTASs;
56  unsigned int urbErrors;
57  unsigned int urbTimeouts;
58 };
59 
69 typedef struct _Tap2D_v1
70 {
72  unsigned char ntap;
74  unsigned char div10;
76  unsigned char cntr;
77  unsigned char dummy;
78 } Tap2Dv1;
79 
84 typedef struct _Tap2D_v2
85 {
87  unsigned short ntap;
89  unsigned char div10;
90 
92  unsigned char cntr;
93 } Tap2D;
94 
95 /*
96  * Believe this struct is unnecessary
97  */
98 typedef struct _Tap2D_v3
99 {
101  unsigned short tas;
103  unsigned short probeResolution;
104 } Tap2D_v3;
105 
106 /* Pick a character as the magic number of your driver.
107  * It isn't strictly necessary that it be distinct between
108  * all modules on the system, but is a good idea. With
109  * distinct magic numbers one can catch a user sending
110  * an ioctl to the wrong device.
111  */
112 #define USB2D_IOC_MAGIC 0x2d
113 
114 #define USB2D_SET_TAS _IOW(USB2D_IOC_MAGIC,0,Tap2D)
115 #define USB2D_SET_SOR_RATE _IOW(USB2D_IOC_MAGIC,1,int)
116 #define USB2D_GET_STATUS _IOR(USB2D_IOC_MAGIC,2,struct usb_twod_stats)
117 
118 /*
119  * Both image and shadow-OR samples are read from this device.
120  * We place the following 4-byte type values at the beginning of
121  * each data sample in big-endian form, so user code can
122  * figure out which is which.
123  */
124 #define TWOD_IMG_TYPE 0
125 #define TWOD_SOR_TYPE 1
126 #define TWOD_SORv3_TYPE 0x534f522c /* SOR, */
127 #define TWOD_IMGv2_TYPE 2
128 #define TWOD_IMGv3_TYPE 3
129 
130 #ifdef __KERNEL__
131 #include <linux/module.h>
132 #include <linux/spinlock.h>
133 #include <linux/kref.h>
134 
135 /* 64 bit probes will have minor numbers starting at 192,
136  * 32 bit probes will have minor numbers starting at 196.
137  * On the vulcan, running 2.6.11 kernel without a udev daemon,
138  * you have to mknod the devices by hand:
139  * mknod /dev/usbtwod_64_0 c 180 192
140  * mknod /dev/usbtwod_64_1 c 180 193
141  * mknod /dev/usbtwod_64_2 c 180 194
142  * mknod /dev/usbtwod_64_3 c 180 195
143  * mknod /dev/usbtwod_32_0 c 180 196
144  * etc...
145  * On systems with a udev daemon, these device files are created
146  * automatically when the device is connected, using the
147  * name member of the struct usb_class_driver, which
148  * is passed to usb_register_dev() in the probe method.
149  */
150 #define USB_TWOD_64_V3_MINOR_BASE 192
151 #define USB_TWOD_64_MINOR_BASE 192
152 #define USB_TWOD_32_MINOR_BASE 196
153 
154 #define TWOD_IMG_BUFF_SIZE 4096
155 #define TWOD_SOR_BUFF_SIZE 128 /*PRS doc hs 70 as max possible size of housekeeping*/
156 #define TWOD_TAS_BUFF_SIZE 4
157 
158 /* SAMPLE_QUEUE_SIZE must be a power of 2 (required by circ_buf).
159  * In order for a circ_buf to tell the difference between empty
160  * and full, a full circ_buf contains (size-1) elements.
161  * In addition, SAMPLE_QUEUE_SIZE should be at least
162  * IMG_URBS_IN_FLIGHT + SOR_URBS_IN_FLIGHT + 1
163  */
164 /*
165  * Throughput tests on both an Intel core laptop PC and an Arcom Vulcan
166  * showed no difference in throughput with the following values
167  * for the sample queue sizes and number of urbs in flight:
168  * SAMPLE_QUEUE_SIZE IMG_URB_QUEUE_SIZE IMG_URBS_IN_FLIGHT
169  * 16 8 7
170  * 8 4 3
171  * 4 2 1
172  * We'll use the middle values.
173  * Having more than one urb in flight means a read()
174  * can return more than one image sample.
175  */
176 #define SAMPLE_QUEUE_SIZE 32
177 
178 /* This queue is only used if throttleRate > 0 */
179 #define IMG_URB_QUEUE_SIZE 16 /* power of two */
180 
181 #define IMG_URBS_IN_FLIGHT (IMG_URB_QUEUE_SIZE-1)
182 
183 #define SOR_URBS_IN_FLIGHT 4
184 
185 #define TAS_URB_QUEUE_SIZE 4 /* power of two */
186 
196 #define THROTTLE_JIFFIES (HZ / 10)
197 
198 struct twod_urb_sample
199 {
200  dsm_sample_time_t timetag; /* timetag of sample */
201  dsm_sample_length_t length; /* number of bytes in data */
202  unsigned int stype; /* sample type, 0=image, 1=SOR */
203  unsigned int data; /* True Airspeed for image sample */
204  int pre_urb_len; /* size of sample without urb contents */
205  struct urb *urb;
206 };
207 struct twod_house_urb_sample
208 {
209  int serialNum;
210  dsm_sample_time_t timetag;
211  unsigned int stype; //sor
212  unsigned int data; //dof or
213  int temperature;
214  double levelD1;
215  double levelD32;
216  double levelD64;
217 };
218 
219 struct sample_circ_buf
220 {
221  struct twod_urb_sample **buf;
222  int head;
223  int tail;
224 };
225 
226 struct urb_circ_buf
227 {
228  struct urb **buf;
229  int head;
230  int tail;
231 };
232 
233 
234 /* reading status keeper */
235 struct read_state
236 {
237  char *dataPtr; /* pointer into data of what is left to copy to user */
238  size_t bytesLeft; /* How much is left to copy to user buffer of sample_ptr */
239  struct twod_urb_sample *pendingSample; /* sample partly copied to user space */
240 };
241 
242 enum twod_probe_type { TWOD_64_V3, TWOD_64, TWOD_32 };
243 
244 /* Structure to hold all of our device specific stuff */
245 struct usb_twod
246 {
247  struct usb_device *udev; /* the usb device for this device */
248  struct usb_interface *interface; /* the interface for this device */
249  struct kref kref; /* reference counter for this structure */
250  rwlock_t usb_iface_lock; /* for detection of whether disconnect has been called */
251 
252  char dev_name[64]; /* device name for log messages */
253 
254  __u8 img_in_endpointAddr; /* the address of the image in endpoint */
255  __u8 tas_out_endpointAddr; /* the address of the tas out endpoint */
256  __u8 sor_in_endpointAddr; /* value is "SOR," the address of the shadow word in endpoint - for v3 sor (rather housekeeping packet) is now binary, this value is used in xml to sort */
257  int is_open; /* don't allow multiple opens. */
258 
259  enum twod_probe_type ptype;
260 
261  struct urb *img_urbs[IMG_URBS_IN_FLIGHT]; /* All data read urbs */
262  struct urb_circ_buf img_urb_q;
263 
264  struct urb *sor_urbs[SOR_URBS_IN_FLIGHT]; /* All sor read urbs */
265 
266  struct sample_circ_buf sampleq; /* samples that are ready for reading from user side */
267  spinlock_t sampqlock; /* control sample producer threads */
268 
269  struct urb_circ_buf tas_urb_q; /* queue of TAS samples for writing */
270 
271  wait_queue_head_t read_wait; /* Zzzzz ... */
272 
273  struct usb_twod_stats stats; /* various I/O counter for info */
274 
275  struct read_state readstate; /* leftovers from past read */
276 
277  int errorStatus; /* current error value */
278 
279  struct timer_list urbThrottle;
280 
281  int throttleJiffies; /* if throttling jiffie wait between
282  timer events */
283 
284  int nurbPerTimer; /* if throttling, how many urbs to submit on
285  every timer event */
286 
287  int latencyJiffies; /* maximum time user wants to wait
288  * between reads */
289 
290  unsigned long lastWakeup; /* time of last read queue wakeup */
291 
292  struct timer_list sendTASTimer; /* kernel timer for sending true airspeed */
293  int sendTASJiffies; /* when to send the next TAS */
294 
295  spinlock_t taslock; /* control access to TAS value */
296 
297  Tap2D tasValue; /* TAS value to send to probe (from user ioctl) */
298 
299  int consecTimeouts;
300 };
301 #endif // ifdef __KERNEL__
302 #endif
unsigned char ntap
which tap in the variable resistor (0-255)
Definition: usbtwod.h:72
struct _Tap2D_v1 Tap2Dv1
Struct to adjust probe slice rate for true airspeed.
struct _Tap2D_v2 Tap2D
This version is for rev2 of Spowarts USB board.
unsigned short probeResolution
which probe resolution
Definition: usbtwod.h:103
Struct to adjust probe slice rate for true airspeed.
Definition: usbtwod.h:69
unsigned short ntap
which tap in the variable resistor (0-255)
Definition: usbtwod.h:87
Definition: usbtwod.h:98
unsigned char cntr
counter from 1 to 10
Definition: usbtwod.h:92
unsigned int numSORs
Number of Shadow-ORs transfered from probe.
Definition: usbtwod.h:53
unsigned int lostTASs
Definition: usbtwod.h:55
unsigned char div10
boolean toggle for frequency divide by 10
Definition: usbtwod.h:74
unsigned char dummy
Definition: usbtwod.h:77
This version is for rev2 of Spowarts USB board.
Definition: usbtwod.h:84
unsigned int lostSORs
Definition: usbtwod.h:54
int dsm_sample_time_t
Depending on the module, either tenths of milliseconds, or milliseconds since 00:00 UTC today...
Definition: types.h:48
unsigned int urbErrors
Definition: usbtwod.h:56
unsigned int lostImages
Definition: usbtwod.h:51
unsigned int urbTimeouts
Definition: usbtwod.h:57
struct _Tap2D_v3 Tap2D_v3
unsigned short tas
sending tas*10, ntap calculation happens on probe
Definition: usbtwod.h:101
unsigned char div10
boolean toggle for frequency divide by 10
Definition: usbtwod.h:89
unsigned int numImages
Number of 4K buffers transfered from probe.
Definition: usbtwod.h:50
unsigned int dsm_sample_length_t
length of data portion of sample.
Definition: types.h:51
unsigned char cntr
counter from 1 to 10
Definition: usbtwod.h:76
Statistics gathered by the PMS2D USB driver.
Definition: usbtwod.h:47