]> sigrok.org Git - libsigrok.git/blame - hardware/zeroplus-logic-cube/zeroplus.c
sr: new API call sr_dev_config_set()
[libsigrok.git] / hardware / zeroplus-logic-cube / zeroplus.c
CommitLineData
a1bb33af
UH
1/*
2 * This file is part of the sigrok project.
3 *
c73d2ea4 4 * Copyright (C) 2010-2012 Bert Vermeulen <bert@biot.com>
a1bb33af
UH
5 *
6 * This program is free software: you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation, either version 3 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <http://www.gnu.org/licenses/>.
18 */
19
20#include <stdio.h>
21#include <stdlib.h>
c31e9ef4 22#include <string.h>
a1bb33af
UH
23#include <sys/time.h>
24#include <inttypes.h>
25#include <glib.h>
26#include <libusb.h>
c31e9ef4 27#include "config.h"
45c59c8b
BV
28#include "libsigrok.h"
29#include "libsigrok-internal.h"
a1bb33af
UH
30#include "analyzer.h"
31
fed16f06 32#define USB_VENDOR 0x0c12
8fdecced
UH
33
34#define VENDOR_NAME "ZEROPLUS"
35#define MODEL_NAME "Logic Cube LAP-C"
36#define MODEL_VERSION NULL
a1bb33af 37
6752905e 38#define NUM_PROBES 16
a1bb33af
UH
39#define USB_INTERFACE 0
40#define USB_CONFIGURATION 1
41#define NUM_TRIGGER_STAGES 4
42#define TRIGGER_TYPES "01"
43
fed16f06 44#define PACKET_SIZE 2048 /* ?? */
a1bb33af
UH
45
46typedef struct {
428edbe1 47 unsigned short vid;
a1bb33af 48 unsigned short pid;
428edbe1 49 char *model_name;
a1bb33af 50 unsigned int channels;
fed16f06 51 unsigned int sample_depth; /* In Ksamples/channel */
a1bb33af
UH
52 unsigned int max_sampling_freq;
53} model_t;
54
fed16f06
UH
55/*
56 * Note -- 16032, 16064 and 16128 *usually* -- but not always -- have the
57 * same 128K sample depth.
58 */
29cbfeaf 59static model_t zeroplus_models[] = {
428edbe1
BV
60 {0x0c12, 0x7009, "LAP-C(16064)", 16, 64, 100},
61 {0x0c12, 0x700A, "LAP-C(16128)", 16, 128, 200},
3f848bb7 62 /* TODO: we don't know anything about these
428edbe1
BV
63 {0x0c12, 0x700B, "LAP-C(32128)", 32, 128, 200},
64 {0x0c12, 0x700C, "LAP-C(321000)", 32, 1024, 200},
65 {0x0c12, 0x700D, "LAP-C(322000)", 32, 2048, 200},
3f848bb7 66 */
428edbe1
BV
67 {0x0c12, 0x700E, "LAP-C(16032)", 16, 32, 100},
68 {0x0c12, 0x7016, "LAP-C(162000)", 16, 2048, 200},
69 { 0, 0, 0, 0, 0, 0 }
a1bb33af
UH
70};
71
915f7cc8 72static const int hwcaps[] = {
5a2326a7
UH
73 SR_HWCAP_LOGIC_ANALYZER,
74 SR_HWCAP_SAMPLERATE,
75 SR_HWCAP_PROBECONFIG,
76 SR_HWCAP_CAPTURE_RATIO,
a1bb33af 77
fed16f06 78 /* These are really implemented in the driver, not the hardware. */
5a2326a7 79 SR_HWCAP_LIMIT_SAMPLES,
fed16f06 80 0,
a1bb33af
UH
81};
82
d261dbbf
UH
83/*
84 * ZEROPLUS LAP-C (16032) numbers the 16 probes A0-A7 and B0-B7.
85 * We currently ignore other untested/unsupported devices here.
86 */
6752905e 87static const char *probe_names[NUM_PROBES + 1] = {
d261dbbf
UH
88 "A0",
89 "A1",
90 "A2",
91 "A3",
92 "A4",
93 "A5",
94 "A6",
95 "A7",
96 "B0",
97 "B1",
98 "B2",
99 "B3",
100 "B4",
101 "B5",
102 "B6",
103 "B7",
464d12c7
KS
104 NULL,
105};
106
e7eb703f 107/* List of struct sr_dev_inst, maintained by dev_open()/dev_close(). */
32756547
BV
108SR_PRIV struct sr_dev_driver zeroplus_logic_cube_driver_info;
109static struct sr_dev_driver *zdi = &zeroplus_logic_cube_driver_info;
a1bb33af
UH
110
111static libusb_context *usb_context = NULL;
112
fed16f06
UH
113/*
114 * The hardware supports more samplerates than these, but these are the
115 * options hardcoded into the vendor's Windows GUI.
116 */
a1bb33af 117
fed16f06
UH
118/*
119 * TODO: We shouldn't support 150MHz and 200MHz on devices that don't go up
120 * that high.
121 */
a533743d 122static const uint64_t supported_samplerates[] = {
c9140419
UH
123 SR_HZ(100),
124 SR_HZ(500),
59df0c77
UH
125 SR_KHZ(1),
126 SR_KHZ(5),
127 SR_KHZ(25),
128 SR_KHZ(50),
129 SR_KHZ(100),
130 SR_KHZ(200),
131 SR_KHZ(400),
132 SR_KHZ(800),
133 SR_MHZ(1),
134 SR_MHZ(10),
135 SR_MHZ(25),
136 SR_MHZ(50),
137 SR_MHZ(80),
138 SR_MHZ(100),
139 SR_MHZ(150),
140 SR_MHZ(200),
fed16f06 141 0,
a1bb33af
UH
142};
143
a533743d 144static const struct sr_samplerates samplerates = {
590b9f9a
UH
145 0,
146 0,
147 0,
fed16f06 148 supported_samplerates,
a1bb33af
UH
149};
150
310e9e9b
BV
151/* Private driver context. */
152struct drv_context {
153 GSList *instances;
154};
155
ea9cfed7 156/* Private, per-device-instance driver context. */
310e9e9b 157struct dev_context {
bf43ea23 158 uint64_t cur_samplerate;
bf43ea23
UH
159 uint64_t limit_samples;
160 int num_channels; /* TODO: This isn't initialized before it's needed :( */
161 uint64_t memory_size;
162 uint8_t probe_mask;
163 uint8_t trigger_mask[NUM_TRIGGER_STAGES];
164 uint8_t trigger_value[NUM_TRIGGER_STAGES];
165 // uint8_t trigger_buffer[NUM_TRIGGER_STAGES];
69890f73 166
7da6f9d5 167 /* TODO: this belongs in the device instance */
d68e2d1a 168 struct sr_usb_dev_inst *usb;
bf43ea23 169};
a1bb33af 170
6f4b1868
BV
171static int hw_dev_config_set(const struct sr_dev_inst *sdi, int hwcap,
172 const void *value);
25a0f108 173static int hw_dev_close(struct sr_dev_inst *sdi);
a1bb33af
UH
174
175static unsigned int get_memory_size(int type)
176{
fed16f06
UH
177 if (type == MEMORY_SIZE_8K)
178 return 8 * 1024;
179 else if (type == MEMORY_SIZE_64K)
180 return 64 * 1024;
181 else if (type == MEMORY_SIZE_128K)
182 return 128 * 1024;
183 else if (type == MEMORY_SIZE_512K)
184 return 512 * 1024;
185 else
186 return 0;
a1bb33af
UH
187}
188
6f4b1868 189static int configure_probes(const struct sr_dev_inst *sdi, const GSList *probes)
a1bb33af 190{
310e9e9b 191 struct dev_context *devc;
1b79df2f
JH
192 const struct sr_probe *probe;
193 const GSList *l;
a1bb33af
UH
194 int probe_bit, stage, i;
195 char *tc;
196
bf43ea23 197 /* Note: sdi and sdi->priv are non-NULL, the caller checked this. */
310e9e9b 198 devc = sdi->priv;
bf43ea23 199
310e9e9b 200 devc->probe_mask = 0;
fed16f06 201 for (i = 0; i < NUM_TRIGGER_STAGES; i++) {
310e9e9b
BV
202 devc->trigger_mask[i] = 0;
203 devc->trigger_value[i] = 0;
a1bb33af
UH
204 }
205
206 stage = -1;
fed16f06 207 for (l = probes; l; l = l->next) {
1afe8989 208 probe = (struct sr_probe *)l->data;
fed16f06 209 if (probe->enabled == FALSE)
a1bb33af 210 continue;
b35c8293 211 probe_bit = 1 << (probe->index);
310e9e9b 212 devc->probe_mask |= probe_bit;
fed16f06
UH
213
214 if (probe->trigger) {
a1bb33af 215 stage = 0;
fed16f06 216 for (tc = probe->trigger; *tc; tc++) {
310e9e9b 217 devc->trigger_mask[stage] |= probe_bit;
fed16f06 218 if (*tc == '1')
310e9e9b 219 devc->trigger_value[stage] |= probe_bit;
a1bb33af 220 stage++;
fed16f06 221 if (stage > NUM_TRIGGER_STAGES)
e46b8fb1 222 return SR_ERR;
a1bb33af
UH
223 }
224 }
225 }
226
e46b8fb1 227 return SR_OK;
a1bb33af
UH
228}
229
7da6f9d5
BV
230static void clear_instances(void)
231{
232 GSList *l;
233 struct sr_dev_inst *sdi;
310e9e9b 234 struct drv_context *drvc;
fabe59b3 235 struct dev_context *devc;
7da6f9d5 236
310e9e9b
BV
237 drvc = zdi->priv;
238 for (l = drvc->instances; l; l = l->next) {
7da6f9d5 239 sdi = l->data;
fabe59b3
BV
240 if (!(devc = sdi->priv)) {
241 /* Log error, but continue cleaning up the rest. */
242 sr_err("zeroplus: %s: sdi->priv was NULL, continuing", __func__);
243 continue;
244 }
245 sr_usb_dev_inst_free(devc->usb);
7da6f9d5 246 /* Properly close all devices... */
25a0f108 247 hw_dev_close(sdi);
7da6f9d5
BV
248 /* ...and free all their memory. */
249 sr_dev_inst_free(sdi);
250 }
310e9e9b
BV
251 g_slist_free(drvc->instances);
252 drvc->instances = NULL;
7da6f9d5
BV
253
254}
255
a1bb33af
UH
256/*
257 * API callbacks
258 */
259
40dda2c3 260static int hw_init(void)
61136ea6 261{
310e9e9b
BV
262 struct drv_context *drvc;
263
264 if (!(drvc = g_try_malloc0(sizeof(struct drv_context)))) {
265 sr_err("zeroplus: driver context malloc failed.");
266 return SR_ERR;
267 }
268 zdi->priv = drvc;
61136ea6 269
7da6f9d5
BV
270 if (libusb_init(&usb_context) != 0) {
271 sr_err("zp: Failed to initialize USB.");
272 return 0;
273 }
61136ea6
BV
274
275 return SR_OK;
276}
277
4ca38984 278static GSList *hw_scan(GSList *options)
a1bb33af 279{
d68e2d1a 280 struct sr_dev_inst *sdi;
428edbe1 281 struct sr_probe *probe;
310e9e9b
BV
282 struct drv_context *drvc;
283 struct dev_context *devc;
428edbe1 284 model_t *prof;
a1bb33af
UH
285 struct libusb_device_descriptor des;
286 libusb_device **devlist;
428edbe1
BV
287 GSList *devices;
288 int ret, devcnt, i, j;
a1bb33af 289
4ca38984 290 (void)options;
310e9e9b 291 drvc = zdi->priv;
4ca38984
BV
292 devices = NULL;
293
7da6f9d5
BV
294 clear_instances();
295
8fdecced 296 /* Find all ZEROPLUS analyzers and add them to device list. */
a1bb33af 297 devcnt = 0;
185ae2c5 298 libusb_get_device_list(usb_context, &devlist); /* TODO: Errors. */
fed16f06
UH
299
300 for (i = 0; devlist[i]; i++) {
ebc34738
UH
301 ret = libusb_get_device_descriptor(devlist[i], &des);
302 if (ret != 0) {
303 sr_err("zp: failed to get device descriptor: %d", ret);
a1bb33af
UH
304 continue;
305 }
306
428edbe1
BV
307 prof = NULL;
308 for (j = 0; j < zeroplus_models[j].vid; j++) {
309 if (des.idVendor == zeroplus_models[j].vid &&
310 des.idProduct == zeroplus_models[j].pid) {
311 prof = &zeroplus_models[j];
bf43ea23 312 }
a1bb33af 313 }
428edbe1
BV
314 /* Skip if the device was not found */
315 if (!prof)
316 continue;
317 sr_info("zp: Found ZEROPLUS model %s", prof->model_name);
318
319 /* Register the device with libsigrok. */
320 if (!(sdi = sr_dev_inst_new(devcnt, SR_ST_INACTIVE,
321 VENDOR_NAME, prof->model_name, NULL))) {
322 sr_err("zp: %s: sr_dev_inst_new failed", __func__);
323 return NULL;
324 }
325 sdi->driver = zdi;
326
327 /* Allocate memory for our private driver context. */
310e9e9b
BV
328 if (!(devc = g_try_malloc0(sizeof(struct dev_context)))) {
329 sr_err("zp: %s: devc malloc failed", __func__);
428edbe1
BV
330 return 0;
331 }
310e9e9b
BV
332 sdi->priv = devc;
333 devc->num_channels = prof->channels;
334 devc->memory_size = prof->sample_depth * 1024;
335 // memset(devc->trigger_buffer, 0, NUM_TRIGGER_STAGES);
428edbe1
BV
336
337 /* Fill in probelist according to this device's profile. */
310e9e9b 338 for (j = 0; j < devc->num_channels; j++) {
428edbe1
BV
339 if (!(probe = sr_probe_new(j, SR_PROBE_LOGIC, TRUE,
340 probe_names[j])))
341 return NULL;
342 sdi->probes = g_slist_append(sdi->probes, probe);
343 }
344
345 devices = g_slist_append(devices, sdi);
310e9e9b
BV
346 drvc->instances = g_slist_append(drvc->instances, sdi);
347 devc->usb = sr_usb_dev_inst_new(
428edbe1
BV
348 libusb_get_bus_number(devlist[i]),
349 libusb_get_device_address(devlist[i]), NULL);
350 devcnt++;
351
a1bb33af
UH
352 }
353 libusb_free_device_list(devlist, 1);
354
4ca38984 355 return devices;
a1bb33af
UH
356}
357
25a0f108 358static int hw_dev_open(struct sr_dev_inst *sdi)
a1bb33af 359{
310e9e9b 360 struct dev_context *devc;
428edbe1
BV
361 libusb_device **devlist, *dev;
362 struct libusb_device_descriptor des;
363 int device_count, ret, i;
a1bb33af 364
310e9e9b 365 if (!(devc = sdi->priv)) {
bf43ea23
UH
366 sr_err("zp: %s: sdi->priv was NULL", __func__);
367 return SR_ERR_ARG;
368 }
369
428edbe1
BV
370 device_count = libusb_get_device_list(usb_context, &devlist);
371 if (device_count < 0) {
372 sr_err("zp: Failed to retrieve device list");
373 return SR_ERR;
374 }
375
376 dev = NULL;
377 for (i = 0; i < device_count; i++) {
378 if ((ret = libusb_get_device_descriptor(devlist[i], &des))) {
379 sr_err("fx2lafw: Failed to get device descriptor: %d.",
380 ret);
381 continue;
382 }
310e9e9b
BV
383 if (libusb_get_bus_number(devlist[i]) == devc->usb->bus
384 && libusb_get_device_address(devlist[i]) == devc->usb->address) {
428edbe1
BV
385 dev = devlist[i];
386 break;
387 }
388 }
389 if (!dev) {
390 sr_err("device on bus %d address %d disappeared!",
310e9e9b 391 devc->usb->bus, devc->usb->address);
428edbe1
BV
392 return SR_ERR;
393 }
394
310e9e9b 395 if (!(ret = libusb_open(dev, &(devc->usb->devhdl)))) {
428edbe1
BV
396 sdi->status = SR_ST_ACTIVE;
397 sr_info("zp: opened device %d on %d.%d interface %d",
310e9e9b
BV
398 sdi->index, devc->usb->bus,
399 devc->usb->address, USB_INTERFACE);
428edbe1
BV
400 } else {
401 sr_err("zp: failed to open device: %d", ret);
402 return SR_ERR;
403 }
404
310e9e9b 405 ret = libusb_set_configuration(devc->usb->devhdl, USB_CONFIGURATION);
ebc34738 406 if (ret < 0) {
133a37bf 407 sr_err("zp: Unable to set USB configuration %d: %d",
ebc34738 408 USB_CONFIGURATION, ret);
185ae2c5
UH
409 return SR_ERR;
410 }
411
310e9e9b 412 ret = libusb_claim_interface(devc->usb->devhdl, USB_INTERFACE);
ebc34738
UH
413 if (ret != 0) {
414 sr_err("zp: Unable to claim interface: %d", ret);
e46b8fb1 415 return SR_ERR;
a1bb33af 416 }
185ae2c5 417
310e9e9b
BV
418 analyzer_reset(devc->usb->devhdl);
419 analyzer_initialize(devc->usb->devhdl);
a1bb33af
UH
420
421 analyzer_set_memory_size(MEMORY_SIZE_512K);
fed16f06 422 // analyzer_set_freq(g_freq, g_freq_scale);
a1bb33af 423 analyzer_set_trigger_count(1);
408e7199
UH
424 // analyzer_set_ramsize_trigger_address((((100 - g_pre_trigger)
425 // * get_memory_size(g_memory_size)) / 100) >> 2);
fed16f06
UH
426 analyzer_set_ramsize_trigger_address(
427 (100 * get_memory_size(MEMORY_SIZE_512K) / 100) >> 2);
a1bb33af 428
fed16f06
UH
429#if 0
430 if (g_double_mode == 1)
a1bb33af
UH
431 analyzer_set_compression(COMPRESSION_DOUBLE);
432 else if (g_compression == 1)
433 analyzer_set_compression(COMPRESSION_ENABLE);
fed16f06
UH
434 else
435#endif
436 analyzer_set_compression(COMPRESSION_NONE);
a1bb33af 437
310e9e9b 438 if (devc->cur_samplerate == 0) {
408e7199 439 /* Samplerate hasn't been set. Default to the slowest one. */
6f4b1868 440 if (hw_dev_config_set(sdi, SR_HWCAP_SAMPLERATE,
73017cf9 441 &samplerates.list[0]) == SR_ERR)
e46b8fb1 442 return SR_ERR;
a1bb33af
UH
443 }
444
e46b8fb1 445 return SR_OK;
a1bb33af
UH
446}
447
25a0f108 448static int hw_dev_close(struct sr_dev_inst *sdi)
a1bb33af 449{
310e9e9b 450 struct dev_context *devc;
a1bb33af 451
310e9e9b 452 if (!(devc = sdi->priv)) {
25a0f108
BV
453 sr_err("zp: %s: sdi->priv was NULL", __func__);
454 return SR_ERR;
697785d1
UH
455 }
456
310e9e9b 457 if (!devc->usb->devhdl)
25a0f108
BV
458 return SR_ERR;
459
460 sr_info("zp: closing device %d on %d.%d interface %d", sdi->index,
310e9e9b
BV
461 devc->usb->bus, devc->usb->address, USB_INTERFACE);
462 libusb_release_interface(devc->usb->devhdl, USB_INTERFACE);
463 libusb_reset_device(devc->usb->devhdl);
464 libusb_close(devc->usb->devhdl);
465 devc->usb->devhdl = NULL;
25a0f108 466 sdi->status = SR_ST_INACTIVE;
697785d1
UH
467
468 return SR_OK;
a1bb33af
UH
469}
470
57ab7d9f 471static int hw_cleanup(void)
a1bb33af 472{
310e9e9b
BV
473 struct drv_context *drvc;
474
475 if (!(drvc = zdi->priv))
476 return SR_OK;
a1bb33af 477
7da6f9d5 478 clear_instances();
a1bb33af 479
fed16f06 480 if (usb_context)
a1bb33af
UH
481 libusb_exit(usb_context);
482 usb_context = NULL;
57ab7d9f
UH
483
484 return SR_OK;
a1bb33af
UH
485}
486
626409ab
BV
487static int hw_info_get(int info_id, const void **data,
488 const struct sr_dev_inst *sdi)
a1bb33af 489{
310e9e9b 490 struct dev_context *devc;
a1bb33af 491
626409ab 492 switch (info_id) {
444adea2
BV
493 case SR_DI_HWCAPS:
494 *data = hwcaps;
495 break;
5a2326a7 496 case SR_DI_NUM_PROBES:
626409ab 497 if (sdi) {
310e9e9b
BV
498 devc = sdi->priv;
499 *data = GINT_TO_POINTER(devc->num_channels);
626409ab 500 sr_spew("zp: %s: Returning number of channels: %d.",
310e9e9b 501 __func__, devc->num_channels);
626409ab
BV
502 } else
503 return SR_ERR;
a1bb33af 504 break;
464d12c7 505 case SR_DI_PROBE_NAMES:
626409ab 506 *data = probe_names;
6752905e 507 sr_spew("zp: %s: Returning probenames.", __func__);
464d12c7 508 break;
5a2326a7 509 case SR_DI_SAMPLERATES:
626409ab 510 *data = &samplerates;
6752905e 511 sr_spew("zp: %s: Returning samplerates.", __func__);
a1bb33af 512 break;
5a2326a7 513 case SR_DI_TRIGGER_TYPES:
626409ab
BV
514 *data = TRIGGER_TYPES;
515 sr_spew("zp: %s: Returning triggertypes: %s.", __func__, TRIGGER_TYPES);
a1bb33af 516 break;
5a2326a7 517 case SR_DI_CUR_SAMPLERATE:
626409ab 518 if (sdi) {
310e9e9b
BV
519 devc = sdi->priv;
520 *data = &devc->cur_samplerate;
626409ab 521 sr_spew("zp: %s: Returning samplerate: %" PRIu64 "Hz.",
310e9e9b 522 __func__, devc->cur_samplerate);
626409ab
BV
523 } else
524 return SR_ERR;
bf43ea23
UH
525 break;
526 default:
626409ab 527 return SR_ERR_ARG;
a1bb33af
UH
528 }
529
626409ab 530 return SR_OK;
a1bb33af
UH
531}
532
6f4b1868 533static int set_samplerate(const struct sr_dev_inst *sdi, uint64_t samplerate)
a1bb33af 534{
310e9e9b 535 struct dev_context *devc;
bf43ea23
UH
536
537 if (!sdi) {
538 sr_err("zp: %s: sdi was NULL", __func__);
539 return SR_ERR_ARG;
540 }
541
310e9e9b 542 if (!(devc = sdi->priv)) {
bf43ea23
UH
543 sr_err("zp: %s: sdi->priv was NULL", __func__);
544 return SR_ERR_ARG;
545 }
546
73017cf9
UH
547 sr_info("zp: Setting samplerate to %" PRIu64 "Hz.", samplerate);
548
59df0c77
UH
549 if (samplerate > SR_MHZ(1))
550 analyzer_set_freq(samplerate / SR_MHZ(1), FREQ_SCALE_MHZ);
551 else if (samplerate > SR_KHZ(1))
552 analyzer_set_freq(samplerate / SR_KHZ(1), FREQ_SCALE_KHZ);
a1bb33af 553 else
fed16f06 554 analyzer_set_freq(samplerate, FREQ_SCALE_HZ);
a1bb33af 555
310e9e9b 556 devc->cur_samplerate = samplerate;
a1bb33af 557
e46b8fb1 558 return SR_OK;
a1bb33af
UH
559}
560
6f4b1868
BV
561static int hw_dev_config_set(const struct sr_dev_inst *sdi, int hwcap,
562 const void *value)
a1bb33af 563{
310e9e9b 564 struct dev_context *devc;
a1bb33af 565
310e9e9b 566 if (!(devc = sdi->priv)) {
bf43ea23
UH
567 sr_err("zp: %s: sdi->priv was NULL", __func__);
568 return SR_ERR_ARG;
569 }
a1bb33af 570
ffedd0bf 571 switch (hwcap) {
5a2326a7 572 case SR_HWCAP_SAMPLERATE:
1b79df2f 573 return set_samplerate(sdi, *(const uint64_t *)value);
5a2326a7 574 case SR_HWCAP_PROBECONFIG:
1b79df2f 575 return configure_probes(sdi, (const GSList *)value);
5a2326a7 576 case SR_HWCAP_LIMIT_SAMPLES:
310e9e9b 577 devc->limit_samples = *(const uint64_t *)value;
e46b8fb1 578 return SR_OK;
fed16f06 579 default:
e46b8fb1 580 return SR_ERR;
a1bb33af
UH
581 }
582}
583
3ffb6964
BV
584static int hw_dev_acquisition_start(const struct sr_dev_inst *sdi,
585 void *cb_data)
a1bb33af 586{
b9c735a2 587 struct sr_datafeed_packet packet;
9c939c51 588 struct sr_datafeed_logic logic;
b9c735a2 589 struct sr_datafeed_header header;
f366e86c 590 struct sr_datafeed_meta_logic meta;
9c939c51 591 uint64_t samples_read;
a1bb33af 592 int res;
afc8e4de 593 unsigned int packet_num;
a1bb33af 594 unsigned char *buf;
310e9e9b 595 struct dev_context *devc;
a1bb33af 596
310e9e9b 597 if (!(devc = sdi->priv)) {
bf43ea23
UH
598 sr_err("zp: %s: sdi->priv was NULL", __func__);
599 return SR_ERR_ARG;
600 }
a1bb33af 601
a143e4e5 602 /* push configured settings to device */
310e9e9b 603 analyzer_configure(devc->usb->devhdl);
a143e4e5 604
310e9e9b 605 analyzer_start(devc->usb->devhdl);
7b48d6e1 606 sr_info("zp: Waiting for data");
310e9e9b 607 analyzer_wait_data(devc->usb->devhdl);
a1bb33af 608
7b48d6e1 609 sr_info("zp: Stop address = 0x%x",
310e9e9b 610 analyzer_get_stop_address(devc->usb->devhdl));
7b48d6e1 611 sr_info("zp: Now address = 0x%x",
310e9e9b 612 analyzer_get_now_address(devc->usb->devhdl));
7b48d6e1 613 sr_info("zp: Trigger address = 0x%x",
310e9e9b 614 analyzer_get_trigger_address(devc->usb->devhdl));
a1bb33af 615
5a2326a7 616 packet.type = SR_DF_HEADER;
9c939c51 617 packet.payload = &header;
a1bb33af
UH
618 header.feed_version = 1;
619 gettimeofday(&header.starttime, NULL);
f366e86c
BV
620 sr_session_send(cb_data, &packet);
621
622 /* Send metadata about the SR_DF_LOGIC packets to come. */
623 packet.type = SR_DF_META_LOGIC;
624 packet.payload = &meta;
310e9e9b
BV
625 meta.samplerate = devc->cur_samplerate;
626 meta.num_probes = devc->num_channels;
3cd3a20b 627 sr_session_send(cb_data, &packet);
a1bb33af 628
b53738ba 629 if (!(buf = g_try_malloc(PACKET_SIZE))) {
bf43ea23 630 sr_err("zp: %s: buf malloc failed", __func__);
b53738ba
UH
631 return SR_ERR_MALLOC;
632 }
633
9c939c51 634 samples_read = 0;
310e9e9b 635 analyzer_read_start(devc->usb->devhdl);
fed16f06 636 /* Send the incoming transfer to the session bus. */
310e9e9b 637 for (packet_num = 0; packet_num < (devc->memory_size * 4 / PACKET_SIZE);
fed16f06 638 packet_num++) {
310e9e9b 639 res = analyzer_read_data(devc->usb->devhdl, buf, PACKET_SIZE);
7b48d6e1 640 sr_info("zp: Tried to read %llx bytes, actually read %x bytes",
b08024a8 641 PACKET_SIZE, res);
a1bb33af 642
5a2326a7 643 packet.type = SR_DF_LOGIC;
9c939c51
BV
644 packet.payload = &logic;
645 logic.length = PACKET_SIZE;
646 logic.unitsize = 4;
647 logic.data = buf;
3cd3a20b 648 sr_session_send(cb_data, &packet);
9c939c51 649 samples_read += res / 4;
a1bb33af 650 }
310e9e9b 651 analyzer_read_stop(devc->usb->devhdl);
a1bb33af
UH
652 g_free(buf);
653
5a2326a7 654 packet.type = SR_DF_END;
3cd3a20b 655 sr_session_send(cb_data, &packet);
a1bb33af 656
e46b8fb1 657 return SR_OK;
a1bb33af
UH
658}
659
3cd3a20b 660/* TODO: This stops acquisition on ALL devices, ignoring dev_index. */
3ffb6964
BV
661static int hw_dev_acquisition_stop(const struct sr_dev_inst *sdi,
662 void *cb_data)
a1bb33af 663{
b9c735a2 664 struct sr_datafeed_packet packet;
310e9e9b 665 struct dev_context *devc;
a1bb33af 666
5a2326a7 667 packet.type = SR_DF_END;
3cd3a20b 668 sr_session_send(cb_data, &packet);
a1bb33af 669
310e9e9b 670 if (!(devc = sdi->priv)) {
69890f73 671 sr_err("zp: %s: sdi->priv was NULL", __func__);
3010f21c 672 return SR_ERR_BUG;
69890f73 673 }
a1bb33af 674
310e9e9b 675 analyzer_reset(devc->usb->devhdl);
fed16f06 676 /* TODO: Need to cancel and free any queued up transfers. */
3010f21c
UH
677
678 return SR_OK;
a1bb33af
UH
679}
680
c09f0b57 681SR_PRIV struct sr_dev_driver zeroplus_logic_cube_driver_info = {
e519ba86 682 .name = "zeroplus-logic-cube",
8fdecced 683 .longname = "ZEROPLUS Logic Cube LAP-C series",
e519ba86
UH
684 .api_version = 1,
685 .init = hw_init,
686 .cleanup = hw_cleanup,
61136ea6 687 .scan = hw_scan,
e7eb703f
UH
688 .dev_open = hw_dev_open,
689 .dev_close = hw_dev_close,
626409ab 690 .info_get = hw_info_get,
a9a245b4 691 .dev_config_set = hw_dev_config_set,
69040b7c
UH
692 .dev_acquisition_start = hw_dev_acquisition_start,
693 .dev_acquisition_stop = hw_dev_acquisition_stop,
310e9e9b 694 .priv = NULL,
a1bb33af 695};