Skip to content

Commit 01039bc

Browse files
committed
libgpiodJtagBitbang: simplify code when libgpiodv2 is used
1 parent 65a7e60 commit 01039bc

2 files changed

Lines changed: 111 additions & 123 deletions

File tree

src/libgpiodJtagBitbang.cpp

Lines changed: 92 additions & 101 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,10 @@ LibgpiodJtagBitbang::LibgpiodJtagBitbang(
5757
/* Validate pins */
5858
#ifdef GPIOD_APIV2
5959
const unsigned int pins[] = {_tck_pin, _tms_pin, _tdi_pin, _tdo_pin};
60+
_out_pins[0] = _tdi_group[0] = _tms_group[0] = _tck_pin;
61+
_out_pins[1] = _tdi_group[1] = _tdi_pin;
62+
_out_pins[2] = _tms_group[1] = _tms_pin;
63+
_out_pins[3] = _tdo_pin;
6064
#else
6165
const int pins[] = {_tck_pin, _tms_pin, _tdi_pin, _tdo_pin};
6266
#endif
@@ -81,72 +85,49 @@ LibgpiodJtagBitbang::LibgpiodJtagBitbang(
8185
}
8286

8387
#ifdef GPIOD_APIV2
84-
_tdo_req_cfg = gpiod_request_config_new();
85-
_tdi_req_cfg = gpiod_request_config_new();
86-
_tck_req_cfg = gpiod_request_config_new();
87-
_tms_req_cfg = gpiod_request_config_new();
88+
_curr_tms = GPIOD_LINE_VALUE_ACTIVE;
89+
_curr_tdi = GPIOD_LINE_VALUE_INACTIVE;
8890

89-
gpiod_request_config_set_consumer(_tdo_req_cfg, "_tdo");
90-
gpiod_request_config_set_consumer(_tdi_req_cfg, "_tdi");
91-
gpiod_request_config_set_consumer(_tck_req_cfg, "_tck");
92-
gpiod_request_config_set_consumer(_tms_req_cfg, "_tms");
91+
_out_req_cfg = gpiod_request_config_new();
9392

94-
_tdo_settings = gpiod_line_settings_new();
95-
_tdi_settings = gpiod_line_settings_new();
96-
_tck_settings = gpiod_line_settings_new();
97-
_tms_settings = gpiod_line_settings_new();
93+
gpiod_request_config_set_consumer(_out_req_cfg, "openFPGALoader_out");
94+
95+
_out_settings = gpiod_line_settings_new();
96+
_in_settings = gpiod_line_settings_new();
9897

9998
gpiod_line_settings_set_direction(
100-
_tdo_settings, GPIOD_LINE_DIRECTION_INPUT);
101-
gpiod_line_settings_set_direction(
102-
_tdi_settings, GPIOD_LINE_DIRECTION_OUTPUT);
103-
gpiod_line_settings_set_direction(
104-
_tck_settings, GPIOD_LINE_DIRECTION_OUTPUT);
99+
_in_settings, GPIOD_LINE_DIRECTION_INPUT);
105100
gpiod_line_settings_set_direction(
106-
_tms_settings, GPIOD_LINE_DIRECTION_OUTPUT);
101+
_out_settings, GPIOD_LINE_DIRECTION_OUTPUT);
107102

108103
gpiod_line_settings_set_bias(
109-
_tdo_settings, GPIOD_LINE_BIAS_DISABLED);
110-
gpiod_line_settings_set_bias(
111-
_tdi_settings, GPIOD_LINE_BIAS_DISABLED);
104+
_in_settings, GPIOD_LINE_BIAS_DISABLED);
112105
gpiod_line_settings_set_bias(
113-
_tck_settings, GPIOD_LINE_BIAS_DISABLED);
114-
gpiod_line_settings_set_bias(
115-
_tms_settings, GPIOD_LINE_BIAS_DISABLED);
106+
_out_settings, GPIOD_LINE_BIAS_DISABLED);
116107

117-
_tdo_line_cfg = gpiod_line_config_new();
118-
_tdi_line_cfg = gpiod_line_config_new();
119-
_tck_line_cfg = gpiod_line_config_new();
120-
_tms_line_cfg = gpiod_line_config_new();
108+
_out_line_cfg = gpiod_line_config_new();
121109

122110
gpiod_line_config_add_line_settings(
123-
_tdo_line_cfg, &_tdo_pin, 1, _tdo_settings);
124-
gpiod_line_config_add_line_settings(
125-
_tdi_line_cfg, &_tdi_pin, 1, _tdi_settings);
126-
gpiod_line_config_add_line_settings(
127-
_tck_line_cfg, &_tck_pin, 1, _tck_settings);
111+
_out_line_cfg, _out_pins, 3, _out_settings);
128112
gpiod_line_config_add_line_settings(
129-
_tms_line_cfg, &_tms_pin, 1, _tms_settings);
130-
131-
_tdo_request = gpiod_chip_request_lines(
132-
_chip, _tdo_req_cfg, _tdo_line_cfg);
133-
_tdi_request = gpiod_chip_request_lines(
134-
_chip, _tdi_req_cfg, _tdi_line_cfg);
135-
_tck_request = gpiod_chip_request_lines(
136-
_chip, _tck_req_cfg, _tck_line_cfg);
137-
_tms_request = gpiod_chip_request_lines(
138-
_chip, _tms_req_cfg, _tms_line_cfg);
113+
_out_line_cfg, &_out_pins[3], 1, _in_settings);
114+
115+
_out_request = gpiod_chip_request_lines(
116+
_chip, _out_req_cfg, _out_line_cfg);
117+
118+
/* set default values for all GPIOs */
119+
enum gpiod_line_value val[3] = {GPIOD_LINE_VALUE_INACTIVE, _curr_tdi, _curr_tms};
120+
gpiod_line_request_set_values_subset(_out_request, 3, _out_pins, val);
139121
#else
122+
_curr_tdi = 0;
123+
_curr_tms = 1;
140124
_tdo_line = get_line(_tdo_pin, 0, GPIOD_LINE_REQUEST_DIRECTION_INPUT);
141125
_tdi_line = get_line(_tdi_pin, 0, GPIOD_LINE_REQUEST_DIRECTION_OUTPUT);
142126
_tck_line = get_line(_tck_pin, 0, GPIOD_LINE_REQUEST_DIRECTION_OUTPUT);
143127
_tms_line = get_line(_tms_pin, 1, GPIOD_LINE_REQUEST_DIRECTION_OUTPUT);
144128
#endif
145129

146-
_curr_tdi = 0;
147130
_curr_tck = 0;
148-
_curr_tms = 1;
149-
150131
// FIXME: I'm unsure how this value should be set.
151132
// Maybe experiment, or think through what it should be.
152133
_clkHZ = 5000000;
@@ -155,33 +136,16 @@ LibgpiodJtagBitbang::LibgpiodJtagBitbang(
155136
LibgpiodJtagBitbang::~LibgpiodJtagBitbang()
156137
{
157138
#ifdef GPIOD_APIV2
158-
if (_tms_request)
159-
gpiod_line_request_release(_tms_request);
160-
if (_tms_line_cfg)
161-
gpiod_line_config_free(_tms_line_cfg);
162-
if (_tms_settings)
163-
gpiod_line_settings_free(_tms_settings);
164-
165-
if (_tck_request)
166-
gpiod_line_request_release(_tck_request);
167-
if (_tck_line_cfg)
168-
gpiod_line_config_free(_tck_line_cfg);
169-
if (_tck_settings)
170-
gpiod_line_settings_free(_tck_settings);
171-
172-
if (_tdi_request)
173-
gpiod_line_request_release(_tdi_request);
174-
if (_tdi_line_cfg)
175-
gpiod_line_config_free(_tdi_line_cfg);
176-
if (_tdi_settings)
177-
gpiod_line_settings_free(_tdi_settings);
178-
179-
if (_tdo_request)
180-
gpiod_line_request_release(_tdo_request);
181-
if (_tdo_line_cfg)
182-
gpiod_line_config_free(_tdo_line_cfg);
183-
if (_tdo_settings)
184-
gpiod_line_settings_free(_tdo_settings);
139+
if (_out_request)
140+
gpiod_line_request_release(_out_request);
141+
142+
if (_out_line_cfg)
143+
gpiod_line_config_free(_out_line_cfg);
144+
145+
if (_out_settings)
146+
gpiod_line_settings_free(_out_settings);
147+
if (_in_settings)
148+
gpiod_line_settings_free(_in_settings);
185149
#else
186150
if (_tms_line)
187151
gpiod_line_release(_tms_line);
@@ -225,44 +189,50 @@ gpiod_line *LibgpiodJtagBitbang::get_line(unsigned int offset, int val, int dir)
225189
}
226190
#endif
227191

192+
#ifdef GPIOD_APIV2
193+
int LibgpiodJtagBitbang::update_pins(gpiod_line_value tms, gpiod_line_value tdi)
194+
#else
228195
int LibgpiodJtagBitbang::update_pins(int tck, int tms, int tdi)
196+
#endif
229197
{
230-
if (tdi != _curr_tdi) {
231198
#ifdef GPIOD_APIV2
232-
if (gpiod_line_request_set_value(_tdi_request, _tdi_pin,
233-
(tdi == 0) ? GPIOD_LINE_VALUE_INACTIVE :
234-
GPIOD_LINE_VALUE_ACTIVE) < 0)
199+
enum gpiod_line_value val[3] = {GPIOD_LINE_VALUE_INACTIVE, tdi, tms};
200+
bool tdi_wr = tdi != _curr_tdi;
201+
bool tms_wr = tms != _curr_tms;
202+
203+
if (tdi_wr & tms_wr) {
204+
gpiod_line_request_set_values_subset(_out_request, 3, _out_pins, val);
205+
} else if (tdi_wr) {
206+
gpiod_line_request_set_values_subset(_out_request, 2, _tdi_group, val);
207+
} else if (tms_wr) {
208+
val[1] = tms;
209+
gpiod_line_request_set_values_subset(_out_request, 2, _tms_group, val);
210+
} else {
211+
gpiod_line_request_set_value(_out_request, _tck_pin,
212+
GPIOD_LINE_VALUE_INACTIVE);
213+
}
214+
gpiod_line_request_set_value(_out_request, _tck_pin,
215+
GPIOD_LINE_VALUE_ACTIVE);
235216
#else
217+
if (tdi != _curr_tdi) {
236218
if (gpiod_line_set_value(_tdi_line, tdi) < 0)
237-
#endif
238219
display("Unable to set gpio pin tdi\n");
239220
}
240221

241222
if (tms != _curr_tms) {
242-
#ifdef GPIOD_APIV2
243-
if (gpiod_line_request_set_value(_tms_request, _tms_pin,
244-
(tms == 0) ? GPIOD_LINE_VALUE_INACTIVE :
245-
GPIOD_LINE_VALUE_ACTIVE) < 0)
246-
#else
247223
if (gpiod_line_set_value(_tms_line, tms) < 0)
248-
#endif
249224
display("Unable to set gpio pin tms\n");
250225
}
251226

252227
if (tck != _curr_tck) {
253-
#ifdef GPIOD_APIV2
254-
if (gpiod_line_request_set_value(_tck_request, _tck_pin,
255-
(tck == 0) ? GPIOD_LINE_VALUE_INACTIVE :
256-
GPIOD_LINE_VALUE_ACTIVE) < 0)
257-
#else
258228
if (gpiod_line_set_value(_tck_line, tck) < 0)
259-
#endif
260229
display("Unable to set gpio pin tck\n");
261230
}
262231

232+
_curr_tck = tck;
233+
#endif
263234
_curr_tdi = tdi;
264235
_curr_tms = tms;
265-
_curr_tck = tck;
266236

267237
return 0;
268238
}
@@ -271,7 +241,7 @@ int LibgpiodJtagBitbang::read_tdo()
271241
{
272242
#ifdef GPIOD_APIV2
273243
gpiod_line_value req = gpiod_line_request_get_value(
274-
_tdo_request, _tdo_pin);
244+
_out_request, _tdo_pin);
275245
if (req == GPIOD_LINE_VALUE_ERROR)
276246
{
277247
display("Error reading TDO line\n");
@@ -295,32 +265,51 @@ int LibgpiodJtagBitbang::writeTMS(const uint8_t *tms_buf, uint32_t len,
295265
__attribute__((unused)) bool flush_buffer,
296266
__attribute__((unused)) uint8_t tdi)
297267
{
298-
int tms;
299-
300268
if (len == 0) // nothing -> stop
301269
return len;
302270

303271
for (uint32_t i = 0; i < len; i++) {
304-
tms = ((tms_buf[i >> 3] & (1 << (i & 7))) ? 1 : 0);
272+
#ifdef GPIOD_APIV2
273+
gpiod_line_value tms = ((tms_buf[i >> 3] & (1 << (i & 7))) ?
274+
GPIOD_LINE_VALUE_ACTIVE : GPIOD_LINE_VALUE_INACTIVE);
275+
update_pins(tms, _curr_tdi);
276+
#else
277+
int tms = ((tms_buf[i >> 3] & (1 << (i & 7))) ? 1 : 0);
305278

306279
update_pins(0, tms, 0);
307280
update_pins(1, tms, 0);
281+
#endif
308282
}
309283

310-
update_pins(0, tms, 0);
311-
312284
return len;
313285
}
314286

315287
int LibgpiodJtagBitbang::writeTDI(const uint8_t *tx, uint8_t *rx, uint32_t len, bool end)
316288
{
289+
#ifdef GPIOD_APIV2
290+
gpiod_line_value tdi = GPIOD_LINE_VALUE_INACTIVE;
291+
#else
317292
int tms = _curr_tms;
318293
int tdi = _curr_tdi;
294+
#endif
319295

320296
if (rx)
321297
memset(rx, 0, len / 8);
322298

323299
for (uint32_t i = 0; i < len; i++) {
300+
#ifdef GPIOD_APIV2
301+
if (tx) {
302+
tdi = (tx[i >> 3] & (1 << (i & 7))) ?
303+
GPIOD_LINE_VALUE_ACTIVE : GPIOD_LINE_VALUE_INACTIVE;
304+
}
305+
306+
/* When TMS needs to be also updated (because of end) */
307+
if (end && (i == len - 1)) {
308+
update_pins(GPIOD_LINE_VALUE_ACTIVE, tdi);
309+
} else {
310+
update_pins(GPIOD_LINE_VALUE_INACTIVE, tdi);
311+
}
312+
#else
324313
if (end && (i == len - 1))
325314
tms = 1;
326315

@@ -329,26 +318,28 @@ int LibgpiodJtagBitbang::writeTDI(const uint8_t *tx, uint8_t *rx, uint32_t len,
329318

330319
update_pins(0, tms, tdi);
331320
update_pins(1, tms, tdi);
321+
#endif
332322

333323
if (rx) {
334324
if (read_tdo() > 0)
335325
rx[i >> 3] |= 1 << (i & 7);
336326
}
337327
}
338328

339-
update_pins(0, tms, tdi);
340-
341329
return len;
342330
}
343331

344332
int LibgpiodJtagBitbang::toggleClk(uint8_t tms, uint8_t tdi, uint32_t clk_len)
345333
{
346334
for (uint32_t i = 0; i < clk_len; i++) {
335+
#ifdef GPIOD_APIV2
336+
gpiod_line_request_set_value(_out_request, _tck_pin, GPIOD_LINE_VALUE_INACTIVE);
337+
gpiod_line_request_set_value(_out_request, _tck_pin, GPIOD_LINE_VALUE_ACTIVE);
338+
#else
347339
update_pins(0, tms, tdi);
348340
update_pins(1, tms, tdi);
341+
#endif
349342
}
350343

351-
update_pins(0, tms, tdi);
352-
353344
return clk_len;
354345
}

src/libgpiodJtagBitbang.hpp

Lines changed: 19 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -44,8 +44,10 @@ class LibgpiodJtagBitbang : public JtagInterface {
4444
private:
4545
#ifndef GPIOD_APIV2
4646
gpiod_line *get_line(unsigned int offset, int val, int dir);
47-
#endif
4847
int update_pins(int tck, int tms, int tdi);
48+
#else
49+
int update_pins(gpiod_line_value tms, gpiod_line_value tdi);
50+
#endif
4951
int read_tdo();
5052

5153
bool _verbose;
@@ -55,6 +57,9 @@ class LibgpiodJtagBitbang : public JtagInterface {
5557
unsigned int _tms_pin;
5658
unsigned int _tdo_pin;
5759
unsigned int _tdi_pin;
60+
unsigned int _out_pins[4];
61+
unsigned int _tms_group[2];
62+
unsigned int _tdi_group[2];
5863
#else
5964
int _tck_pin;
6065
int _tms_pin;
@@ -65,34 +70,26 @@ class LibgpiodJtagBitbang : public JtagInterface {
6570
gpiod_chip *_chip;
6671

6772
#ifdef GPIOD_APIV2
68-
gpiod_request_config *_tck_req_cfg;
69-
gpiod_request_config *_tms_req_cfg;
70-
gpiod_request_config *_tdo_req_cfg;
71-
gpiod_request_config *_tdi_req_cfg;
72-
73-
gpiod_line_config *_tck_line_cfg;
74-
gpiod_line_config *_tms_line_cfg;
75-
gpiod_line_config *_tdo_line_cfg;
76-
gpiod_line_config *_tdi_line_cfg;
77-
78-
gpiod_line_settings *_tck_settings;
79-
gpiod_line_settings *_tms_settings;
80-
gpiod_line_settings *_tdo_settings;
81-
gpiod_line_settings *_tdi_settings;
82-
83-
gpiod_line_request *_tdo_request;
84-
gpiod_line_request *_tdi_request;
85-
gpiod_line_request *_tck_request;
86-
gpiod_line_request *_tms_request;
73+
gpiod_request_config *_out_req_cfg;
74+
75+
gpiod_line_config *_out_line_cfg;
76+
77+
gpiod_line_settings *_in_settings;
78+
gpiod_line_settings *_out_settings;
79+
80+
gpiod_line_request *_out_request;
81+
82+
gpiod_line_value _curr_tms;
83+
gpiod_line_value _curr_tdi;
8784
#else
8885
gpiod_line *_tck_line;
8986
gpiod_line *_tms_line;
9087
gpiod_line *_tdo_line;
9188
gpiod_line *_tdi_line;
92-
#endif
93-
9489
int _curr_tms;
9590
int _curr_tdi;
91+
#endif
92+
9693
int _curr_tck;
9794
};
9895
#endif

0 commit comments

Comments
 (0)