]> sigrok.org Git - libsigrok.git/blob - tests/trigger.c
Build: Include <config.h> first in all source files
[libsigrok.git] / tests / trigger.c
1 /*
2  * This file is part of the libsigrok project.
3  *
4  * Copyright (C) 2014 Uwe Hermann <uwe@hermann-uwe.de>
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 2 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, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301 USA
19  */
20
21 #include <config.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <check.h>
25 #include <libsigrok/libsigrok.h>
26 #include "lib.h"
27
28 /* Test lots of triggers/stages/matches/channels */
29 #define NUM_TRIGGERS 70
30 #define NUM_STAGES 30
31 #define NUM_MATCHES 70
32 #define NUM_CHANNELS NUM_MATCHES
33
34 /* Check whether creating/freeing triggers with valid names works. */
35 START_TEST(test_trigger_new_free)
36 {
37         int i;
38         struct sr_trigger *t[NUM_TRIGGERS];
39         char name[10];
40
41         /* Create a few triggers with a valid name. */
42         for (i = 0; i < NUM_TRIGGERS; i++) {
43                 sprintf((char *)&name, "T%d", i);
44                 t[i] = sr_trigger_new((const char *)&name);
45                 fail_unless(t[i] != NULL);
46                 fail_unless(!strcmp(t[i]->name, (const char *)&name));
47                 fail_unless(t[i]->stages == NULL);
48         }
49
50         /* Free the triggers again (must not segfault). */
51         for (i = 0; i < NUM_TRIGGERS; i++)
52                 sr_trigger_free(t[i]);
53 }
54 END_TEST
55
56 /* Check whether creating/freeing triggers with NULL names works. */
57 START_TEST(test_trigger_new_free_null)
58 {
59         int i;
60         struct sr_trigger *t[NUM_TRIGGERS];
61
62         /* Create a few triggers with a NULL name (which is allowed). */
63         for (i = 0; i < NUM_TRIGGERS; i++) {
64                 t[i] = sr_trigger_new(NULL);
65                 fail_unless(t[i] != NULL);
66                 fail_unless(t[i]->name == NULL);
67                 fail_unless(t[i]->stages == NULL);
68         }
69
70         /* Free the triggers again (must not segfault). */
71         for (i = 0; i < NUM_TRIGGERS; i++)
72                 sr_trigger_free(t[i]);
73 }
74 END_TEST
75
76 /* Check whether sr_trigger_free(NULL) works without segfaulting. */
77 START_TEST(test_trigger_free_null)
78 {
79         sr_trigger_free(NULL);
80 }
81 END_TEST
82
83 /* Check whether creating/freeing triggers with stages works. */
84 START_TEST(test_trigger_stage_add)
85 {
86         int i, j;
87         struct sr_trigger *t[NUM_TRIGGERS];
88         struct sr_trigger_stage *s[NUM_STAGES];
89
90         /* Create a few triggers with a valid name. */
91         for (i = 0; i < NUM_TRIGGERS; i++) {
92                 t[i] = sr_trigger_new("T");
93
94                 /* Add a bunch of trigger stages to this trigger. */
95                 for (j = 0; j < NUM_STAGES; j++) {
96                         s[j] = sr_trigger_stage_add(t[i]);
97                         fail_unless(s[j] != NULL);
98                         fail_unless(t[i]->stages != NULL);
99                         fail_unless((int)g_slist_length(t[i]->stages) == (j + 1));
100                         fail_unless(s[j]->stage == j);
101                         fail_unless(s[j]->matches == NULL);
102                 }
103         }
104
105         /* Free the triggers again (must not segfault). */
106         for (i = 0; i < NUM_TRIGGERS; i++)
107                 sr_trigger_free(t[i]);
108 }
109 END_TEST
110
111 /* Check whether creating NULL trigger stages fails (as it should). */
112 START_TEST(test_trigger_stage_add_null)
113 {
114         /* Should not segfault, but rather return NULL. */
115         fail_unless(sr_trigger_stage_add(NULL) == NULL);
116 }
117 END_TEST
118
119 /* Check whether creating/freeing triggers with matches works. */
120 START_TEST(test_trigger_match_add)
121 {
122         int i, j, k, tm, ret;
123         struct sr_trigger *t[NUM_TRIGGERS];
124         struct sr_trigger_stage *s[NUM_STAGES];
125         struct sr_channel *chl[NUM_CHANNELS];
126         struct sr_channel *cha[NUM_CHANNELS];
127         char name[10];
128
129         /* Create a bunch of logic and analog channels. */
130         for (i = 0; i < NUM_CHANNELS; i++) {
131                 sprintf((char *)&name, "L%d", i);
132                 chl[i] = g_malloc0(sizeof(struct sr_channel));
133                 chl[i]->index = i;
134                 chl[i]->type = SR_CHANNEL_LOGIC;
135                 chl[i]->enabled = TRUE;
136                 chl[i]->name = g_strdup((const char *)&name);
137
138                 sprintf((char *)&name, "A%d", i);
139                 cha[i] = g_malloc0(sizeof(struct sr_channel));
140                 cha[i]->index = i;
141                 cha[i]->type = SR_CHANNEL_ANALOG;
142                 cha[i]->enabled = TRUE;
143                 cha[i]->name = g_strdup((const char *)&name);
144         }
145
146         /* Create a few triggers with a valid name. */
147         for (i = 0; i < NUM_TRIGGERS; i++) {
148                 t[i] = sr_trigger_new("T");
149
150                 /* Add a bunch of trigger stages to this trigger. */
151                 for (j = 0; j < NUM_STAGES; j++) {
152                         s[j] = sr_trigger_stage_add(t[i]);
153
154                         /* Add a bunch of matches to this stage. */
155                         for (k = 0; k < NUM_MATCHES; k++) {
156                                 /* Logic channel matches. */
157                                 tm = 1 + (k % 5); /* *_ZERO .. *_EDGE */
158                                 ret = sr_trigger_match_add(s[j], chl[k], tm, 0);
159                                 fail_unless(ret == SR_OK);
160
161                                 /* Analog channel matches. */
162                                 tm = 3 + (k % 4); /* *_RISING .. *_UNDER */
163                                 ret = sr_trigger_match_add(s[j], cha[k],
164                                         tm, ((rand() % 500) - 500) * 1.739);
165                                 fail_unless(ret == SR_OK);
166                         }
167                 }
168         }
169
170         /* Free the triggers again (must not segfault). */
171         for (i = 0; i < NUM_TRIGGERS; i++)
172                 sr_trigger_free(t[i]);
173
174         /* Free the channels. */
175         for (i = 0; i < NUM_CHANNELS; i++) {
176                 g_free(chl[i]->name);
177                 g_free(chl[i]);
178                 g_free(cha[i]->name);
179                 g_free(cha[i]);
180         }
181 }
182 END_TEST
183
184 /* Check whether trigger_match_add() copes well with incorrect input. */
185 START_TEST(test_trigger_match_add_bogus)
186 {
187         int ret;
188         struct sr_trigger *t;
189         struct sr_trigger_stage *s, *sl;
190         struct sr_channel *chl, *cha;
191
192         t = sr_trigger_new("T");
193         s = sr_trigger_stage_add(t);
194         chl = g_malloc0(sizeof(struct sr_channel));
195         chl->index = 0;
196         chl->type = SR_CHANNEL_LOGIC;
197         chl->enabled = TRUE;
198         chl->name = g_strdup("L0");
199         cha = g_malloc0(sizeof(struct sr_channel));
200         cha->index = 1;
201         cha->type = SR_CHANNEL_ANALOG;
202         cha->enabled = TRUE;
203         cha->name = g_strdup("A0");
204
205         /* Initially we have no matches at all. */
206         sl = t->stages->data;
207         fail_unless(g_slist_length(sl->matches) == 0);
208
209         /* NULL stage */
210         ret = sr_trigger_match_add(NULL, chl, SR_TRIGGER_ZERO, 0);
211         fail_unless(ret == SR_ERR_ARG);
212         fail_unless(g_slist_length(sl->matches) == 0);
213
214         /* NULL channel */
215         ret = sr_trigger_match_add(s, NULL, SR_TRIGGER_ZERO, 0);
216         fail_unless(ret == SR_ERR_ARG);
217         fail_unless(g_slist_length(sl->matches) == 0);
218
219         /* Invalid trigger matches for logic channels. */
220         ret = sr_trigger_match_add(s, chl, SR_TRIGGER_OVER, 0);
221         fail_unless(ret == SR_ERR_ARG);
222         fail_unless(g_slist_length(sl->matches) == 0);
223         ret = sr_trigger_match_add(s, chl, SR_TRIGGER_UNDER, 0);
224         fail_unless(ret == SR_ERR_ARG);
225         fail_unless(g_slist_length(sl->matches) == 0);
226
227         /* Invalid trigger matches for analog channels. */
228         ret = sr_trigger_match_add(s, cha, SR_TRIGGER_ZERO, 9.4);
229         fail_unless(ret == SR_ERR_ARG);
230         fail_unless(g_slist_length(sl->matches) == 0);
231         ret = sr_trigger_match_add(s, cha, SR_TRIGGER_ONE, -9.4);
232         fail_unless(ret == SR_ERR_ARG);
233         fail_unless(g_slist_length(sl->matches) == 0);
234
235         /* Invalid channel type. */
236         chl->type = -1;
237         ret = sr_trigger_match_add(s, chl, SR_TRIGGER_ZERO, 0);
238         fail_unless(ret == SR_ERR_ARG);
239         fail_unless(g_slist_length(sl->matches) == 0);
240         chl->type = 270;
241         ret = sr_trigger_match_add(s, chl, SR_TRIGGER_ZERO, 0);
242         fail_unless(ret == SR_ERR_ARG);
243         fail_unless(g_slist_length(sl->matches) == 0);
244
245         sr_trigger_free(t);
246         g_free(chl->name);
247         g_free(chl);
248         g_free(cha->name);
249         g_free(cha);
250 }
251 END_TEST
252
253 Suite *suite_trigger(void)
254 {
255         Suite *s;
256         TCase *tc;
257
258         s = suite_create("trigger");
259
260         tc = tcase_create("new_free");
261         tcase_add_checked_fixture(tc, srtest_setup, srtest_teardown);
262         tcase_add_test(tc, test_trigger_new_free);
263         tcase_add_test(tc, test_trigger_new_free_null);
264         tcase_add_test(tc, test_trigger_free_null);
265         suite_add_tcase(s, tc);
266
267         tc = tcase_create("stage");
268         tcase_add_checked_fixture(tc, srtest_setup, srtest_teardown);
269         tcase_add_test(tc, test_trigger_stage_add);
270         tcase_add_test(tc, test_trigger_stage_add_null);
271         suite_add_tcase(s, tc);
272
273         tc = tcase_create("match");
274         tcase_set_timeout(tc, 0);
275         tcase_add_checked_fixture(tc, srtest_setup, srtest_teardown);
276         tcase_add_test(tc, test_trigger_match_add);
277         tcase_add_test(tc, test_trigger_match_add_bogus);
278         suite_add_tcase(s, tc);
279
280         return s;
281 }