-
Notifications
You must be signed in to change notification settings - Fork 39
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add Mode 5: Physical reset, for UARTS with only RTS, no DTR. #28
base: master
Are you sure you want to change the base?
Changes from 2 commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -53,6 +53,7 @@ const char *usage = | |
"\t\t\tn=2 Two-wire UART, Reset by DTR\n" | ||
"\t\t\tn=3 Single-wire UART, Reset by RTS\n" | ||
"\t\t\tn=4 Two-wire UART, Reset by RTS\n" | ||
"\t\t\tn=5 Single-wire UART, Hardware Reset, reset state read by CTS (modified mode 1/3)\n" | ||
"\t\t\tdefault: n=1\n" | ||
"\t-P n\tSet protocol version\n" | ||
"\t\t\tn=-1 Try to autodetect the protocol version from the unit's Silicon Signature\n" | ||
|
@@ -117,14 +118,21 @@ int main(int argc, char *argv[]) | |
break; | ||
case 'm': | ||
mode = strtol(optarg, &endp, 10) - 1; | ||
// mode = desired communication mode from terminal input - 1 | ||
if (optarg == endp | ||
|| MODE_MAX_VALUE < mode | ||
|| MODE_MIN_VALUE > mode) | ||
{ | ||
fprintf(stderr, "Invalid mode\n"); | ||
printf("%s", usage); | ||
// For debug | ||
//printf("Communication mode passed to rl78 funcs: %i\r\n", mode); | ||
//printf("Mode value expression: %i\r\n",mode_val_expr); | ||
return EINVAL; | ||
} | ||
// For debug | ||
//printf("Communication mode passed to rl78 funcs: %i\r\n", mode); | ||
//printf("Mode value expression: %i\r\n",mode_val_expr); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Normally, you'd remove your temporary debugging code from the commit before issuing a PR. Or, wrap it in |
||
break; | ||
case 't': | ||
terminal = 1; | ||
|
@@ -222,7 +230,16 @@ int main(int argc, char *argv[]) | |
|
||
if (invert_reset) | ||
{ | ||
mode |= MODE_INVERT_RESET; | ||
if (mode == 4) | ||
{ | ||
mode = 4; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This code is only ever run if There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Actually, treating That is, just remove this change and go back to the original code. It's ok if |
||
printf("Using mode 5. INVERT RESET command will not be applied.\r\n"); | ||
} | ||
else | ||
{ | ||
mode |= MODE_INVERT_RESET; | ||
} | ||
|
||
} | ||
char *portname = NULL; | ||
char *filename = NULL; | ||
|
@@ -473,9 +490,18 @@ int main(int argc, char *argv[]) | |
{ | ||
if (1 <= verbose_level) | ||
{ | ||
printf("Reset MCU\n"); | ||
if (mode == 4) // operating in mode 5 | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. When used to determine whether reset is controlled by the code, or triggered by the user, change This happens in multiple places. I'll just say |
||
{ | ||
printf("Done! Use HW reset switch to reset MCU.\r\n"); | ||
} | ||
else { | ||
printf("Resetting MCU...\n"); | ||
} | ||
} | ||
if (mode != 4) // Case for HW reset switch | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
{ | ||
rl78_reset(fd, mode); | ||
} | ||
rl78_reset(fd, mode); | ||
} | ||
} | ||
while (0); | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -21,6 +21,8 @@ | |
#include <string.h> | ||
#include <stdio.h> | ||
#include "wait_kbhit.h" | ||
#include <errno.h> | ||
#include <sys/ioctl.h> | ||
|
||
#include "serial.h" | ||
#include "rl78.h" | ||
|
@@ -29,7 +31,13 @@ extern int verbose_level; | |
static unsigned char communication_mode; | ||
|
||
static void rl78_set_reset(port_handle_t fd, int mode, int value) | ||
// Set reset signal for MCU based on mode (not applicable for mode 5 with hardware switch) | ||
{ | ||
if (mode == 4) // operating in mode 5 | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
{ | ||
printf("No GPIO SW reset available, must use switch\r\n"); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Pedantic Pet Peeve of mine: feel free to ignore. ;-) Switches are latching and/or sliding/rotating, buttons are momentary and/or linear motion. This is a button, not a switch. Yes, yes, this depends on how you implement the hardware. But I've never seen a Reset Switch, only ever Reset Buttons. Possibly a Reset Momentary Switch on front-panels of old mini-computers. But these are almost certainly going to be buttons. |
||
} | ||
else { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. GitHub won't let me select the whole block here. But fix the indentation below. |
||
int level = (mode & MODE_INVERT_RESET) ? !value : value; | ||
|
||
if (MODE_RESET_RTS == (mode & MODE_RESET)) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We shouldn't be messing with RTS or DTR if we are inputing the reset signal.
|
||
|
@@ -40,48 +48,105 @@ static void rl78_set_reset(port_handle_t fd, int mode, int value) | |
{ | ||
serial_set_dtr(fd, level); | ||
} | ||
} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Indentation is broken down to here. |
||
} | ||
|
||
int rl78_reset_init(port_handle_t fd, int wait, int baud, int mode, float voltage) | ||
// Routine for resetting RL78 and initializing it in programming mode | ||
{ | ||
unsigned char r; | ||
//(mode = desired communication mode from terminal input - 1) | ||
|
||
// Determine UART mode from mode argument | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Indentation (just the one line) |
||
if (MODE_UART_1 == (mode & MODE_UART)) | ||
{ | ||
r = SET_MODE_1WIRE_UART; | ||
communication_mode = 1; | ||
} | ||
|
||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Remove blank line. |
||
else | ||
{ | ||
r = SET_MODE_2WIRE_UART; | ||
communication_mode = 2; | ||
} | ||
if (4 <= verbose_level) | ||
{ | ||
if (mode == 4) // Special case for mode 5 | ||
{ | ||
communication_mode = 5; | ||
printf("Using communication mode 5 (HW RESET with CTS reading RESET)\n"); | ||
} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Don't change |
||
else | ||
{ | ||
printf("Using communication mode %u%s\n", | ||
(mode & (MODE_UART | MODE_RESET)) + 1, | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
(mode & MODE_INVERT_RESET) ? " with RESET inversion" : ""); | ||
} | ||
} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is why the behavior changes when you change your verbosity level. Or rather, you shouldn't be setting |
||
rl78_set_reset(fd, mode, 0); /* RESET -> 0 */ | ||
serial_set_txd(fd, 0); /* TOOL0 -> 0 */ | ||
if (wait) | ||
// Begin reset procedure | ||
if (mode == 4) // sequencing for mode 5 | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
(ngl, I don't understand putting the constant before the == thing. But maintaining code style is more important than using MY code style.) |
||
{ | ||
printf("Turn MCU's power on and press any key..."); | ||
wait_kbhit(); | ||
printf("\n"); | ||
//printf("Turn MCU's power on with RESET low. Press any key to continue...\n"); | ||
//wait_kbhit(); | ||
serial_set_txd(fd, 0); | ||
printf("Press and hold RESET.\n"); | ||
int reset = serial_get_cts(fd); | ||
if (reset == 1) | ||
{ | ||
while (1) // while CTS/RESET is high, wait | ||
{ | ||
reset = serial_get_cts(fd); | ||
if (reset == 0) | ||
{ | ||
printf("Got reset press. Hang on...\n"); | ||
usleep(100000); | ||
printf("Let go of RESET.\n"); | ||
break; | ||
} | ||
} | ||
} | ||
|
||
while (1) // while CTS/RESET is low, wait | ||
{ | ||
reset = serial_get_cts(fd); | ||
if (reset == 1) | ||
{ | ||
printf("Got reset release. Attempting to set communication mode...\n"); | ||
break; | ||
} | ||
} | ||
Comment on lines
+91
to
+115
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is overly complex to read. Also, lets allow for inverted reset here. Add:
Test my Replace the first block with just:
Then move the Replace the second block with:
Then move the The usleep(1000) just keeps it from completely locking up a CPU while waiting. |
||
// Reset is now high | ||
serial_flush(fd); | ||
usleep(3000); | ||
serial_set_txd(fd,1); // TOOL0 -> 1 | ||
usleep(1000); | ||
serial_flush(fd); | ||
|
||
} | ||
else if ((mode == 0) | (mode == 1) | (mode == 2)) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Actually, this is just |
||
{ // sequencing for mode 1,2,3,4 | ||
rl78_set_reset(fd, mode, 0); /* RESET -> 0 */ | ||
serial_set_txd(fd, 0); /* TOOL0 -> 0 */ | ||
if (wait) | ||
{ | ||
printf("Turn MCU's power on and press any key..."); | ||
wait_kbhit(); | ||
printf("\n"); | ||
} | ||
serial_flush(fd); | ||
usleep(1000); | ||
rl78_set_reset(fd, mode, 1); /* RESET -> 1 */ | ||
usleep(3000); | ||
serial_set_txd(fd, 1); /* TOOL0 -> 1 */ | ||
usleep(1000); | ||
serial_flush(fd); | ||
} | ||
serial_flush(fd); | ||
usleep(1000); | ||
rl78_set_reset(fd, mode, 1); /* RESET -> 1 */ | ||
usleep(3000); | ||
serial_set_txd(fd, 1); /* TOOL0 -> 1 */ | ||
usleep(1000); | ||
serial_flush(fd); | ||
if (3 <= verbose_level) | ||
{ | ||
printf("Send 1-byte data for setting mode\n"); | ||
} | ||
serial_write(fd, &r, 1); | ||
if (1 == communication_mode) | ||
if ((1 == communication_mode) | (5 == communication_mode)) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Read: Undo this change. Only test for |
||
{ | ||
serial_read(fd, &r, 1); | ||
} | ||
|
@@ -91,11 +156,12 @@ int rl78_reset_init(port_handle_t fd, int wait, int baud, int mode, float voltag | |
|
||
int rl78_reset(port_handle_t fd, int mode) | ||
{ | ||
serial_set_txd(fd, 1); /* TOOL0 -> 1 */ | ||
rl78_set_reset(fd, mode, 0); /* RESET -> 0 */ | ||
usleep(10000); | ||
rl78_set_reset(fd, mode, 1); /* RESET -> 1 */ | ||
serial_set_txd(fd, 1); /* TOOL0 -> 1 */ | ||
rl78_set_reset(fd, mode, 0); /* RESET -> 0 */ | ||
usleep(10000); | ||
rl78_set_reset(fd, mode, 1); /* RESET -> 1 */ | ||
return 0; | ||
Comment on lines
154
to
160
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Too much indentation. Fix this. |
||
|
||
} | ||
|
||
static | ||
|
@@ -131,7 +197,7 @@ int rl78_send_cmd(port_handle_t fd, int cmd, const void *data, int len) | |
buf[len + 4] = ETX; | ||
int ret = serial_write(fd, buf, sizeof buf); | ||
// Read back echo | ||
if (1 == communication_mode) | ||
if ((1 == communication_mode) | (5 == communication_mode)) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Same as above. Only test for |
||
{ | ||
serial_read(fd, buf, sizeof buf); | ||
} | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -63,19 +63,23 @@ | |
#define RESPONSE_FORMAT_ERROR (-2) | ||
#define RESPONSE_EXPECTED_LENGTH_ERROR (-3) | ||
|
||
// serial command data to tell RL78 which serial mode to use for programming | ||
#define SET_MODE_1WIRE_UART 0x3A | ||
#define SET_MODE_2WIRE_UART 0x00 | ||
|
||
#define RL78_MIN_VOLTAGE 1.8f | ||
#define RL78_MAX_VOLTAGE 5.5f | ||
|
||
// Communication modes passed to RL78 funcs | ||
// Mode 1: MODE | ||
#define MODE_UART 1 | ||
#define MODE_UART_1 0 | ||
#define MODE_UART_2 MODE_UART | ||
#define MODE_RESET 2 | ||
#define MODE_RESET_DTR 0 | ||
#define MODE_RESET_RTS MODE_RESET | ||
#define MODE_MAX_VALUE (MODE_UART | MODE_RESET) | ||
#define MODE_MAX_VALUE 4 | ||
//#define MODE_MAX_VALUE (MODE_UART | MODE_RESET) | ||
#define MODE_MIN_VALUE 0 | ||
#define MODE_INVERT_RESET 0x80 | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Ok this is the big " Bit 1 of mode is whether it's a 1-wire or 2-wire serial protocol. We should make Bit 4 of mode be whether RESET is an INPUT or not. All my comments above are to change the code for this. Here, we need these
|
||
|
||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's all "hardware reset." I'd say "Manual reset button" instead.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Will probably want to update this after seeing below about
mode
being a bitmap.n=5
is as you describe, butn=6
will beTwo-wire UART, Manual Reset
. (You get it for free whenmode
is a bitmap.)