Using modified version of latest fork of stm32flash
This commit is contained in:
parent
0f78542eef
commit
1faf1d6b0d
|
@ -1,7 +1,9 @@
|
|||
.DS_store
|
||||
other/maple-bootloader/.dep
|
||||
other/maple-bootloader/TAGS
|
||||
other/maple-bootloader/tags
|
||||
other/maple-bootloader/cscope.out
|
||||
other/maple-bootloader/build
|
||||
other/maple-bootloader/*~
|
||||
.DS_store
|
||||
other/maple-bootloader/.dep
|
||||
other/maple-bootloader/TAGS
|
||||
other/maple-bootloader/tags
|
||||
other/maple-bootloader/cscope.out
|
||||
other/maple-bootloader/build
|
||||
other/maple-bootloader/*~
|
||||
*.o
|
||||
tools/src/stm32flash/src/parsers/parsers.a
|
||||
|
|
Binary file not shown.
|
@ -32,7 +32,7 @@
|
|||
#include "port.h"
|
||||
|
||||
|
||||
#if defined(__WIN32__) || defined(__CYGWIN__) || defined(__APPLE__)
|
||||
#if !defined(__linux__)
|
||||
|
||||
static port_err_t i2c_open(struct port_interface *port,
|
||||
struct port_options *ops)
|
||||
|
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
@ -18,6 +18,7 @@
|
|||
*/
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <limits.h>
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
@ -197,13 +198,27 @@ static port_err_t serial_setup(serial_t *h, const serial_baud_t baud,
|
|||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static int startswith(const char *haystack, const char *needle) {
|
||||
return strncmp(haystack, needle, strlen(needle)) == 0;
|
||||
}
|
||||
|
||||
static int is_tty(const char *path) {
|
||||
char resolved[PATH_MAX];
|
||||
|
||||
if(!realpath(path, resolved)) return 0;
|
||||
|
||||
if(startswith(resolved, "/dev/tty")) return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static port_err_t serial_posix_open(struct port_interface *port,
|
||||
struct port_options *ops)
|
||||
{
|
||||
serial_t *h;
|
||||
|
||||
/* 1. check device name match */
|
||||
if (strncmp(ops->device, "/dev/tty", strlen("/dev/tty")))
|
||||
if (!is_tty(ops->device))
|
||||
return PORT_ERR_NODEV;
|
||||
|
||||
/* 2. check options */
|
||||
|
|
|
@ -1,342 +1,341 @@
|
|||
/*
|
||||
stm32flash - Open Source ST STM32 flash program for *nix
|
||||
Copyright (C) 2010 Geoffrey McRae <geoff@spacevs.com>
|
||||
Copyright (C) 2010 Gareth McMullin <gareth@blacksphere.co.nz>
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
#include <windows.h>
|
||||
#include <ctype.h>
|
||||
|
||||
#include "serial.h"
|
||||
#include "port.h"
|
||||
|
||||
struct serial {
|
||||
HANDLE fd;
|
||||
DCB oldtio;
|
||||
DCB newtio;
|
||||
char setup_str[11];
|
||||
};
|
||||
|
||||
static serial_t *serial_open(const char *device)
|
||||
{
|
||||
serial_t *h = calloc(sizeof(serial_t), 1);
|
||||
char *devName;
|
||||
|
||||
/* timeout in ms */
|
||||
COMMTIMEOUTS timeouts = {MAXDWORD, MAXDWORD, 500, 0, 0};
|
||||
|
||||
/* Fix the device name if required */
|
||||
if (strlen(device) > 4 && device[0] != '\\') {
|
||||
devName = calloc(1, strlen(device) + 5);
|
||||
sprintf(devName, "\\\\.\\%s", device);
|
||||
} else {
|
||||
devName = (char *)device;
|
||||
}
|
||||
|
||||
/* Create file handle for port */
|
||||
h->fd = CreateFile(devName, GENERIC_READ | GENERIC_WRITE,
|
||||
0, /* Exclusive access */
|
||||
NULL, /* No security */
|
||||
OPEN_EXISTING,
|
||||
0, /* No overlap */
|
||||
NULL);
|
||||
|
||||
if (devName != device)
|
||||
free(devName);
|
||||
|
||||
if (h->fd == INVALID_HANDLE_VALUE) {
|
||||
if (GetLastError() == ERROR_FILE_NOT_FOUND)
|
||||
fprintf(stderr, "File not found: %s\n", device);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
SetupComm(h->fd, 4096, 4096); /* Set input and output buffer size */
|
||||
|
||||
SetCommTimeouts(h->fd, &timeouts);
|
||||
|
||||
SetCommMask(h->fd, EV_ERR); /* Notify us of error events */
|
||||
|
||||
GetCommState(h->fd, &h->oldtio); /* Retrieve port parameters */
|
||||
GetCommState(h->fd, &h->newtio); /* Retrieve port parameters */
|
||||
|
||||
/* PurgeComm(h->fd, PURGE_RXABORT | PURGE_TXCLEAR | PURGE_TXABORT | PURGE_TXCLEAR); */
|
||||
|
||||
return h;
|
||||
}
|
||||
|
||||
static void serial_flush(const serial_t *h)
|
||||
{
|
||||
/* We shouldn't need to flush in non-overlapping (blocking) mode */
|
||||
/* tcflush(h->fd, TCIFLUSH); */
|
||||
}
|
||||
|
||||
static void serial_close(serial_t *h)
|
||||
{
|
||||
serial_flush(h);
|
||||
SetCommState(h->fd, &h->oldtio);
|
||||
CloseHandle(h->fd);
|
||||
free(h);
|
||||
}
|
||||
|
||||
static port_err_t serial_setup(serial_t *h,
|
||||
const serial_baud_t baud,
|
||||
const serial_bits_t bits,
|
||||
const serial_parity_t parity,
|
||||
const serial_stopbit_t stopbit)
|
||||
{
|
||||
switch (baud) {
|
||||
case SERIAL_BAUD_1200: h->newtio.BaudRate = CBR_1200; break;
|
||||
/* case SERIAL_BAUD_1800: h->newtio.BaudRate = CBR_1800; break; */
|
||||
case SERIAL_BAUD_2400: h->newtio.BaudRate = CBR_2400; break;
|
||||
case SERIAL_BAUD_4800: h->newtio.BaudRate = CBR_4800; break;
|
||||
case SERIAL_BAUD_9600: h->newtio.BaudRate = CBR_9600; break;
|
||||
case SERIAL_BAUD_19200: h->newtio.BaudRate = CBR_19200; break;
|
||||
case SERIAL_BAUD_38400: h->newtio.BaudRate = CBR_38400; break;
|
||||
case SERIAL_BAUD_57600: h->newtio.BaudRate = CBR_57600; break;
|
||||
case SERIAL_BAUD_115200: h->newtio.BaudRate = CBR_115200; break;
|
||||
case SERIAL_BAUD_128000: h->newtio.BaudRate = CBR_128000; break;
|
||||
case SERIAL_BAUD_256000: h->newtio.BaudRate = CBR_256000; break;
|
||||
/* These are not defined in WinBase.h and might work or not */
|
||||
case SERIAL_BAUD_230400: h->newtio.BaudRate = 230400; break;
|
||||
case SERIAL_BAUD_460800: h->newtio.BaudRate = 460800; break;
|
||||
case SERIAL_BAUD_500000: h->newtio.BaudRate = 500000; break;
|
||||
case SERIAL_BAUD_576000: h->newtio.BaudRate = 576000; break;
|
||||
case SERIAL_BAUD_921600: h->newtio.BaudRate = 921600; break;
|
||||
case SERIAL_BAUD_1000000: h->newtio.BaudRate = 1000000; break;
|
||||
case SERIAL_BAUD_1500000: h->newtio.BaudRate = 1500000; break;
|
||||
case SERIAL_BAUD_2000000: h->newtio.BaudRate = 2000000; break;
|
||||
case SERIAL_BAUD_INVALID:
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
switch (bits) {
|
||||
case SERIAL_BITS_5: h->newtio.ByteSize = 5; break;
|
||||
case SERIAL_BITS_6: h->newtio.ByteSize = 6; break;
|
||||
case SERIAL_BITS_7: h->newtio.ByteSize = 7; break;
|
||||
case SERIAL_BITS_8: h->newtio.ByteSize = 8; break;
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
switch (parity) {
|
||||
case SERIAL_PARITY_NONE: h->newtio.Parity = NOPARITY; break;
|
||||
case SERIAL_PARITY_EVEN: h->newtio.Parity = EVENPARITY; break;
|
||||
case SERIAL_PARITY_ODD: h->newtio.Parity = ODDPARITY; break;
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
switch (stopbit) {
|
||||
case SERIAL_STOPBIT_1: h->newtio.StopBits = ONESTOPBIT; break;
|
||||
case SERIAL_STOPBIT_2: h->newtio.StopBits = TWOSTOPBITS; break;
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
/* reset the settings */
|
||||
h->newtio.fOutxCtsFlow = FALSE;
|
||||
h->newtio.fOutxDsrFlow = FALSE;
|
||||
h->newtio.fOutX = FALSE;
|
||||
h->newtio.fInX = FALSE;
|
||||
h->newtio.fNull = 0;
|
||||
h->newtio.fAbortOnError = 0;
|
||||
|
||||
/* set the settings */
|
||||
serial_flush(h);
|
||||
if (!SetCommState(h->fd, &h->newtio))
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
snprintf(h->setup_str, sizeof(h->setup_str), "%u %d%c%d",
|
||||
serial_get_baud_int(baud),
|
||||
serial_get_bits_int(bits),
|
||||
serial_get_parity_str(parity),
|
||||
serial_get_stopbit_int(stopbit)
|
||||
);
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_open(struct port_interface *port,
|
||||
struct port_options *ops)
|
||||
{
|
||||
serial_t *h;
|
||||
|
||||
/* 1. check device name match */
|
||||
/* Roger Clark. Added support for com10 and higher numbers */
|
||||
if (!((strlen(ops->device) == 4 || strlen(ops->device) == 5)
|
||||
&& !strncmp(ops->device, "COM", 3) && isdigit(ops->device[3]))
|
||||
&& !(!strncmp(ops->device, "\\\\.\\COM", strlen("\\\\.\\COM"))
|
||||
&& isdigit(ops->device[strlen("\\\\.\\COM")])))
|
||||
return PORT_ERR_NODEV;
|
||||
|
||||
/* 2. check options */
|
||||
if (ops->baudRate == SERIAL_BAUD_INVALID)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
if (serial_get_bits(ops->serial_mode) == SERIAL_BITS_INVALID)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
if (serial_get_parity(ops->serial_mode) == SERIAL_PARITY_INVALID)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
if (serial_get_stopbit(ops->serial_mode) == SERIAL_STOPBIT_INVALID)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
/* 3. open it */
|
||||
h = serial_open(ops->device);
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
/* 4. set options */
|
||||
if (serial_setup(h, ops->baudRate,
|
||||
serial_get_bits(ops->serial_mode),
|
||||
serial_get_parity(ops->serial_mode),
|
||||
serial_get_stopbit(ops->serial_mode)
|
||||
) != PORT_ERR_OK) {
|
||||
serial_close(h);
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
port->private = h;
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_close(struct port_interface *port)
|
||||
{
|
||||
serial_t *h;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
serial_close(h);
|
||||
port->private = NULL;
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_read(struct port_interface *port, void *buf,
|
||||
size_t nbyte)
|
||||
{
|
||||
serial_t *h;
|
||||
DWORD r;
|
||||
uint8_t *pos = (uint8_t *)buf;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
while (nbyte) {
|
||||
ReadFile(h->fd, pos, nbyte, &r, NULL);
|
||||
if (r == 0)
|
||||
return PORT_ERR_TIMEDOUT;
|
||||
if (r < 0)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
nbyte -= r;
|
||||
pos += r;
|
||||
}
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_write(struct port_interface *port, void *buf,
|
||||
size_t nbyte)
|
||||
{
|
||||
serial_t *h;
|
||||
DWORD r;
|
||||
uint8_t *pos = (uint8_t *)buf;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
while (nbyte) {
|
||||
if (!WriteFile(h->fd, pos, nbyte, &r, NULL))
|
||||
return PORT_ERR_UNKNOWN;
|
||||
if (r < 1)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
nbyte -= r;
|
||||
pos += r;
|
||||
}
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_gpio(struct port_interface *port,
|
||||
serial_gpio_t n, int level)
|
||||
{
|
||||
serial_t *h;
|
||||
int bit;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
switch (n) {
|
||||
case GPIO_RTS:
|
||||
bit = level ? SETRTS : CLRRTS;
|
||||
break;
|
||||
|
||||
case GPIO_DTR:
|
||||
bit = level ? SETDTR : CLRDTR;
|
||||
break;
|
||||
|
||||
case GPIO_BRK:
|
||||
if (level == 0)
|
||||
return PORT_ERR_OK;
|
||||
if (EscapeCommFunction(h->fd, SETBREAK) == 0)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
usleep(500000);
|
||||
if (EscapeCommFunction(h->fd, CLRBREAK) == 0)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
return PORT_ERR_OK;
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
/* handle RTS/DTR */
|
||||
if (EscapeCommFunction(h->fd, bit) == 0)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static const char *serial_w32_get_cfg_str(struct port_interface *port)
|
||||
{
|
||||
serial_t *h;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
return h ? h->setup_str : "INVALID";
|
||||
}
|
||||
|
||||
struct port_interface port_serial = {
|
||||
.name = "serial_w32",
|
||||
.flags = PORT_BYTE | PORT_GVR_ETX | PORT_CMD_INIT | PORT_RETRY,
|
||||
.open = serial_w32_open,
|
||||
.close = serial_w32_close,
|
||||
.read = serial_w32_read,
|
||||
.write = serial_w32_write,
|
||||
.gpio = serial_w32_gpio,
|
||||
.get_cfg_str = serial_w32_get_cfg_str,
|
||||
};
|
||||
/*
|
||||
stm32flash - Open Source ST STM32 flash program for *nix
|
||||
Copyright (C) 2010 Geoffrey McRae <geoff@spacevs.com>
|
||||
Copyright (C) 2010 Gareth McMullin <gareth@blacksphere.co.nz>
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
#include <windows.h>
|
||||
#include <ctype.h>
|
||||
|
||||
#include "serial.h"
|
||||
#include "port.h"
|
||||
|
||||
struct serial {
|
||||
HANDLE fd;
|
||||
DCB oldtio;
|
||||
DCB newtio;
|
||||
char setup_str[11];
|
||||
};
|
||||
|
||||
static serial_t *serial_open(const char *device)
|
||||
{
|
||||
serial_t *h = calloc(sizeof(serial_t), 1);
|
||||
char *devName;
|
||||
|
||||
/* timeout in ms */
|
||||
COMMTIMEOUTS timeouts = {MAXDWORD, MAXDWORD, 500, 0, 0};
|
||||
|
||||
/* Fix the device name if required */
|
||||
if (strlen(device) > 4 && device[0] != '\\') {
|
||||
devName = calloc(1, strlen(device) + 5);
|
||||
sprintf(devName, "\\\\.\\%s", device);
|
||||
} else {
|
||||
devName = (char *)device;
|
||||
}
|
||||
|
||||
/* Create file handle for port */
|
||||
h->fd = CreateFile(devName, GENERIC_READ | GENERIC_WRITE,
|
||||
0, /* Exclusive access */
|
||||
NULL, /* No security */
|
||||
OPEN_EXISTING,
|
||||
0, /* No overlap */
|
||||
NULL);
|
||||
|
||||
if (devName != device)
|
||||
free(devName);
|
||||
|
||||
if (h->fd == INVALID_HANDLE_VALUE) {
|
||||
if (GetLastError() == ERROR_FILE_NOT_FOUND)
|
||||
fprintf(stderr, "File not found: %s\n", device);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
SetupComm(h->fd, 4096, 4096); /* Set input and output buffer size */
|
||||
|
||||
SetCommTimeouts(h->fd, &timeouts);
|
||||
|
||||
SetCommMask(h->fd, EV_ERR); /* Notify us of error events */
|
||||
|
||||
GetCommState(h->fd, &h->oldtio); /* Retrieve port parameters */
|
||||
GetCommState(h->fd, &h->newtio); /* Retrieve port parameters */
|
||||
|
||||
/* PurgeComm(h->fd, PURGE_RXABORT | PURGE_TXCLEAR | PURGE_TXABORT | PURGE_TXCLEAR); */
|
||||
|
||||
return h;
|
||||
}
|
||||
|
||||
static void serial_flush(const serial_t *h)
|
||||
{
|
||||
/* We shouldn't need to flush in non-overlapping (blocking) mode */
|
||||
/* tcflush(h->fd, TCIFLUSH); */
|
||||
}
|
||||
|
||||
static void serial_close(serial_t *h)
|
||||
{
|
||||
serial_flush(h);
|
||||
SetCommState(h->fd, &h->oldtio);
|
||||
CloseHandle(h->fd);
|
||||
free(h);
|
||||
}
|
||||
|
||||
static port_err_t serial_setup(serial_t *h,
|
||||
const serial_baud_t baud,
|
||||
const serial_bits_t bits,
|
||||
const serial_parity_t parity,
|
||||
const serial_stopbit_t stopbit)
|
||||
{
|
||||
switch (baud) {
|
||||
case SERIAL_BAUD_1200: h->newtio.BaudRate = CBR_1200; break;
|
||||
/* case SERIAL_BAUD_1800: h->newtio.BaudRate = CBR_1800; break; */
|
||||
case SERIAL_BAUD_2400: h->newtio.BaudRate = CBR_2400; break;
|
||||
case SERIAL_BAUD_4800: h->newtio.BaudRate = CBR_4800; break;
|
||||
case SERIAL_BAUD_9600: h->newtio.BaudRate = CBR_9600; break;
|
||||
case SERIAL_BAUD_19200: h->newtio.BaudRate = CBR_19200; break;
|
||||
case SERIAL_BAUD_38400: h->newtio.BaudRate = CBR_38400; break;
|
||||
case SERIAL_BAUD_57600: h->newtio.BaudRate = CBR_57600; break;
|
||||
case SERIAL_BAUD_115200: h->newtio.BaudRate = CBR_115200; break;
|
||||
case SERIAL_BAUD_128000: h->newtio.BaudRate = CBR_128000; break;
|
||||
case SERIAL_BAUD_256000: h->newtio.BaudRate = CBR_256000; break;
|
||||
/* These are not defined in WinBase.h and might work or not */
|
||||
case SERIAL_BAUD_230400: h->newtio.BaudRate = 230400; break;
|
||||
case SERIAL_BAUD_460800: h->newtio.BaudRate = 460800; break;
|
||||
case SERIAL_BAUD_500000: h->newtio.BaudRate = 500000; break;
|
||||
case SERIAL_BAUD_576000: h->newtio.BaudRate = 576000; break;
|
||||
case SERIAL_BAUD_921600: h->newtio.BaudRate = 921600; break;
|
||||
case SERIAL_BAUD_1000000: h->newtio.BaudRate = 1000000; break;
|
||||
case SERIAL_BAUD_1500000: h->newtio.BaudRate = 1500000; break;
|
||||
case SERIAL_BAUD_2000000: h->newtio.BaudRate = 2000000; break;
|
||||
case SERIAL_BAUD_INVALID:
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
switch (bits) {
|
||||
case SERIAL_BITS_5: h->newtio.ByteSize = 5; break;
|
||||
case SERIAL_BITS_6: h->newtio.ByteSize = 6; break;
|
||||
case SERIAL_BITS_7: h->newtio.ByteSize = 7; break;
|
||||
case SERIAL_BITS_8: h->newtio.ByteSize = 8; break;
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
switch (parity) {
|
||||
case SERIAL_PARITY_NONE: h->newtio.Parity = NOPARITY; break;
|
||||
case SERIAL_PARITY_EVEN: h->newtio.Parity = EVENPARITY; break;
|
||||
case SERIAL_PARITY_ODD: h->newtio.Parity = ODDPARITY; break;
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
switch (stopbit) {
|
||||
case SERIAL_STOPBIT_1: h->newtio.StopBits = ONESTOPBIT; break;
|
||||
case SERIAL_STOPBIT_2: h->newtio.StopBits = TWOSTOPBITS; break;
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
/* reset the settings */
|
||||
h->newtio.fOutxCtsFlow = FALSE;
|
||||
h->newtio.fOutxDsrFlow = FALSE;
|
||||
h->newtio.fOutX = FALSE;
|
||||
h->newtio.fInX = FALSE;
|
||||
h->newtio.fNull = 0;
|
||||
h->newtio.fAbortOnError = 0;
|
||||
|
||||
/* set the settings */
|
||||
serial_flush(h);
|
||||
if (!SetCommState(h->fd, &h->newtio))
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
snprintf(h->setup_str, sizeof(h->setup_str), "%u %d%c%d",
|
||||
serial_get_baud_int(baud),
|
||||
serial_get_bits_int(bits),
|
||||
serial_get_parity_str(parity),
|
||||
serial_get_stopbit_int(stopbit)
|
||||
);
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_open(struct port_interface *port,
|
||||
struct port_options *ops)
|
||||
{
|
||||
serial_t *h;
|
||||
|
||||
/* 1. check device name match */
|
||||
if (!((strlen(ops->device) == 4 || strlen(ops->device) == 5)
|
||||
&& !strncmp(ops->device, "COM", 3) && isdigit(ops->device[3]))
|
||||
&& !(!strncmp(ops->device, "\\\\.\\COM", strlen("\\\\.\\COM"))
|
||||
&& isdigit(ops->device[strlen("\\\\.\\COM")])))
|
||||
return PORT_ERR_NODEV;
|
||||
|
||||
/* 2. check options */
|
||||
if (ops->baudRate == SERIAL_BAUD_INVALID)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
if (serial_get_bits(ops->serial_mode) == SERIAL_BITS_INVALID)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
if (serial_get_parity(ops->serial_mode) == SERIAL_PARITY_INVALID)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
if (serial_get_stopbit(ops->serial_mode) == SERIAL_STOPBIT_INVALID)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
/* 3. open it */
|
||||
h = serial_open(ops->device);
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
/* 4. set options */
|
||||
if (serial_setup(h, ops->baudRate,
|
||||
serial_get_bits(ops->serial_mode),
|
||||
serial_get_parity(ops->serial_mode),
|
||||
serial_get_stopbit(ops->serial_mode)
|
||||
) != PORT_ERR_OK) {
|
||||
serial_close(h);
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
port->private = h;
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_close(struct port_interface *port)
|
||||
{
|
||||
serial_t *h;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
serial_close(h);
|
||||
port->private = NULL;
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_read(struct port_interface *port, void *buf,
|
||||
size_t nbyte)
|
||||
{
|
||||
serial_t *h;
|
||||
DWORD r;
|
||||
uint8_t *pos = (uint8_t *)buf;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
while (nbyte) {
|
||||
ReadFile(h->fd, pos, nbyte, &r, NULL);
|
||||
if (r == 0)
|
||||
return PORT_ERR_TIMEDOUT;
|
||||
if (r < 0)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
nbyte -= r;
|
||||
pos += r;
|
||||
}
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_write(struct port_interface *port, void *buf,
|
||||
size_t nbyte)
|
||||
{
|
||||
serial_t *h;
|
||||
DWORD r;
|
||||
uint8_t *pos = (uint8_t *)buf;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
while (nbyte) {
|
||||
if (!WriteFile(h->fd, pos, nbyte, &r, NULL))
|
||||
return PORT_ERR_UNKNOWN;
|
||||
if (r < 1)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
nbyte -= r;
|
||||
pos += r;
|
||||
}
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static port_err_t serial_w32_gpio(struct port_interface *port,
|
||||
serial_gpio_t n, int level)
|
||||
{
|
||||
serial_t *h;
|
||||
int bit;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
if (h == NULL)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
switch (n) {
|
||||
case GPIO_RTS:
|
||||
bit = level ? SETRTS : CLRRTS;
|
||||
break;
|
||||
|
||||
case GPIO_DTR:
|
||||
bit = level ? SETDTR : CLRDTR;
|
||||
break;
|
||||
|
||||
case GPIO_BRK:
|
||||
if (level == 0)
|
||||
return PORT_ERR_OK;
|
||||
if (EscapeCommFunction(h->fd, SETBREAK) == 0)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
usleep(500000);
|
||||
if (EscapeCommFunction(h->fd, CLRBREAK) == 0)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
return PORT_ERR_OK;
|
||||
|
||||
default:
|
||||
return PORT_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
/* handle RTS/DTR */
|
||||
if (EscapeCommFunction(h->fd, bit) == 0)
|
||||
return PORT_ERR_UNKNOWN;
|
||||
|
||||
return PORT_ERR_OK;
|
||||
}
|
||||
|
||||
static const char *serial_w32_get_cfg_str(struct port_interface *port)
|
||||
{
|
||||
serial_t *h;
|
||||
|
||||
h = (serial_t *)port->private;
|
||||
return h ? h->setup_str : "INVALID";
|
||||
}
|
||||
|
||||
struct port_interface port_serial = {
|
||||
.name = "serial_w32",
|
||||
.flags = PORT_BYTE | PORT_GVR_ETX | PORT_CMD_INIT | PORT_RETRY,
|
||||
.open = serial_w32_open,
|
||||
.close = serial_w32_close,
|
||||
.read = serial_w32_read,
|
||||
.write = serial_w32_write,
|
||||
.gpio = serial_w32_gpio,
|
||||
.get_cfg_str = serial_w32_get_cfg_str,
|
||||
};
|
||||
|
|
|
@ -784,7 +784,7 @@ stm32_err_t stm32_erase_memory(const stm32_t *stm, uint8_t spage, uint8_t pages)
|
|||
return STM32_ERR_UNKNOWN;
|
||||
}
|
||||
|
||||
s_err = stm32_get_ack_timeout(stm, STM32_SECTERASE_TIMEOUT);
|
||||
s_err = stm32_get_ack_timeout(stm, pages * STM32_SECTERASE_TIMEOUT);
|
||||
if (s_err != STM32_ERR_OK) {
|
||||
fprintf(stderr, "Page-by-page erase failed. Check the maximum pages your device supports.\n");
|
||||
if (port->flags & PORT_STRETCH_W
|
||||
|
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Loading…
Reference in New Issue