]> sigrok.org Git - libsigrok.git/blame - hardware/zeroplus-logic-cube/zeroplus.c
Add sr_device_get_info
[libsigrok.git] / hardware / zeroplus-logic-cube / zeroplus.c
CommitLineData
a1bb33af
UH
1/*
2 * This file is part of the sigrok project.
3 *
4 * Copyright (C) 2010 Bert Vermeulen <bert@biot.com>
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
22b02383 20#include "config.h"
a1bb33af
UH
21#include <stdio.h>
22#include <stdlib.h>
23#include <sys/time.h>
24#include <inttypes.h>
25#include <glib.h>
26#include <libusb.h>
b7f09cf8
UH
27#include "sigrok.h"
28#include "sigrok-internal.h"
a1bb33af
UH
29#include "analyzer.h"
30
fed16f06
UH
31#define USB_VENDOR 0x0c12
32#define USB_VENDOR_NAME "Zeroplus"
a1bb33af
UH
33#define USB_MODEL_NAME "Logic Cube"
34#define USB_MODEL_VERSION ""
35
36#define USB_INTERFACE 0
37#define USB_CONFIGURATION 1
38#define NUM_TRIGGER_STAGES 4
39#define TRIGGER_TYPES "01"
40
fed16f06 41#define PACKET_SIZE 2048 /* ?? */
a1bb33af
UH
42
43typedef struct {
44 unsigned short pid;
45 char model_name[64];
46 unsigned int channels;
fed16f06 47 unsigned int sample_depth; /* In Ksamples/channel */
a1bb33af
UH
48 unsigned int max_sampling_freq;
49} model_t;
50
fed16f06
UH
51/*
52 * Note -- 16032, 16064 and 16128 *usually* -- but not always -- have the
53 * same 128K sample depth.
54 */
29cbfeaf 55static model_t zeroplus_models[] = {
a1bb33af
UH
56 {0x7009, "LAP-C(16064)", 16, 64, 100},
57 {0x700A, "LAP-C(16128)", 16, 128, 200},
58 {0x700B, "LAP-C(32128)", 32, 128, 200},
59 {0x700C, "LAP-C(321000)", 32, 1024, 200},
60 {0x700D, "LAP-C(322000)", 32, 2048, 200},
61 {0x700E, "LAP-C(16032)", 16, 32, 100},
62 {0x7016, "LAP-C(162000)", 16, 2048, 200},
63};
64
65static int capabilities[] = {
5a2326a7
UH
66 SR_HWCAP_LOGIC_ANALYZER,
67 SR_HWCAP_SAMPLERATE,
68 SR_HWCAP_PROBECONFIG,
69 SR_HWCAP_CAPTURE_RATIO,
a1bb33af 70
fed16f06 71 /* These are really implemented in the driver, not the hardware. */
5a2326a7 72 SR_HWCAP_LIMIT_SAMPLES,
fed16f06 73 0,
a1bb33af
UH
74};
75
c37d2b1b 76static const char *probe_names[] = {
464d12c7
KS
77 "0",
78 "1",
79 "2",
80 "3",
81 "4",
82 "5",
83 "6",
84 "7",
85 "8",
86 "9",
87 "10",
88 "11",
89 "12",
90 "13",
91 "14",
92 "15",
93 "16",
94 "17",
95 "18",
96 "19",
97 "20",
98 "21",
99 "22",
100 "23",
101 "24",
102 "25",
103 "26",
104 "27",
105 "28",
106 "29",
107 "30",
108 "31",
109 NULL,
110};
111
a00ba012 112/* List of struct sr_device_instance, maintained by opendev()/closedev(). */
a1bb33af
UH
113static GSList *device_instances = NULL;
114
115static libusb_context *usb_context = NULL;
116
fed16f06
UH
117/*
118 * The hardware supports more samplerates than these, but these are the
119 * options hardcoded into the vendor's Windows GUI.
120 */
a1bb33af 121
fed16f06
UH
122/*
123 * TODO: We shouldn't support 150MHz and 200MHz on devices that don't go up
124 * that high.
125 */
a1bb33af 126static uint64_t supported_samplerates[] = {
c9140419
UH
127 SR_HZ(100),
128 SR_HZ(500),
59df0c77
UH
129 SR_KHZ(1),
130 SR_KHZ(5),
131 SR_KHZ(25),
132 SR_KHZ(50),
133 SR_KHZ(100),
134 SR_KHZ(200),
135 SR_KHZ(400),
136 SR_KHZ(800),
137 SR_MHZ(1),
138 SR_MHZ(10),
139 SR_MHZ(25),
140 SR_MHZ(50),
141 SR_MHZ(80),
142 SR_MHZ(100),
143 SR_MHZ(150),
144 SR_MHZ(200),
fed16f06 145 0,
a1bb33af
UH
146};
147
60679b18 148static struct sr_samplerates samplerates = {
c9140419
UH
149 SR_HZ(0),
150 SR_HZ(0),
151 SR_HZ(0),
fed16f06 152 supported_samplerates,
a1bb33af
UH
153};
154
bf43ea23
UH
155struct zp {
156 uint64_t cur_samplerate;
157 uint64_t period_ps;
158 uint64_t limit_samples;
159 int num_channels; /* TODO: This isn't initialized before it's needed :( */
160 uint64_t memory_size;
161 uint8_t probe_mask;
162 uint8_t trigger_mask[NUM_TRIGGER_STAGES];
163 uint8_t trigger_value[NUM_TRIGGER_STAGES];
164 // uint8_t trigger_buffer[NUM_TRIGGER_STAGES];
165};
a1bb33af
UH
166
167static int hw_set_configuration(int device_index, int capability, void *value);
168
169static unsigned int get_memory_size(int type)
170{
fed16f06
UH
171 if (type == MEMORY_SIZE_8K)
172 return 8 * 1024;
173 else if (type == MEMORY_SIZE_64K)
174 return 64 * 1024;
175 else if (type == MEMORY_SIZE_128K)
176 return 128 * 1024;
177 else if (type == MEMORY_SIZE_512K)
178 return 512 * 1024;
179 else
180 return 0;
a1bb33af
UH
181}
182
a00ba012 183static int opendev4(struct sr_device_instance **sdi, libusb_device *dev,
408e7199
UH
184 struct libusb_device_descriptor *des)
185{
bf43ea23 186 struct zp *zp;
9a498834
UH
187 unsigned int i;
188 int err;
408e7199 189
bf43ea23
UH
190 /* Note: sdi is non-NULL, the caller already checked this. */
191
192 if (!(zp = (*sdi)->priv)) {
193 sr_err("zp: %s: (*sdi)->priv was NULL", __func__);
194 return -1;
195 }
196
408e7199 197 if ((err = libusb_get_device_descriptor(dev, des))) {
b08024a8 198 sr_warn("failed to get device descriptor: %d", err);
408e7199
UH
199 return -1;
200 }
201
9a498834 202 if (des->idVendor != USB_VENDOR)
408e7199
UH
203 return 0;
204
205 if (libusb_get_bus_number(dev) == (*sdi)->usb->bus
206 && libusb_get_device_address(dev) == (*sdi)->usb->address) {
207
9a498834
UH
208 for (i = 0; i < ARRAY_SIZE(zeroplus_models); i++) {
209 if (!(des->idProduct == zeroplus_models[i].pid))
408e7199
UH
210 continue;
211
b08024a8
UH
212 sr_info("Found PID=%04X (%s)", des->idProduct,
213 zeroplus_models[i].model_name);
bf43ea23
UH
214 zp->num_channels = zeroplus_models[i].channels;
215 zp->memory_size = zeroplus_models[i].sample_depth * 1024;
408e7199
UH
216 break;
217 }
218
bf43ea23 219 if (zp->num_channels == 0) {
b08024a8 220 sr_warn("Unknown ZeroPlus device %04X", des->idProduct);
408e7199
UH
221 return -2;
222 }
223
224 /* Found it. */
225 if (!(err = libusb_open(dev, &((*sdi)->usb->devhdl)))) {
5a2326a7 226 (*sdi)->status = SR_ST_ACTIVE;
b08024a8
UH
227 sr_info("opened device %d on %d.%d interface %d",
228 (*sdi)->index, (*sdi)->usb->bus,
229 (*sdi)->usb->address, USB_INTERFACE);
408e7199 230 } else {
b08024a8 231 sr_warn("failed to open device: %d", err);
408e7199
UH
232 *sdi = NULL;
233 }
234 }
235
236 return 0;
237}
238
29cbfeaf 239static struct sr_device_instance *zp_open_device(int device_index)
a1bb33af 240{
a00ba012 241 struct sr_device_instance *sdi;
a1bb33af
UH
242 libusb_device **devlist;
243 struct libusb_device_descriptor des;
afc8e4de 244 int err, i;
a1bb33af 245
d32d961d 246 if (!(sdi = sr_get_device_instance(device_instances, device_index)))
a1bb33af
UH
247 return NULL;
248
249 libusb_get_device_list(usb_context, &devlist);
5a2326a7 250 if (sdi->status == SR_ST_INACTIVE) {
fed16f06 251 /* Find the device by vendor, product, bus and address. */
a1bb33af 252 libusb_get_device_list(usb_context, &devlist);
fed16f06 253 for (i = 0; devlist[i]; i++) {
408e7199 254 /* TODO: Error handling. */
9a5c6dcf 255 err = opendev4(&sdi, devlist[i], &des);
a1bb33af 256 }
fed16f06 257 } else {
5a2326a7 258 /* Status must be SR_ST_ACTIVE, i.e. already in use... */
a1bb33af
UH
259 sdi = NULL;
260 }
261 libusb_free_device_list(devlist, 1);
262
5a2326a7 263 if (sdi && sdi->status != SR_ST_ACTIVE)
a1bb33af
UH
264 sdi = NULL;
265
266 return sdi;
267}
268
a00ba012 269static void close_device(struct sr_device_instance *sdi)
a1bb33af 270{
408e7199
UH
271 if (!sdi->usb->devhdl)
272 return;
273
b08024a8
UH
274 sr_info("closing device %d on %d.%d interface %d", sdi->index,
275 sdi->usb->bus, sdi->usb->address, USB_INTERFACE);
408e7199
UH
276 libusb_release_interface(sdi->usb->devhdl, USB_INTERFACE);
277 libusb_close(sdi->usb->devhdl);
278 sdi->usb->devhdl = NULL;
5a2326a7 279 sdi->status = SR_ST_INACTIVE;
a1bb33af
UH
280}
281
bf43ea23 282static int configure_probes(struct sr_device_instance *sdi, GSList *probes)
a1bb33af 283{
bf43ea23 284 struct zp *zp;
1afe8989 285 struct sr_probe *probe;
a1bb33af
UH
286 GSList *l;
287 int probe_bit, stage, i;
288 char *tc;
289
bf43ea23
UH
290 /* Note: sdi and sdi->priv are non-NULL, the caller checked this. */
291 zp = sdi->priv;
292
293 zp->probe_mask = 0;
fed16f06 294 for (i = 0; i < NUM_TRIGGER_STAGES; i++) {
bf43ea23
UH
295 zp->trigger_mask[i] = 0;
296 zp->trigger_value[i] = 0;
a1bb33af
UH
297 }
298
299 stage = -1;
fed16f06 300 for (l = probes; l; l = l->next) {
1afe8989 301 probe = (struct sr_probe *)l->data;
fed16f06 302 if (probe->enabled == FALSE)
a1bb33af
UH
303 continue;
304 probe_bit = 1 << (probe->index - 1);
bf43ea23 305 zp->probe_mask |= probe_bit;
fed16f06
UH
306
307 if (probe->trigger) {
a1bb33af 308 stage = 0;
fed16f06 309 for (tc = probe->trigger; *tc; tc++) {
bf43ea23 310 zp->trigger_mask[stage] |= probe_bit;
fed16f06 311 if (*tc == '1')
bf43ea23 312 zp->trigger_value[stage] |= probe_bit;
a1bb33af 313 stage++;
fed16f06 314 if (stage > NUM_TRIGGER_STAGES)
e46b8fb1 315 return SR_ERR;
a1bb33af
UH
316 }
317 }
318 }
319
e46b8fb1 320 return SR_OK;
a1bb33af
UH
321}
322
a1bb33af
UH
323/*
324 * API callbacks
325 */
326
54ac5277 327static int hw_init(const char *deviceinfo)
a1bb33af 328{
a00ba012 329 struct sr_device_instance *sdi;
a1bb33af
UH
330 struct libusb_device_descriptor des;
331 libusb_device **devlist;
332 int err, devcnt, i;
bf43ea23 333 struct zp *zp;
a1bb33af 334
17e1afcb 335 /* Avoid compiler warnings. */
cb93f8a9 336 (void)deviceinfo;
afc8e4de 337
bf43ea23
UH
338 /* Allocate memory for our private driver context. */
339 if (!(zp = g_try_malloc(sizeof(struct zp)))) {
340 sr_err("zp: %s: struct zp malloc failed", __func__);
341 return 0;
342 }
343
344 /* Set some sane defaults. */
345 zp->cur_samplerate = 0;
346 zp->period_ps = 0;
347 zp->limit_samples = 0;
348 zp->num_channels = 32; /* TODO: This isn't initialized before it's needed :( */
349 zp->memory_size = 0;
350 zp->probe_mask = 0;
351 memset(zp->trigger_mask, 0, NUM_TRIGGER_STAGES);
352 memset(zp->trigger_value, 0, NUM_TRIGGER_STAGES);
353 // memset(zp->trigger_buffer, 0, NUM_TRIGGER_STAGES);
354
fed16f06 355 if (libusb_init(&usb_context) != 0) {
b08024a8 356 sr_warn("Failed to initialize USB.");
a1bb33af
UH
357 return 0;
358 }
359
fed16f06 360 /* Find all ZeroPlus analyzers and add them to device list. */
a1bb33af
UH
361 devcnt = 0;
362 libusb_get_device_list(usb_context, &devlist);
fed16f06
UH
363
364 for (i = 0; devlist[i]; i++) {
a1bb33af 365 err = libusb_get_device_descriptor(devlist[i], &des);
fed16f06 366 if (err != 0) {
b08024a8 367 sr_warn("failed to get device descriptor: %d", err);
a1bb33af
UH
368 continue;
369 }
370
fed16f06
UH
371 if (des.idVendor == USB_VENDOR) {
372 /*
373 * Definitely a Zeroplus.
374 * TODO: Any way to detect specific model/version in
375 * the zeroplus range?
376 */
bf43ea23 377 /* Register the device with libsigrok. */
a00ba012 378 sdi = sr_device_instance_new(devcnt,
5a2326a7 379 SR_ST_INACTIVE, USB_VENDOR_NAME,
fed16f06 380 USB_MODEL_NAME, USB_MODEL_VERSION);
bf43ea23
UH
381 if (!sdi) {
382 sr_err("zp: %s: sr_device_instance_new failed",
383 __func__);
a1bb33af 384 return 0;
bf43ea23
UH
385 }
386
387 sdi->priv = zp;
388
fed16f06
UH
389 device_instances =
390 g_slist_append(device_instances, sdi);
6c290072 391 sdi->usb = sr_usb_device_instance_new(
fed16f06
UH
392 libusb_get_bus_number(devlist[i]),
393 libusb_get_device_address(devlist[i]), NULL);
a1bb33af
UH
394 devcnt++;
395 }
396 }
397 libusb_free_device_list(devlist, 1);
398
399 return devcnt;
400}
401
a1bb33af
UH
402static int hw_opendev(int device_index)
403{
a00ba012 404 struct sr_device_instance *sdi;
bf43ea23 405 struct zp *zp;
a1bb33af
UH
406 int err;
407
fed16f06 408 if (!(sdi = zp_open_device(device_index))) {
b08024a8 409 sr_warn("unable to open device");
e46b8fb1 410 return SR_ERR;
a1bb33af
UH
411 }
412
bf43ea23
UH
413 /* TODO: Note: sdi is retrieved in zp_open_device(). */
414
415 if (!(zp = sdi->priv)) {
416 sr_err("zp: %s: sdi->priv was NULL", __func__);
417 return SR_ERR_ARG;
418 }
419
a1bb33af 420 err = libusb_claim_interface(sdi->usb->devhdl, USB_INTERFACE);
fed16f06 421 if (err != 0) {
b08024a8 422 sr_warn("Unable to claim interface: %d", err);
e46b8fb1 423 return SR_ERR;
a1bb33af
UH
424 }
425 analyzer_reset(sdi->usb->devhdl);
426 analyzer_initialize(sdi->usb->devhdl);
a1bb33af
UH
427
428 analyzer_set_memory_size(MEMORY_SIZE_512K);
fed16f06 429 // analyzer_set_freq(g_freq, g_freq_scale);
a1bb33af 430 analyzer_set_trigger_count(1);
408e7199
UH
431 // analyzer_set_ramsize_trigger_address((((100 - g_pre_trigger)
432 // * get_memory_size(g_memory_size)) / 100) >> 2);
fed16f06
UH
433 analyzer_set_ramsize_trigger_address(
434 (100 * get_memory_size(MEMORY_SIZE_512K) / 100) >> 2);
a1bb33af 435
fed16f06
UH
436#if 0
437 if (g_double_mode == 1)
a1bb33af
UH
438 analyzer_set_compression(COMPRESSION_DOUBLE);
439 else if (g_compression == 1)
440 analyzer_set_compression(COMPRESSION_ENABLE);
fed16f06
UH
441 else
442#endif
443 analyzer_set_compression(COMPRESSION_NONE);
a1bb33af 444
bf43ea23 445 if (zp->cur_samplerate == 0) {
408e7199 446 /* Samplerate hasn't been set. Default to the slowest one. */
5a2326a7 447 if (hw_set_configuration(device_index, SR_HWCAP_SAMPLERATE,
73017cf9 448 &samplerates.list[0]) == SR_ERR)
e46b8fb1 449 return SR_ERR;
a1bb33af
UH
450 }
451
e46b8fb1 452 return SR_OK;
a1bb33af
UH
453}
454
697785d1 455static int hw_closedev(int device_index)
a1bb33af 456{
a00ba012 457 struct sr_device_instance *sdi;
a1bb33af 458
697785d1 459 if (!(sdi = sr_get_device_instance(device_instances, device_index))) {
bf43ea23 460 sr_err("zp: %s: sdi was NULL", __func__);
697785d1
UH
461 return SR_ERR; /* TODO: SR_ERR_ARG? */
462 }
463
464 /* TODO */
465 close_device(sdi);
466
467 return SR_OK;
a1bb33af
UH
468}
469
a1bb33af
UH
470static void hw_cleanup(void)
471{
472 GSList *l;
473
408e7199 474 /* Properly close all devices... */
fed16f06 475 for (l = device_instances; l; l = l->next)
a00ba012 476 close_device((struct sr_device_instance *)l->data);
a1bb33af 477
408e7199 478 /* ...and free all their memory. */
fed16f06 479 for (l = device_instances; l; l = l->next)
a1bb33af
UH
480 g_free(l->data);
481 g_slist_free(device_instances);
482 device_instances = NULL;
483
fed16f06 484 if (usb_context)
a1bb33af
UH
485 libusb_exit(usb_context);
486 usb_context = NULL;
a1bb33af
UH
487}
488
a1bb33af
UH
489static void *hw_get_device_info(int device_index, int device_info_id)
490{
a00ba012 491 struct sr_device_instance *sdi;
bf43ea23
UH
492 struct zp *zp;
493 void *info;
a1bb33af 494
bf43ea23
UH
495 if (!(sdi = sr_get_device_instance(device_instances, device_index))) {
496 sr_err("zp: %s: sdi was NULL", __func__);
a1bb33af 497 return NULL;
bf43ea23
UH
498 }
499
500 if (!(zp = sdi->priv)) {
501 sr_err("zp: %s: sdi->priv was NULL", __func__);
502 return NULL;
503 }
a1bb33af 504
fed16f06 505 switch (device_info_id) {
5a2326a7 506 case SR_DI_INSTANCE:
a1bb33af
UH
507 info = sdi;
508 break;
5a2326a7 509 case SR_DI_NUM_PROBES:
bf43ea23 510 info = GINT_TO_POINTER(zp->num_channels);
a1bb33af 511 break;
464d12c7
KS
512 case SR_DI_PROBE_NAMES:
513 info = probe_names;
514 break;
5a2326a7 515 case SR_DI_SAMPLERATES:
a1bb33af
UH
516 info = &samplerates;
517 break;
5a2326a7 518 case SR_DI_TRIGGER_TYPES:
a1bb33af
UH
519 info = TRIGGER_TYPES;
520 break;
5a2326a7 521 case SR_DI_CUR_SAMPLERATE:
bf43ea23
UH
522 info = &zp->cur_samplerate;
523 break;
524 default:
525 /* Unknown device info ID, return NULL. */
526 sr_err("zp: %s: Unknown device info ID", __func__);
527 info = NULL;
a1bb33af
UH
528 break;
529 }
530
531 return info;
532}
533
a1bb33af
UH
534static int hw_get_status(int device_index)
535{
a00ba012 536 struct sr_device_instance *sdi;
a1bb33af 537
d32d961d 538 sdi = sr_get_device_instance(device_instances, device_index);
fed16f06 539 if (sdi)
a1bb33af
UH
540 return sdi->status;
541 else
5a2326a7 542 return SR_ST_NOT_FOUND;
a1bb33af
UH
543}
544
a1bb33af
UH
545static int *hw_get_capabilities(void)
546{
a1bb33af
UH
547 return capabilities;
548}
549
bf43ea23
UH
550static int set_configuration_samplerate(struct sr_device_instance *sdi,
551 uint64_t samplerate)
a1bb33af 552{
bf43ea23
UH
553 struct zp *zp;
554
555 if (!sdi) {
556 sr_err("zp: %s: sdi was NULL", __func__);
557 return SR_ERR_ARG;
558 }
559
560 if (!(zp = sdi->priv)) {
561 sr_err("zp: %s: sdi->priv was NULL", __func__);
562 return SR_ERR_ARG;
563 }
564
73017cf9
UH
565 sr_info("zp: Setting samplerate to %" PRIu64 "Hz.", samplerate);
566
59df0c77
UH
567 if (samplerate > SR_MHZ(1))
568 analyzer_set_freq(samplerate / SR_MHZ(1), FREQ_SCALE_MHZ);
569 else if (samplerate > SR_KHZ(1))
570 analyzer_set_freq(samplerate / SR_KHZ(1), FREQ_SCALE_KHZ);
a1bb33af 571 else
fed16f06 572 analyzer_set_freq(samplerate, FREQ_SCALE_HZ);
a1bb33af 573
bf43ea23
UH
574 zp->cur_samplerate = samplerate;
575 zp->period_ps = 1000000000000 / samplerate;
a1bb33af 576
e46b8fb1 577 return SR_OK;
a1bb33af
UH
578}
579
580static int hw_set_configuration(int device_index, int capability, void *value)
581{
a00ba012 582 struct sr_device_instance *sdi;
a1bb33af 583 uint64_t *tmp_u64;
bf43ea23 584 struct zp *zp;
a1bb33af 585
bf43ea23
UH
586 if (!(sdi = sr_get_device_instance(device_instances, device_index))) {
587 sr_err("zp: %s: sdi was NULL", __func__);
e46b8fb1 588 return SR_ERR;
bf43ea23
UH
589 }
590
591 if (!(zp = sdi->priv)) {
592 sr_err("zp: %s: sdi->priv was NULL", __func__);
593 return SR_ERR_ARG;
594 }
a1bb33af
UH
595
596 switch (capability) {
5a2326a7 597 case SR_HWCAP_SAMPLERATE:
fed16f06 598 tmp_u64 = value;
bf43ea23 599 return set_configuration_samplerate(sdi, *tmp_u64);
5a2326a7 600 case SR_HWCAP_PROBECONFIG:
bf43ea23 601 return configure_probes(sdi, (GSList *)value);
5a2326a7 602 case SR_HWCAP_LIMIT_SAMPLES:
2458ea65 603 tmp_u64 = value;
bf43ea23 604 zp->limit_samples = *tmp_u64;
e46b8fb1 605 return SR_OK;
fed16f06 606 default:
e46b8fb1 607 return SR_ERR;
a1bb33af
UH
608 }
609}
610
9c939c51 611static int hw_start_acquisition(int device_index, gpointer session_data)
a1bb33af 612{
a00ba012 613 struct sr_device_instance *sdi;
b9c735a2 614 struct sr_datafeed_packet packet;
9c939c51 615 struct sr_datafeed_logic logic;
b9c735a2 616 struct sr_datafeed_header header;
9c939c51 617 uint64_t samples_read;
a1bb33af 618 int res;
afc8e4de 619 unsigned int packet_num;
a1bb33af 620 unsigned char *buf;
bf43ea23 621 struct zp *zp;
a1bb33af 622
bf43ea23
UH
623 if (!(sdi = sr_get_device_instance(device_instances, device_index))) {
624 sr_err("zp: %s: sdi was NULL", __func__);
e46b8fb1 625 return SR_ERR;
bf43ea23
UH
626 }
627
628 if (!(zp = sdi->priv)) {
629 sr_err("zp: %s: sdi->priv was NULL", __func__);
630 return SR_ERR_ARG;
631 }
a1bb33af 632
a143e4e5
BV
633 /* push configured settings to device */
634 analyzer_configure(sdi->usb->devhdl);
635
a1bb33af 636 analyzer_start(sdi->usb->devhdl);
b08024a8 637 sr_info("Waiting for data");
a1bb33af
UH
638 analyzer_wait_data(sdi->usb->devhdl);
639
9c939c51
BV
640 sr_info("Stop address = 0x%x", analyzer_get_stop_address(sdi->usb->devhdl));
641 sr_info("Now address = 0x%x", analyzer_get_now_address(sdi->usb->devhdl));
642 sr_info("Trigger address = 0x%x", analyzer_get_trigger_address(sdi->usb->devhdl));
a1bb33af 643
5a2326a7 644 packet.type = SR_DF_HEADER;
9c939c51 645 packet.payload = &header;
a1bb33af
UH
646 header.feed_version = 1;
647 gettimeofday(&header.starttime, NULL);
bf43ea23
UH
648 header.samplerate = zp->cur_samplerate;
649 header.num_logic_probes = zp->num_channels;
c2616fb9 650 header.num_analog_probes = 0;
9c939c51 651 sr_session_bus(session_data, &packet);
a1bb33af 652
b53738ba 653 if (!(buf = g_try_malloc(PACKET_SIZE))) {
bf43ea23 654 sr_err("zp: %s: buf malloc failed", __func__);
b53738ba
UH
655 return SR_ERR_MALLOC;
656 }
657
9c939c51 658 samples_read = 0;
a1bb33af 659 analyzer_read_start(sdi->usb->devhdl);
fed16f06 660 /* Send the incoming transfer to the session bus. */
bf43ea23 661 for (packet_num = 0; packet_num < (zp->memory_size * 4 / PACKET_SIZE);
fed16f06 662 packet_num++) {
a1bb33af 663 res = analyzer_read_data(sdi->usb->devhdl, buf, PACKET_SIZE);
b08024a8
UH
664 sr_info("Tried to read %llx bytes, actually read %x bytes",
665 PACKET_SIZE, res);
a1bb33af 666
5a2326a7 667 packet.type = SR_DF_LOGIC;
bf43ea23
UH
668 packet.timeoffset = samples_read * zp->period_ps;
669 packet.duration = res / 4 * zp->period_ps;
9c939c51
BV
670 packet.payload = &logic;
671 logic.length = PACKET_SIZE;
672 logic.unitsize = 4;
673 logic.data = buf;
674 sr_session_bus(session_data, &packet);
675 samples_read += res / 4;
a1bb33af
UH
676 }
677 analyzer_read_stop(sdi->usb->devhdl);
678 g_free(buf);
679
5a2326a7 680 packet.type = SR_DF_END;
9c939c51 681 sr_session_bus(session_data, &packet);
a1bb33af 682
e46b8fb1 683 return SR_OK;
a1bb33af
UH
684}
685
fed16f06 686/* This stops acquisition on ALL devices, ignoring device_index. */
a1bb33af
UH
687static void hw_stop_acquisition(int device_index, gpointer session_device_id)
688{
b9c735a2 689 struct sr_datafeed_packet packet;
a00ba012 690 struct sr_device_instance *sdi;
a1bb33af 691
5a2326a7 692 packet.type = SR_DF_END;
8a2efef2 693 sr_session_bus(session_device_id, &packet);
a1bb33af 694
d32d961d 695 if (!(sdi = sr_get_device_instance(device_instances, device_index)))
fed16f06 696 return; /* TODO: Cry? */
a1bb33af
UH
697
698 analyzer_reset(sdi->usb->devhdl);
fed16f06 699 /* TODO: Need to cancel and free any queued up transfers. */
a1bb33af
UH
700}
701
5c2d46d1 702struct sr_device_plugin zeroplus_logic_cube_plugin_info = {
e519ba86
UH
703 .name = "zeroplus-logic-cube",
704 .longname = "Zeroplus Logic Cube LAP-C series",
705 .api_version = 1,
706 .init = hw_init,
707 .cleanup = hw_cleanup,
86f5e3d8
UH
708 .opendev = hw_opendev,
709 .closedev = hw_closedev,
e519ba86
UH
710 .get_device_info = hw_get_device_info,
711 .get_status = hw_get_status,
712 .get_capabilities = hw_get_capabilities,
713 .set_configuration = hw_set_configuration,
714 .start_acquisition = hw_start_acquisition,
715 .stop_acquisition = hw_stop_acquisition,
a1bb33af 716};