diff options
Diffstat (limited to 'drivers/usb/serial/cypress_m8.c')
-rw-r--r-- | drivers/usb/serial/cypress_m8.c | 104 |
1 files changed, 59 insertions, 45 deletions
diff --git a/drivers/usb/serial/cypress_m8.c b/drivers/usb/serial/cypress_m8.c index bdeda0936951..4bf45c711b9d 100644 --- a/drivers/usb/serial/cypress_m8.c +++ b/drivers/usb/serial/cypress_m8.c | |||
@@ -291,6 +291,59 @@ static struct usb_serial_driver cypress_ca42v2_device = { | |||
291 | *****************************************************************************/ | 291 | *****************************************************************************/ |
292 | 292 | ||
293 | 293 | ||
294 | static int analyze_baud_rate(struct usb_serial_port *port, unsigned baud_mask) | ||
295 | { | ||
296 | int new_rate; | ||
297 | struct cypress_private *priv; | ||
298 | priv = usb_get_serial_port_data(port); | ||
299 | |||
300 | /* | ||
301 | * The general purpose firmware for the Cypress M8 allows for | ||
302 | * a maximum speed of 57600bps (I have no idea whether DeLorme | ||
303 | * chose to use the general purpose firmware or not), if you | ||
304 | * need to modify this speed setting for your own project | ||
305 | * please add your own chiptype and modify the code likewise. | ||
306 | * The Cypress HID->COM device will work successfully up to | ||
307 | * 115200bps (but the actual throughput is around 3kBps). | ||
308 | */ | ||
309 | new_rate = mask_to_rate(baud_mask); | ||
310 | if (new_rate < 0) { | ||
311 | dbg("%s - failed setting baud rate, untranslatable speed", | ||
312 | __func__); | ||
313 | return -1; | ||
314 | } | ||
315 | if (port->serial->dev->speed == USB_SPEED_LOW) { | ||
316 | /* | ||
317 | * Mike Isely <isely@pobox.com> 2-Feb-2008: The | ||
318 | * Cypress app note that describes this mechanism | ||
319 | * states the the low-speed part can't handle more | ||
320 | * than 800 bytes/sec, in which case 4800 baud is the | ||
321 | * safest speed for a part like that. | ||
322 | */ | ||
323 | if (new_rate > 4800) { | ||
324 | dbg("%s - failed setting baud rate, device incapable " | ||
325 | "speed %d", __func__, new_rate); | ||
326 | return -1; | ||
327 | } | ||
328 | } | ||
329 | switch (priv->chiptype) { | ||
330 | case CT_EARTHMATE: | ||
331 | if (new_rate <= 600) { | ||
332 | /* 300 and 600 baud rates are supported under | ||
333 | * the generic firmware, but are not used with | ||
334 | * NMEA and SiRF protocols */ | ||
335 | dbg("%s - failed setting baud rate, unsupported speed " | ||
336 | "of %d on Earthmate GPS", __func__, new_rate); | ||
337 | return -1; | ||
338 | } | ||
339 | break; | ||
340 | default: | ||
341 | break; | ||
342 | } | ||
343 | return new_rate; | ||
344 | } | ||
345 | |||
346 | |||
294 | /* This function can either set or retrieve the current serial line settings */ | 347 | /* This function can either set or retrieve the current serial line settings */ |
295 | static int cypress_serial_control (struct usb_serial_port *port, unsigned baud_mask, int data_bits, int stop_bits, | 348 | static int cypress_serial_control (struct usb_serial_port *port, unsigned baud_mask, int data_bits, int stop_bits, |
296 | int parity_enable, int parity_type, int reset, int cypress_request_type) | 349 | int parity_enable, int parity_type, int reset, int cypress_request_type) |
@@ -309,54 +362,15 @@ static int cypress_serial_control (struct usb_serial_port *port, unsigned baud_m | |||
309 | 362 | ||
310 | switch(cypress_request_type) { | 363 | switch(cypress_request_type) { |
311 | case CYPRESS_SET_CONFIG: | 364 | case CYPRESS_SET_CONFIG: |
312 | 365 | new_baudrate = priv->baud_rate; | |
313 | /* | ||
314 | * The general purpose firmware for the Cypress M8 allows for a maximum speed | ||
315 | * of 57600bps (I have no idea whether DeLorme chose to use the general purpose | ||
316 | * firmware or not), if you need to modify this speed setting for your own | ||
317 | * project please add your own chiptype and modify the code likewise. The | ||
318 | * Cypress HID->COM device will work successfully up to 115200bps (but the | ||
319 | * actual throughput is around 3kBps). | ||
320 | */ | ||
321 | if (baud_mask != priv->cbr_mask) { | 366 | if (baud_mask != priv->cbr_mask) { |
322 | dbg("%s - baud rate is changing", __FUNCTION__); | 367 | dbg("%s - baud rate is changing", __FUNCTION__); |
323 | if ( priv->chiptype == CT_EARTHMATE ) { | 368 | retval = analyze_baud_rate(port, baud_mask); |
324 | /* 300 and 600 baud rates are supported under the generic firmware, | 369 | if (retval >= 0) { |
325 | * but are not used with NMEA and SiRF protocols */ | 370 | new_baudrate = retval; |
326 | 371 | dbg("%s - New baud rate set to %d", | |
327 | if ( (baud_mask == B300) || (baud_mask == B600) ) { | 372 | __func__, new_baudrate); |
328 | err("%s - failed setting baud rate, unsupported speed", | ||
329 | __FUNCTION__); | ||
330 | new_baudrate = priv->baud_rate; | ||
331 | } else if ( (new_baudrate = mask_to_rate(baud_mask)) == -1) { | ||
332 | err("%s - failed setting baud rate, unsupported speed", | ||
333 | __FUNCTION__); | ||
334 | new_baudrate = priv->baud_rate; | ||
335 | } | ||
336 | } else if (priv->chiptype == CT_CYPHIDCOM) { | ||
337 | if ( (new_baudrate = mask_to_rate(baud_mask)) == -1) { | ||
338 | err("%s - failed setting baud rate, unsupported speed", | ||
339 | __FUNCTION__); | ||
340 | new_baudrate = priv->baud_rate; | ||
341 | } | ||
342 | } else if (priv->chiptype == CT_CA42V2) { | ||
343 | if ( (new_baudrate = mask_to_rate(baud_mask)) == -1) { | ||
344 | err("%s - failed setting baud rate, unsupported speed", | ||
345 | __FUNCTION__); | ||
346 | new_baudrate = priv->baud_rate; | ||
347 | } | ||
348 | } else if (priv->chiptype == CT_GENERIC) { | ||
349 | if ( (new_baudrate = mask_to_rate(baud_mask)) == -1) { | ||
350 | err("%s - failed setting baud rate, unsupported speed", | ||
351 | __FUNCTION__); | ||
352 | new_baudrate = priv->baud_rate; | ||
353 | } | ||
354 | } else { | ||
355 | info("%s - please define your chiptype", __FUNCTION__); | ||
356 | new_baudrate = priv->baud_rate; | ||
357 | } | 373 | } |
358 | } else { /* baud rate not changing, keep the old */ | ||
359 | new_baudrate = priv->baud_rate; | ||
360 | } | 374 | } |
361 | dbg("%s - baud rate is being sent as %d", __FUNCTION__, new_baudrate); | 375 | dbg("%s - baud rate is being sent as %d", __FUNCTION__, new_baudrate); |
362 | 376 | ||