driver/linuxgpiod: add support for opendrain srst 59/6559/2
authorAlex Crawford <openocd@code.acrawford.com>
Thu, 16 Sep 2021 17:00:25 +0000 (10:00 -0700)
committerAntonio Borneo <borneo.antonio@gmail.com>
Sat, 25 Sep 2021 13:15:05 +0000 (13:15 +0000)
Some MCUs (e.g. the STM32F3) directly expose the internal reset line to
an external pin. When this signal is driven by a push/pull line, it can
actually be inhibited by the external driver. This results in a setup
where the MCU cannot reset itself, for example, by a watchdog timeout or
a sysreset request. To fix this condition, support for open drain output
on the SRST line is required.

Note that because `reset_config srst_open_drain` is the default, all
users of this adapter will switch over to an open drain output unless
explicitly configured otherwise.

Signed-off-by: Alex Crawford <openocd@code.acrawford.com>
Change-Id: I89b39b03aa03f826ed3c45793412780448940bcc
Reviewed-on: https://review.openocd.org/c/openocd/+/6559
Tested-by: jenkins
Reviewed-by: Antonio Borneo <borneo.antonio@gmail.com>
src/jtag/drivers/linuxgpiod.c

index 42c8a31408d6c9af1b55c3b8407ee580cc314e2c..dd50b44066616b207c745cdc1c43d743cd20e1d1 100644 (file)
@@ -278,7 +278,7 @@ static int linuxgpiod_quit(void)
        return ERROR_OK;
 }
 
-static struct gpiod_line *helper_get_input_line(const char *label, unsigned int offset)
+static struct gpiod_line *helper_get_line(const char *label, unsigned int offset, int val, int dir, int flags)
 {
        struct gpiod_line *line;
        int retval;
@@ -289,33 +289,34 @@ static struct gpiod_line *helper_get_input_line(const char *label, unsigned int
                return NULL;
        }
 
-       retval = gpiod_line_request_input(line, "OpenOCD");
+       struct gpiod_line_request_config config = {
+               .consumer = "OpenOCD",
+               .request_type = dir,
+               .flags = flags,
+       };
+
+       retval = gpiod_line_request(line, &config, val);
        if (retval < 0) {
-               LOG_ERROR("Error request_input line %s", label);
+               LOG_ERROR("Error requesting gpio line %s", label);
                return NULL;
        }
 
        return line;
 }
 
-static struct gpiod_line *helper_get_output_line(const char *label, unsigned int offset, int val)
+static struct gpiod_line *helper_get_input_line(const char *label, unsigned int offset)
 {
-       struct gpiod_line *line;
-       int retval;
-
-       line = gpiod_chip_get_line(gpiod_chip, offset);
-       if (!line) {
-               LOG_ERROR("Error get line %s", label);
-               return NULL;
-       }
+       return helper_get_line(label, offset, 0, GPIOD_LINE_REQUEST_DIRECTION_INPUT, 0);
+}
 
-       retval = gpiod_line_request_output(line, "OpenOCD", val);
-       if (retval < 0) {
-               LOG_ERROR("Error request_output line %s", label);
-               return NULL;
-       }
+static struct gpiod_line *helper_get_output_line(const char *label, unsigned int offset, int val)
+{
+       return helper_get_line(label, offset, val, GPIOD_LINE_REQUEST_DIRECTION_OUTPUT, 0);
+}
 
-       return line;
+static struct gpiod_line *helper_get_open_drain_output_line(const char *label, unsigned int offset, int val)
+{
+       return helper_get_line(label, offset, val, GPIOD_LINE_REQUEST_DIRECTION_OUTPUT, GPIOD_LINE_REQUEST_FLAG_OPEN_DRAIN);
 }
 
 static int linuxgpiod_init(void)
@@ -381,7 +382,11 @@ static int linuxgpiod_init(void)
        }
 
        if (is_gpio_valid(srst_gpio)) {
-               gpiod_srst = helper_get_output_line("srst", srst_gpio, 1);
+               if (jtag_get_reset_config() & RESET_SRST_PUSH_PULL)
+                       gpiod_srst = helper_get_output_line("srst", srst_gpio, 1);
+               else
+                       gpiod_srst = helper_get_open_drain_output_line("srst", srst_gpio, 1);
+
                if (!gpiod_srst)
                        goto out_error;
        }

Linking to existing account procedure

If you already have an account and want to add another login method you MUST first sign in with your existing account and then change URL to read https://review.openocd.org/login/?link to get to this page again but this time it'll work for linking. Thank you.

SSH host keys fingerprints

1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=..              |
|+o..   .         |
|*.o   . .        |
|+B . . .         |
|Bo. = o S        |
|Oo.+ + =         |
|oB=.* = . o      |
| =+=.+   + E     |
|. .=o   . o      |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)