Mercurial > ~darius > hgwebdir.cgi > wh1080
comparison wh1080.c @ 3:dc5ff2a1ed81
Be smarter about retries.
If the interrupt endpoint can't be read 100 times then retry the whole request.
author | Daniel O'Connor <darius@dons.net.au> |
---|---|
date | Wed, 10 Feb 2010 11:33:27 +1030 |
parents | 9da35e705144 |
children | b22a888eb975 |
comparison
equal
deleted
inserted
replaced
2:9da35e705144 | 3:dc5ff2a1ed81 |
---|---|
228 /* | 228 /* |
229 * Read 8 bytes from the device. | 229 * Read 8 bytes from the device. |
230 */ | 230 */ |
231 int read_station (char *buf) | 231 int read_station (char *buf) |
232 { | 232 { |
233 int bytes_read; | 233 #define MAXTRIES 100 |
234 int bytes_read, i = 0; | |
234 | 235 |
235 /* XXX Find out what all this means, and be cleverer about retries */ | 236 /* XXX Find out what all this means, and be cleverer about retries */ |
236 do | 237 do |
237 { | 238 { |
238 if ((bytes_read = usb_interrupt_read (station, | 239 if ((bytes_read = usb_interrupt_read (station, |
239 USB_ENDPOINT_IN | USB_RECIP_INTERFACE, | 240 USB_ENDPOINT_IN | USB_RECIP_INTERFACE, |
240 buf, | 241 buf, |
241 8, | 242 8, |
242 10 )) == 8 ) | 243 10 )) == 8 ){ |
244 if (i > 5) | |
245 fprintf(stderr, "Read OK after %d tries\n", i + 1); | |
243 return bytes_read; | 246 return bytes_read; |
247 } | |
248 | |
244 if (errno == EAGAIN) | 249 if (errno == EAGAIN) |
245 usleep (10000); | 250 usleep (10000); |
246 } | 251 i++; |
247 while (errno != EINTR); | 252 } |
248 fprintf (stderr, | 253 while (errno != EINTR && i < MAXTRIES); |
249 "Can't read device: %s (%d)\n", | 254 if (i == MAXTRIES) { |
250 usb_strerror (), | 255 #if 0 |
251 errno ); | 256 fprintf(stderr, |
257 "Can't read from device after %d attempts\n", MAXTRIES); | |
258 #endif | |
259 } else | |
260 fprintf (stderr, | |
261 "Can't read device: %s (%d)\n", | |
262 usb_strerror (), | |
263 errno ); | |
252 return 0; | 264 return 0; |
253 } | 265 } |
254 | 266 |
255 /* Read a page (32 bytes) from the device. */ | 267 /* Read a page (32 bytes) from the device. */ |
256 int read_station_page (uint16_t page, char *buf) | 268 int read_station_page (uint16_t page, char *buf) |
257 { | 269 { |
258 int bytes_read = 0; /* keep track of input */ | 270 int i, bytes_read, tries = 0; |
259 struct read_page_request | 271 struct read_page_request |
260 { | 272 { |
261 char command; /* XXX I'm guessing at this */ | 273 char command; /* XXX I'm guessing at this */ |
262 uint16_t address; | 274 uint16_t address; |
263 char length; | 275 char length; |
264 } __attribute__ ((packed)) request [2]; | 276 } __attribute__ ((packed)) request [2]; |
265 | 277 |
266 #if BYTE_ORDER == LITTLE_ENDIAN | 278 #if BYTE_ORDER == LITTLE_ENDIAN |
267 page = htobe16 (page); /* in big-endian for the command */ | 279 page = htobe16 (page); /* in big-endian for the command */ |
268 #endif | 280 #endif |
281 rerequest: | |
282 bytes_read = 0; | |
283 tries++; | |
284 if (tries > 10) { | |
285 fprintf(stderr, "Unable to read page after 10 tries\n"); | |
286 exit(1); | |
287 } | |
288 | |
269 request [0] = (struct read_page_request) {0xa1, page, 32}; | 289 request [0] = (struct read_page_request) {0xa1, page, 32}; |
270 request [1] = request [0]; | 290 request [1] = request [0]; |
271 if (write_station_control ((char *) request) == 0) | 291 if (write_station_control ((char *) request) == 0) |
272 exit (1); /* XXX we've already complained */ | 292 exit (1); /* XXX we've already complained */ |
273 while (bytes_read < 32) | 293 |
274 bytes_read += read_station ((char *) &buf [bytes_read]); | 294 while (bytes_read < 32) { |
295 if ((i = read_station ((char *) &buf [bytes_read])) == 0) { | |
296 #if 0 | |
297 fprintf(stderr, "Couldn't read from the device, rerequesting\n"); | |
298 #endif | |
299 goto rerequest; | |
300 } | |
301 | |
302 bytes_read += i; | |
303 } | |
304 | |
275 return bytes_read; | 305 return bytes_read; |
276 } | 306 } |
277 | 307 |
278 /* | 308 /* |
279 * Read and compare page from station. Keep trying until we get two that are | 309 * Read and compare page from station. Keep trying until we get two that are |
501 readings->wind_gust, | 531 readings->wind_gust, |
502 readings->wind_direction, | 532 readings->wind_direction, |
503 readings->wind_direction_text, | 533 readings->wind_direction_text, |
504 readings->rain - db_previous_rain ); | 534 readings->rain - db_previous_rain ); |
505 db_previous_rain = readings->rain; /* update our current rainfall XXX fix this */ | 535 db_previous_rain = readings->rain; /* update our current rainfall XXX fix this */ |
536 #if 0 | |
506 if (update) /* only if updates set */ | 537 if (update) /* only if updates set */ |
507 { | 538 { |
508 if (mysql_query (mysql, mysql_querytext)) | 539 if (mysql_query (mysql, mysql_querytext)) |
509 { | 540 { |
510 fprintf (stderr, | 541 fprintf (stderr, |
512 mysql_error (mysql), | 543 mysql_error (mysql), |
513 mysql_errno (mysql) ); | 544 mysql_errno (mysql) ); |
514 } | 545 } |
515 } | 546 } |
516 else if (verbose) | 547 else if (verbose) |
517 puts (mysql_querytext); | 548 #endif |
518 } | 549 } |
519 | 550 |
520 /* | 551 /* |
521 * Check if we have missed any updates since we last ran. | 552 * Check if we have missed any updates since we last ran. |
522 * | 553 * |
628 } | 659 } |
629 /* If we ever get here, this is what we should do */ | 660 /* If we ever get here, this is what we should do */ |
630 usb_release_interface (station, 0); | 661 usb_release_interface (station, 0); |
631 return 0; | 662 return 0; |
632 } | 663 } |
664 | |
665 | |
666 /* | |
667 *;;; Local Variables: *** | |
668 *;;; c-basic-offset:2 *** | |
669 *;;; End: *** | |
670 */ |