From c24413879c42c24a534735ef71859ab1054a4716 Mon Sep 17 00:00:00 2001 From: Carl-Daniel Hailfinger Date: Tue, 9 Nov 2010 22:00:31 +0000 Subject: Support setting the Dediprog SF100 SPI voltage Add a generic voltage parameter parser. Move tolower_string() from dummyflasher.c to flashrom.c to make it available everywhere. Corresponding to flashrom svn r1226. Signed-off-by: Carl-Daniel Hailfinger Acked-by: Stefan Reinauer --- dediprog.c | 94 ++++++++++++++++++++++++++++++++++++++++++++++++---------- dummyflasher.c | 7 ----- flash.h | 1 + flashrom.8 | 15 +++++++++- flashrom.c | 7 +++++ 5 files changed, 100 insertions(+), 24 deletions(-) diff --git a/dediprog.c b/dediprog.c index cf4bd645..1889bfe1 100644 --- a/dediprog.c +++ b/dediprog.c @@ -55,34 +55,35 @@ static struct usb_device *get_device_by_vid_pid(uint16_t vid, uint16_t pid) //int usb_control_msg(usb_dev_handle *dev, int requesttype, int request, int value, int index, char *bytes, int size, int timeout); -static int dediprog_set_spi_voltage(uint16_t voltage) +static int dediprog_set_spi_voltage(int millivolt) { int ret; - unsigned int mv; + uint16_t voltage_selector; - switch (voltage) { - case 0x0: + switch (millivolt) { + case 0: /* Admittedly this one is an assumption. */ - mv = 0; + voltage_selector = 0x0; break; - case 0x12: - mv = 1800; + case 1800: + voltage_selector = 0x12; break; - case 0x11: - mv = 2500; + case 2500: + voltage_selector = 0x11; break; - case 0x10: - mv = 3500; + case 3500: + voltage_selector = 0x10; break; default: - msg_perr("Unknown voltage selector 0x%x! Aborting.\n", voltage); + msg_perr("Unknown voltage %i mV! Aborting.\n", millivolt); return 1; } - msg_pdbg("Setting SPI voltage to %u.%03u V\n", mv / 1000, mv % 1000); + msg_pdbg("Setting SPI voltage to %u.%03u V\n", millivolt / 1000, + millivolt % 1000); - ret = usb_control_msg(dediprog_handle, 0x42, 0x9, voltage, 0xff, NULL, 0x0, DEFAULT_TIMEOUT); + ret = usb_control_msg(dediprog_handle, 0x42, 0x9, voltage_selector, 0xff, NULL, 0x0, DEFAULT_TIMEOUT); if (ret != 0x0) { - msg_perr("Command Set SPI Voltage 0x%x failed!\n", voltage); + msg_perr("Command Set SPI Voltage 0x%x failed!\n", voltage_selector); return 1; } return 0; @@ -279,13 +280,74 @@ static int dediprog_command_f(int timeout) } #endif +static int parse_voltage(char *voltage) +{ + char *tmp = NULL; + int i; + int millivolt; + int fraction = 0; + + if (!voltage || !strlen(voltage)) { + msg_perr("Empty voltage= specified.\n"); + return -1; + } + millivolt = (int)strtol(voltage, &tmp, 0); + voltage = tmp; + /* Handle "," and "." as decimal point. Everything after it is assumed + * to be in decimal notation. + */ + if ((*voltage == '.') || (*voltage == ',')) { + voltage++; + for (i = 0; i < 3; i++) { + fraction *= 10; + /* Don't advance if the current character is invalid, + * but continue multiplying. + */ + if ((*voltage < '0') || (*voltage > '9')) + continue; + fraction += *voltage - '0'; + voltage++; + } + /* Throw away remaining digits. */ + voltage += strspn(voltage, "0123456789"); + } + /* The remaining string must be empty or "mV" or "V". */ + tolower_string(voltage); + + /* No unit or "V". */ + if ((*voltage == '\0') || !strncmp(voltage, "v", 1)) { + millivolt *= 1000; + millivolt += fraction; + } else if (!strncmp(voltage, "mv", 2) || + !strncmp(voltage, "milliv", 6)) { + /* No adjustment. fraction is discarded. */ + } else { + /* Garbage at the end of the string. */ + msg_perr("Garbage voltage= specified.\n"); + return -1; + } + return millivolt; +} + /* URB numbers refer to the first log ever captured. */ int dediprog_init(void) { struct usb_device *dev; + char *voltage; + int millivolt = 3500; msg_pspew("%s\n", __func__); + voltage = extract_programmer_param("voltage"); + if (voltage) { + millivolt = parse_voltage(voltage); + free(voltage); + if (millivolt < 0) { + return 1; + } + msg_pinfo("Setting voltage to %i mV\n", millivolt); + } + /* Here comes the USB stuff. */ usb_init(); usb_find_busses(); @@ -315,7 +377,7 @@ int dediprog_init(void) if (dediprog_command_c()) return 1; /* URB 11. Command Set SPI Voltage. */ - if (dediprog_set_spi_voltage(0x10)) + if (dediprog_set_spi_voltage(millivolt)) return 1; buses_supported = CHIP_BUSTYPE_SPI; diff --git a/dummyflasher.c b/dummyflasher.c index 21ee9b4d..473e45e9 100644 --- a/dummyflasher.c +++ b/dummyflasher.c @@ -19,7 +19,6 @@ #include #include -#include #include "flash.h" #include "chipdrivers.h" #include "programmer.h" @@ -61,12 +60,6 @@ static int emu_jedec_ce_c7_size = 0; static int spi_write_256_chunksize = 256; -static void tolower_string(char *str) -{ - for (; *str != '\0'; str++) - *str = (char)tolower((unsigned char)*str); -} - int dummy_init(void) { char *bustext = NULL; diff --git a/flash.h b/flash.h index 6ac3c1cf..250482fc 100644 --- a/flash.h +++ b/flash.h @@ -197,6 +197,7 @@ struct flashchip *probe_flash(struct flashchip *first_flash, int force); int read_flash_to_file(struct flashchip *flash, char *filename); int min(int a, int b); int max(int a, int b); +void tolower_string(char *str); char *extract_param(char **haystack, char *needle, char *delim); int check_erased_range(struct flashchip *flash, int start, int len); int verify_range(struct flashchip *flash, uint8_t *cmpbuf, int start, int len, char *message); diff --git a/flashrom.8 b/flashrom.8 index 667e06bc..0f2a6c4d 100644 --- a/flashrom.8 +++ b/flashrom.8 @@ -402,7 +402,20 @@ can be any of (in Hz). The default is the maximum frequency of 8 MHz. .TP .BR "dediprog " programmer -No parameters defined yet. +An optional +.B voltage +parameter specifies the voltage the Dediprog should use. The default unit is +Volt if no unit is specified. You can use +.BR mV ", " milliVolt ", " V " or " Volt +as unit specifier. Syntax is +.sp +.B "flashrom \-p dediprog:voltage=value" +.sp +where +.B value +can be any of +.BR 0V ", " 1.8V ", " 2.5V ", " 3.5V +or the equivalent in mV. .TP .BR "rayer_spi " programmer The default I/O base address used for the parallel port is 0x378 and you can use diff --git a/flashrom.c b/flashrom.c index 4fc8fca6..b45ac132 100644 --- a/flashrom.c +++ b/flashrom.c @@ -29,6 +29,7 @@ #endif #include #include +#include #include #if HAVE_UTSNAME == 1 #include @@ -615,6 +616,12 @@ int bitcount(unsigned long a) return i; } +void tolower_string(char *str) +{ + for (; *str != '\0'; str++) + *str = (char)tolower((unsigned char)*str); +} + char *strcat_realloc(char *dest, const char *src) { dest = realloc(dest, strlen(dest) + strlen(src) + 1); -- cgit v1.2.3