aboutsummaryrefslogtreecommitdiff
path: root/lib/chibios-contrib/testhal/common/onewire/synth_searchrom.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/chibios-contrib/testhal/common/onewire/synth_searchrom.c')
-rw-r--r--lib/chibios-contrib/testhal/common/onewire/synth_searchrom.c370
1 files changed, 370 insertions, 0 deletions
diff --git a/lib/chibios-contrib/testhal/common/onewire/synth_searchrom.c b/lib/chibios-contrib/testhal/common/onewire/synth_searchrom.c
new file mode 100644
index 000000000..53d4a3084
--- /dev/null
+++ b/lib/chibios-contrib/testhal/common/onewire/synth_searchrom.c
@@ -0,0 +1,370 @@
1/*
2 ChibiOS/RT - Copyright (C) 2014 Uladzimir Pylinsky aka barthess
3
4 Licensed under the Apache License, Version 2.0 (the "License");
5 you may not use this file except in compliance with the License.
6 You may obtain a copy of the License at
7
8 http://www.apache.org/licenses/LICENSE-2.0
9
10 Unless required by applicable law or agreed to in writing, software
11 distributed under the License is distributed on an "AS IS" BASIS,
12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 See the License for the specific language governing permissions and
14 limitations under the License.
15*/
16
17#include <stdlib.h>
18
19/*
20 ******************************************************************************
21 * DEFINES
22 ******************************************************************************
23 */
24
25/* do not set it more than 64 because of some fill_pattern functions
26 will be broken.*/
27#define SYNTH_DEVICES_MAX 64
28
29/*
30 * synthetic device
31 */
32typedef struct {
33 bool active;
34 uint64_t id;
35} OWSynthDevice;
36
37/*
38 * synthetic bus
39 */
40typedef struct {
41 OWSynthDevice devices[SYNTH_DEVICES_MAX];
42 size_t dev_present;
43 bool complement_bit;
44 ioline_t rom_bit;
45} OWSynthBus;
46
47/*
48 ******************************************************************************
49 * EXTERNS
50 ******************************************************************************
51 */
52
53/*
54 ******************************************************************************
55 * PROTOTYPES
56 ******************************************************************************
57 */
58
59/*
60 ******************************************************************************
61 * GLOBAL VARIABLES
62 ******************************************************************************
63 */
64
65static OWSynthBus synth_bus;
66
67/*
68 * local buffer for discovered ROMs
69 */
70static uint64_t detected_devices[SYNTH_DEVICES_MAX];
71
72/*
73 ******************************************************************************
74 ******************************************************************************
75 * LOCAL FUNCTIONS
76 ******************************************************************************
77 ******************************************************************************
78 */
79
80/*
81 ******************************************************************************
82 * EXPORTED FUNCTIONS
83 ******************************************************************************
84 */
85
86/*
87 *
88 */
89void _synth_ow_write_bit(onewireDriver *owp, ioline_t bit) {
90 (void)owp;
91 size_t i;
92
93 for (i=0; i<SYNTH_DEVICES_MAX; i++) {
94 if (((synth_bus.devices[i].id >> synth_bus.rom_bit) & 1U) != bit) {
95 synth_bus.devices[i].active = false;
96 }
97 }
98 synth_bus.rom_bit++;
99}
100
101/*
102 *
103 */
104ioline_t _synth_ow_read_bit(void) {
105 ioline_t ret = 0xFF;
106 size_t i;
107 ioline_t bit;
108
109 for (i=0; i<SYNTH_DEVICES_MAX; i++) {
110 if (synth_bus.devices[i].active){
111 bit = (synth_bus.devices[i].id >> synth_bus.rom_bit) & 1U;
112 if (synth_bus.complement_bit){
113 bit ^= 1U;
114 }
115 if (0xFF == ret)
116 ret = bit;
117 else
118 ret &= bit;
119 }
120 }
121 synth_bus.complement_bit = !synth_bus.complement_bit;
122 return ret;
123}
124
125/*
126 *
127 */
128static void synth_reset_pulse(void){
129 size_t i;
130
131 for (i=0; i<synth_bus.dev_present; i++){
132 synth_bus.devices[i].active = true;
133 }
134}
135
136/*
137 *
138 */
139static size_t synth_search_rom(onewireDriver *owp, uint8_t *result, size_t max_rom_cnt) {
140
141 size_t i;
142
143 search_clean_start(&owp->search_rom);
144
145 do {
146 /* initialize buffer to store result */
147 if (owp->search_rom.reg.devices_found >= max_rom_cnt)
148 owp->search_rom.retbuf = result + 8*(max_rom_cnt-1);
149 else
150 owp->search_rom.retbuf = result + 8*owp->search_rom.reg.devices_found;
151 memset(owp->search_rom.retbuf, 0, 8);
152
153 /* clean iteration state */
154 search_clean_iteration(&owp->search_rom);
155
156 /**/
157 synth_reset_pulse();
158 synth_bus.rom_bit = 0;
159 synth_bus.complement_bit = false;
160 for (i=0; i<64*3 - 1; i++){
161 ow_search_rom_cb(NULL, owp);
162 }
163
164 if (ONEWIRE_SEARCH_ROM_ERROR != owp->search_rom.reg.result) {
165 /* store cached result for usage in next iteration */
166 memcpy(owp->search_rom.prev_path, owp->search_rom.retbuf, 8);
167 }
168 }
169 while (ONEWIRE_SEARCH_ROM_SUCCESS == owp->search_rom.reg.result);
170
171 /**/
172 if (ONEWIRE_SEARCH_ROM_ERROR == owp->search_rom.reg.result)
173 return 0;
174 else
175 return owp->search_rom.reg.devices_found;
176}
177
178/*
179 *
180 */
181static void fill_pattern_real_devices(void) {
182 size_t i;
183
184 for (i=0; i<SYNTH_DEVICES_MAX; i++)
185 synth_bus.devices[i].active = false;
186
187 synth_bus.devices[0].active = true;
188 synth_bus.devices[0].id = 0x1d00000567f5ec28;
189
190 synth_bus.devices[1].active = true;
191 synth_bus.devices[1].id = 0x37000005601abd28;
192
193 synth_bus.devices[2].active = true;
194 synth_bus.devices[2].id = 0x0f000005677d8328;
195}
196
197/*
198 *
199 */
200static void fill_pattern_00(size_t devices, size_t start) {
201 size_t i;
202
203 for (i=0; i<SYNTH_DEVICES_MAX; i++)
204 synth_bus.devices[i].active = false;
205
206 for (i=0; i<devices; i++){
207 synth_bus.devices[i].active = true;
208 synth_bus.devices[i].id = (start + i);
209 }
210}
211
212/*
213 *
214 */
215static void fill_pattern_01(size_t devices) {
216 size_t i;
217
218 for (i=0; i<SYNTH_DEVICES_MAX; i++)
219 synth_bus.devices[i].active = false;
220
221 for (i=0; i<devices; i++){
222 synth_bus.devices[i].active = true;
223 synth_bus.devices[i].id = (devices - i);
224 }
225}
226
227/*
228 *
229 */
230static void fill_pattern_02(size_t devices) {
231 size_t i;
232
233 for (i=0; i<SYNTH_DEVICES_MAX; i++)
234 synth_bus.devices[i].active = false;
235
236 for (i=0; i<devices; i++){
237 synth_bus.devices[i].active = true;
238 synth_bus.devices[i].id = ((uint64_t)1 << i);
239 }
240}
241
242/*
243 *
244 */
245static void fill_pattern_03(size_t devices) {
246 size_t i;
247
248 for (i=0; i<SYNTH_DEVICES_MAX; i++)
249 synth_bus.devices[i].active = false;
250
251 for (i=0; i<devices; i++){
252 synth_bus.devices[i].active = true;
253 synth_bus.devices[i].id = ((uint64_t)0x8000000000000000 >> i);
254 }
255}
256
257/*
258 * Random pattern helper
259 */
260static bool is_id_uniq(const OWSynthDevice *dev, size_t n, uint64_t id) {
261 size_t i;
262
263 for (i=0; i<n; i++) {
264 if (dev[i].id == id)
265 return false;
266 }
267 return true;
268}
269
270/*
271 *
272 */
273static void fill_pattern_rand(size_t devices) {
274 size_t i;
275 uint64_t new_id;
276
277 for (i=0; i<SYNTH_DEVICES_MAX; i++){
278 synth_bus.devices[i].active = false;
279 synth_bus.devices[i].id = 0;
280 }
281
282 for (i=0; i<devices; i++) {
283 do {
284 new_id = rand();
285 new_id = (new_id << 32) | rand();
286 } while (true != is_id_uniq(synth_bus.devices, i, new_id));
287
288 synth_bus.devices[i].id = new_id;
289 synth_bus.devices[i].active = true;
290 }
291}
292
293/*
294 *
295 */
296static bool check_result(size_t detected) {
297
298 size_t i,j;
299 bool match = false;
300
301 for (i=0; i<detected; i++){
302 match = false;
303 for (j=0; j<detected; j++){
304 if (synth_bus.devices[i].id == detected_devices[j]){
305 match = true;
306 break;
307 }
308 }
309 if (false == match)
310 return OSAL_FAILED;
311 }
312 return OSAL_SUCCESS;
313}
314
315/*
316 *
317 */
318void synthSearchRomTest(onewireDriver *owp) {
319
320 size_t detected = 0;
321 size_t i;
322
323 synth_bus.dev_present = 3;
324 fill_pattern_real_devices();
325 detected = synth_search_rom(owp, (uint8_t *)detected_devices, SYNTH_DEVICES_MAX);
326 osalDbgCheck(synth_bus.dev_present == detected);
327 osalDbgCheck(OSAL_SUCCESS == check_result(detected));
328
329 for (i=1; i<=SYNTH_DEVICES_MAX; i++){
330 synth_bus.dev_present = i;
331
332 fill_pattern_00(synth_bus.dev_present, 0);
333 detected = synth_search_rom(owp, (uint8_t *)detected_devices, SYNTH_DEVICES_MAX);
334 osalDbgCheck(synth_bus.dev_present == detected);
335 osalDbgCheck(OSAL_SUCCESS == check_result(detected));
336
337 fill_pattern_00(synth_bus.dev_present, 1);
338 detected = synth_search_rom(owp, (uint8_t *)detected_devices, SYNTH_DEVICES_MAX);
339 osalDbgCheck(synth_bus.dev_present == detected);
340 osalDbgCheck(OSAL_SUCCESS == check_result(detected));
341
342 fill_pattern_01(synth_bus.dev_present);
343 detected = synth_search_rom(owp, (uint8_t *)detected_devices, SYNTH_DEVICES_MAX);
344 osalDbgCheck(synth_bus.dev_present == detected);
345 osalDbgCheck(OSAL_SUCCESS == check_result(detected));
346
347 fill_pattern_02(synth_bus.dev_present);
348 detected = synth_search_rom(owp, (uint8_t *)detected_devices, SYNTH_DEVICES_MAX);
349 osalDbgCheck(synth_bus.dev_present == detected);
350 osalDbgCheck(OSAL_SUCCESS == check_result(detected));
351
352 fill_pattern_03(synth_bus.dev_present);
353 detected = synth_search_rom(owp, (uint8_t *)detected_devices, SYNTH_DEVICES_MAX);
354 osalDbgCheck(synth_bus.dev_present == detected);
355 osalDbgCheck(OSAL_SUCCESS == check_result(detected));
356 }
357
358 i = 0;
359 while (i < 1000) {
360 synth_bus.dev_present = 1 + (rand() & 63);
361
362 fill_pattern_rand(synth_bus.dev_present);
363 detected = synth_search_rom(owp, (uint8_t *)detected_devices, SYNTH_DEVICES_MAX);
364 osalDbgCheck(synth_bus.dev_present == detected);
365 osalDbgCheck(OSAL_SUCCESS == check_result(detected));
366 i++;
367 }
368}
369
370