389ab3fff5e0ecae0ec433d1e9a03447ce4ad6b3
[openocd.git] / src / jtag / stlink / stlink_interface.c
1 /***************************************************************************
2 * Copyright (C) 2011 by Mathias Kuester *
3 * Mathias Kuester <kesmtp@freenet.de> *
4 * *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
9 * *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
14 * *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
20
21 #ifdef HAVE_CONFIG_H
22 #include "config.h"
23 #endif
24
25 /* project specific includes */
26 #include <jtag/interface.h>
27 #include <transport/transport.h>
28 #include <helper/time_support.h>
29
30 #include <jtag/stlink/stlink_tcl.h>
31 #include <jtag/stlink/stlink_layout.h>
32 #include <jtag/stlink/stlink_transport.h>
33 #include <jtag/stlink/stlink_interface.h>
34
35 #include <target/target.h>
36
37 static struct stlink_interface_s stlink_if = { {0, 0, 0, 0, 0}, 0, 0 };
38
39 int stlink_interface_open(enum stlink_transports tr)
40 {
41 LOG_DEBUG("stlink_interface_open");
42
43 /* set transport mode */
44 stlink_if.param.transport = tr;
45
46 return stlink_if.layout->open(&stlink_if);
47 }
48
49 int stlink_interface_init_target(struct target *t)
50 {
51 int res;
52
53 LOG_DEBUG("stlink_interface_init_target");
54
55 /* this is the interface for the current target and we
56 * can setup the private pointer in the tap structure
57 * if the interface match the tap idcode
58 */
59 res = stlink_if.layout->api->idcode(stlink_if.fd, &t->tap->idcode);
60
61 if (res != ERROR_OK)
62 return res;
63
64 unsigned ii, limit = t->tap->expected_ids_cnt;
65 int found = 0;
66
67 for (ii = 0; ii < limit; ii++) {
68 uint32_t expected = t->tap->expected_ids[ii];
69
70 /* treat "-expected-id 0" as a "don't-warn" wildcard */
71 if (!expected || (t->tap->idcode == expected)) {
72 found = 1;
73 break;
74 }
75 }
76
77 if (found == 0) {
78 LOG_ERROR
79 ("stlink_interface_init_target: target not found: idcode: %x ",
80 t->tap->idcode);
81 return ERROR_FAIL;
82 }
83
84 t->tap->priv = &stlink_if;
85 t->tap->hasidcode = 1;
86
87 return ERROR_OK;
88 }
89
90 static int stlink_interface_init(void)
91 {
92 LOG_DEBUG("stlink_interface_init");
93
94 /* here we can initialize the layout */
95 return stlink_layout_init(&stlink_if);
96 }
97
98 static int stlink_interface_quit(void)
99 {
100 LOG_DEBUG("stlink_interface_quit");
101
102 return ERROR_OK;
103 }
104
105 static int stlink_interface_speed(int speed)
106 {
107 LOG_DEBUG("stlink_interface_speed: ignore speed %d", speed);
108
109 return ERROR_OK;
110 }
111
112 static int stlink_speed_div(int speed, int *khz)
113 {
114 *khz = speed;
115 return ERROR_OK;
116 }
117
118 static int stlink_khz(int khz, int *jtag_speed)
119 {
120 *jtag_speed = khz;
121 return ERROR_OK;
122 }
123
124 static int stlink_interface_execute_queue(void)
125 {
126 LOG_DEBUG("stlink_interface_execute_queue: ignored");
127
128 return ERROR_OK;
129 }
130
131 COMMAND_HANDLER(stlink_interface_handle_device_desc_command)
132 {
133 LOG_DEBUG("stlink_interface_handle_device_desc_command");
134
135 if (CMD_ARGC == 1) {
136 stlink_if.param.device_desc = strdup(CMD_ARGV[0]);
137 } else {
138 LOG_ERROR
139 ("expected exactly one argument to stlink_device_desc <description>");
140 }
141
142 return ERROR_OK;
143 }
144
145 COMMAND_HANDLER(stlink_interface_handle_serial_command)
146 {
147 LOG_DEBUG("stlink_interface_handle_serial_command");
148
149 if (CMD_ARGC == 1) {
150 stlink_if.param.serial = strdup(CMD_ARGV[0]);
151 } else {
152 LOG_ERROR
153 ("expected exactly one argument to stlink_serial <serial-number>");
154 }
155
156 return ERROR_OK;
157 }
158
159 COMMAND_HANDLER(stlink_interface_handle_layout_command)
160 {
161 LOG_DEBUG("stlink_interface_handle_layout_command");
162
163 if (CMD_ARGC != 1) {
164 LOG_ERROR("Need exactly one argument to stlink_layout");
165 return ERROR_COMMAND_SYNTAX_ERROR;
166 }
167
168 if (stlink_if.layout) {
169 LOG_ERROR("already specified stlink_layout %s",
170 stlink_if.layout->name);
171 return (strcmp(stlink_if.layout->name, CMD_ARGV[0]) != 0)
172 ? ERROR_FAIL : ERROR_OK;
173 }
174
175 for (const struct stlink_layout *l = stlink_layout_get_list(); l->name;
176 l++) {
177 if (strcmp(l->name, CMD_ARGV[0]) == 0) {
178 stlink_if.layout = l;
179 return ERROR_OK;
180 }
181 }
182
183 LOG_ERROR("No STLINK layout '%s' found", CMD_ARGV[0]);
184 return ERROR_FAIL;
185 }
186
187 COMMAND_HANDLER(stlink_interface_handle_vid_pid_command)
188 {
189 LOG_DEBUG("stlink_interface_handle_vid_pid_command");
190
191 if (CMD_ARGC != 2) {
192 LOG_WARNING
193 ("ignoring extra IDs in stlink_vid_pid (maximum is 1 pair)");
194 return ERROR_COMMAND_SYNTAX_ERROR;
195 }
196
197 COMMAND_PARSE_NUMBER(u16, CMD_ARGV[0], stlink_if.param.vid);
198 COMMAND_PARSE_NUMBER(u16, CMD_ARGV[1], stlink_if.param.pid);
199
200 return ERROR_OK;
201 }
202
203 static const struct command_registration stlink_interface_command_handlers[] = {
204 {
205 .name = "stlink_device_desc",
206 .handler = &stlink_interface_handle_device_desc_command,
207 .mode = COMMAND_CONFIG,
208 .help = "set the stlink device description of the STLINK device",
209 .usage = "description_string",
210 },
211 {
212 .name = "stlink_serial",
213 .handler = &stlink_interface_handle_serial_command,
214 .mode = COMMAND_CONFIG,
215 .help = "set the serial number of the STLINK device",
216 .usage = "serial_string",
217 },
218 {
219 .name = "stlink_layout",
220 .handler = &stlink_interface_handle_layout_command,
221 .mode = COMMAND_CONFIG,
222 .help = "set the layout of the STLINK to usb or sg",
223 .usage = "layout_name",
224 },
225 {
226 .name = "stlink_vid_pid",
227 .handler = &stlink_interface_handle_vid_pid_command,
228 .mode = COMMAND_CONFIG,
229 .help = "the vendor and product ID of the STLINK device",
230 .usage = "(vid pid)* ",
231 },
232 COMMAND_REGISTRATION_DONE
233 };
234
235 struct jtag_interface stlink_interface = {
236 .name = "stlink",
237 .supported = 0,
238 .commands = stlink_interface_command_handlers,
239 .transports = stlink_transports,
240 .init = stlink_interface_init,
241 .quit = stlink_interface_quit,
242 .speed = stlink_interface_speed,
243 .speed_div = stlink_speed_div,
244 .khz = stlink_khz,
245 .execute_queue = stlink_interface_execute_queue,
246 };

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)