]> rtime.felk.cvut.cz Git - fpga/lx-cpu1/lx-rocon.git/blob - sw/app/rocon/appl_tests.c
a46987b1aeff53458b9cb836be2a2df4e9aaf5fb
[fpga/lx-cpu1/lx-rocon.git] / sw / app / rocon / appl_tests.c
1 #include <system_def.h>
2 #include <stdio.h>
3 #include <unistd.h>
4 #include <string.h>
5 #include <ctype.h>
6 #include <stddef.h>
7 #include <malloc.h>
8 #include <utils.h>
9 #include <cmd_proc.h>
10 #include <hal_gpio.h>
11 #include <hal_machperiph.h>
12 #include <LPC17xx.h>
13 #include <lpcTIM.h>
14 #include <spi_drv.h>
15 #include <pxmc.h>
16 #include <inttypes.h>
17
18 #include <ul_log.h>
19 #include <ul_logreg.h>
20
21 #include "appl_defs.h"
22 #include "appl_fpga.h"
23
24 int cmd_do_test_memusage(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
25 {
26   void *maxaddr;
27   char str[40];
28
29   maxaddr = sbrk(0);
30
31   snprintf(str, sizeof(str), "memusage maxaddr 0x%08lx\n", (unsigned long)maxaddr);
32   cmd_io_write(cmd_io, str, strlen(str));
33
34   return 0;
35 }
36
37 int cmd_do_test_adc(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
38 {
39   printf("ADC: %ld %ld %ld %ld %ld\n", (LPC_ADC->DR[0] & 0xFFF0) >> 4,
40          (LPC_ADC->DR[1] & 0xFFF0) >> 4,
41          (LPC_ADC->DR[2] & 0xFFF0) >> 4,
42          (LPC_ADC->DR[3] & 0xFFF0) >> 4,
43          (LPC_ADC->DR[7] & 0xFFF0) >> 4);
44   return 0;
45 }
46
47 #ifdef APPL_WITH_DISTORE_EEPROM_USER
48 int cmd_do_test_distore(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
49 {
50   appl_distore_user_set_check4change();
51   return 0;
52 }
53
54 int cmd_do_test_diload(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
55 {
56   appl_distore_user_restore();
57   return 0;
58 }
59 #endif /*APPL_WITH_DISTORE_EEPROM_USER*/
60
61 int cmd_do_test_loglevel_cb(ul_log_domain_t *domain, void *context)
62 {
63   char s[30];
64   cmd_io_t *cmd_io = (cmd_io_t *)context;
65
66   s[sizeof(s) - 1] = 0;
67   snprintf(s, sizeof(s) - 1, "%s (%d)\n\r", domain->name, domain->level);
68   cmd_io_puts(cmd_io, s);
69   return 0;
70 }
71
72 int cmd_do_test_loglevel(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
73 {
74   int res = 0;
75   char *line;
76   line = param[1];
77
78   if (!line || (si_skspace(&line), !*line))
79   {
80     ul_logreg_for_each_domain(cmd_do_test_loglevel_cb, cmd_io);
81   }
82   else
83   {
84     res = ul_log_domain_arg2levels(line);
85   }
86
87   return res >= 0 ? 0 : CMDERR_BADPAR;
88 }
89
90 int cmd_do_spimst_blocking(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
91 {
92   int res;
93   int opchar;
94   char *p = param[3];
95   int spi_chan = (int)(intptr_t)des->info[0];
96   uint8_t *tx_buff = NULL;
97   uint8_t *rx_buff = NULL;
98   long addr = 0;
99   int len = 0;
100   spi_drv_t *spi_drv;
101
102   if ((opchar = cmd_opchar_check(cmd_io, des, param)) < 0)
103     return opchar;
104
105   if (opchar != ':')
106     return -CMDERR_OPCHAR;
107
108   if (spi_chan == -1)
109     spi_chan = *param[1] - '0';
110
111   spi_drv = spi_find_drv(NULL, spi_chan);
112
113   if (spi_drv == NULL)
114     return -CMDERR_BADSUF;
115
116   p = param[3];
117
118   si_skspace(&p);
119
120   if (isdigit((int)*p))
121   {
122     if (si_long(&p, &addr, 16) < 0)
123       return -CMDERR_BADPAR;
124   }
125
126   if (si_fndsep(&p, "({") < 0)
127     return -CMDERR_BADSEP;
128
129   if ((res = si_add_to_arr(&p, (void **)&tx_buff, &len, 16, 1, "})")) < 0)
130     return -CMDERR_BADPAR;
131
132   rx_buff = malloc(len);
133
134   res = -1;
135
136   if (rx_buff != NULL)
137     res = spi_transfer(spi_drv, addr, len, tx_buff, rx_buff);
138
139   if (res < 0)
140   {
141     printf("SPI! %02lX ERROR\n", addr);
142   }
143   else
144   {
145     int i;
146     printf("SPI! %02lX ", addr);
147     printf("TX(");
148
149     for (i = 0; i < len; i++)
150       printf("%s%02X", i ? "," : "", tx_buff[i]);
151
152     printf(") RX(");
153
154     for (i = 0; i < len; i++)
155       printf("%s%02X", i ? "," : "", rx_buff[i]);
156
157     printf(")");
158     printf("\n");
159     return 0;
160   }
161
162   if (rx_buff)
163     free(rx_buff);
164
165   if (tx_buff)
166     free(tx_buff);
167
168   return 0;
169 }
170
171 #ifdef SDRAM_BASE
172 int sdram_access_test(void)
173 {
174   unsigned int *ptr;
175   unsigned int pattern;
176   size_t ramsz = SDRAM_SIZE;
177   size_t cnt;
178   lt_mstime_t tic;
179   size_t blksz, i;
180
181   lt_mstime_update();
182   tic = actual_msec;
183
184   pattern = 0x12abcdef;
185
186   for (cnt = ramsz / sizeof(*ptr), ptr = (typeof(ptr))SDRAM_BASE; cnt--;)
187   {
188     *(ptr++) = pattern;
189     pattern = pattern + 0x87654321;
190   }
191
192   lt_mstime_update();
193   printf("SDRAM write %d ms\n", (int)(lt_msdiff_t)(actual_msec - tic));
194
195   lt_mstime_update();
196   tic = actual_msec;
197
198   pattern = 0x12abcdef;
199
200   for (cnt = ramsz / sizeof(*ptr), ptr = (typeof(ptr))SDRAM_BASE; cnt--;)
201   {
202     if (*ptr != pattern)
203     {
204       printf("SDRAM error modify at %p (%08x)\n", ptr, *ptr ^ pattern);
205       return -1;
206     }
207
208     *(ptr++) = ~pattern;
209     pattern = pattern + 0x87654321;
210   }
211
212   lt_mstime_update();
213   printf("SDRAM modify %d ms\n", (int)(lt_msdiff_t)(actual_msec - tic));
214
215   lt_mstime_update();
216   tic = actual_msec;
217
218   pattern = 0x12abcdef;
219
220   for (cnt = ramsz / sizeof(*ptr), ptr = (typeof(ptr))SDRAM_BASE; cnt--;)
221   {
222     if (*(ptr++) != ~pattern)
223     {
224       printf("SDRAM error read at %p (%08x)\n", ptr, *ptr ^ pattern);
225       return -1;
226     }
227
228     pattern = pattern + 0x87654321;
229   }
230
231   lt_mstime_update();
232   printf("SDRAM read %d ms\n", (int)(lt_msdiff_t)(actual_msec - tic));
233
234   lt_mstime_update();
235   tic = actual_msec;
236
237   pattern = 0;
238
239   for (cnt = ramsz / sizeof(*ptr), ptr = (typeof(ptr))SDRAM_BASE; cnt--;)
240   {
241     pattern += *(ptr++);
242   }
243
244   lt_mstime_update();
245   printf("SDRAM sum %d ms res 0x%08x\n", (int)(lt_msdiff_t)(actual_msec - tic), pattern);
246
247   for (blksz = 1; blksz < 256 ; blksz *= 2)
248   {
249     lt_mstime_update();
250     tic = actual_msec;
251
252     pattern = 0;
253
254     for (cnt = ramsz / sizeof(*ptr); cnt; cnt -= blksz)
255     {
256       ptr = (typeof(ptr))SDRAM_BASE;
257
258       //ptr = (typeof(ptr))cmd_do_test_memusage;
259       //ptr = (typeof(ptr))&ptr;
260       for (i = blksz; i--;)
261         pattern += *(ptr++);
262     }
263
264     lt_mstime_update();
265     printf("SDRAM sum %d blksz %d ms res 0x%08x\n", (int)(lt_msdiff_t)(actual_msec - tic), (int)blksz, pattern);
266   }
267
268   return 0;
269 }
270
271 int cmd_do_testsdram(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
272 {
273   sdram_access_test();
274   return 0;
275 }
276 #endif /*SDRAM_BASE*/
277
278 int cmd_do_testlxpwrrx(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
279 {
280   char *ps = param[1];
281   long mode = 0;
282   uint32_t *ptr;
283
284   if (ps != NULL) {
285     si_skspace(&ps);
286     if (*ps) {
287       if (si_ulong(&ps, &mode, 0) < 0)
288         return -CMDERR_BADPAR;
289     }
290   }
291   pxmc_rocon_rx_data_hist_buff = NULL;
292   pxmc_rocon_rx_data_hist_mode = mode;
293
294  #ifndef PXMC_ROCON_TIMED_BY_RX_DONE
295   pxmc_rocon_rx_done_isr_setup(pxmc_rocon_rx_done_isr);
296  #endif /*PXMC_ROCON_TIMED_BY_RX_DONE*/
297   pxmc_rocon_rx_data_hist_buff_end = (void *)(FPGA_CONFIGURATION_FILE_ADDRESS +
298                                          0x80000);
299   ptr = (void *)FPGA_CONFIGURATION_FILE_ADDRESS;
300   if (mode != 0) {
301     *(ptr++) = '10XL';
302     *(ptr++) = mode;
303   }
304   pxmc_rocon_rx_data_hist_buff = (void *)ptr;
305   return 0;
306 }
307
308 int cmd_do_testlxpwrstat(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
309 {
310   printf("lxpwrrx period %ld latency %ld max %ld\n",
311          (long)pxmc_rocon_rx_cycle_time, (long)pxmc_rocon_rx_irq_latency,
312          (long)pxmc_rocon_rx_irq_latency_max);
313   return 0;
314 }
315
316 #include <math.h>
317
318 int cmd_do_testfncapprox(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
319 {
320   char *ps = param[1];
321   unsigned long fnc;
322   unsigned long val;
323   unsigned long res;
324   long diff;
325   long diff_max = 0;
326   unsigned int  xb;
327   uint32_t x;
328   uint32_t xl;
329   double   xf;
330   int64_t  yl;
331   long count = 1;
332   long step = 1 << (30-7-18+1  +4);
333
334   si_skspace(&ps);
335   if (si_ulong(&ps, &fnc, 0) < 0)
336       return -CMDERR_BADPAR;
337
338   si_skspace(&ps);
339   if (!strcmp(ps, "all")) {
340     val = 0;
341     count = 0x80000000UL / step;
342     if (fnc == 1) {
343       val = 1;
344     }
345   } else {
346     if (si_ulong(&ps, &val, 0) < 0)
347         return -CMDERR_BADPAR;
348   }
349
350   for (; count--;  val += step) {
351
352     if (fnc == 1) {
353       x = val;
354       xb = __builtin_clz(x);
355       xl = x << xb;
356     } else {
357       xl = val;
358     }
359
360     fpga_fncapprox_base[fnc] = xl;
361
362     /* dummy read to provide time to function aproximator to proceed computation */
363     res = fpga_fncapprox_base[fnc];
364     res = fpga_fncapprox_base[fnc];
365
366     switch (fnc) {
367       case 0:
368         yl = xl;
369       case 1:
370         yl = (1LL << 62) / xl;
371         break;
372       case 2:
373         xf = (double)xl * M_PI / 2.0 / (1UL << 30);
374         yl = round(sin(xf) * (1UL << 16));
375         break;
376       case 3:
377         xf = (double)xl * M_PI / 2.0 / (1UL << 30);
378         yl = round(cos(xf) * (1UL << 16));
379         break;
380       default:
381       yl = 0;
382     }
383
384     diff = yl - res;
385
386     if ((diff > 0) && (diff > diff_max))
387       diff_max = diff;
388     else if ((diff < 0) && (-diff > diff_max))
389       diff_max = -diff;
390
391   }
392
393   val -= step;
394
395   printf("fnc=%ld val=0x%08lx res=0x%08lx ref=0x%08lx diff=%ld max %ld\n",
396          fnc, val, res, (unsigned long)yl, diff, diff_max);
397
398   return 0;
399 }
400
401 int cmd_do_testtumblefw(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
402 {
403   char *ps = param[1];
404   long pwm_d;
405   long pwm_q;
406   uint32_t ptofs;
407   uint32_t irc;
408   uint32_t ptirc;
409   uint32_t ptreci;
410   uint64_t ull;
411   pxmc_state_t *mcs = pxmc_main_list.pxml_arr[0];
412
413   fpga_tumbl_dmem[0] = 0;
414
415   si_skspace(&ps);
416   if (si_long(&ps, &pwm_d, 0) < 0)
417       return -CMDERR_BADPAR;
418
419   si_skspace(&ps);
420   if (si_ulong(&ps, &pwm_q, 0) < 0)
421         return -CMDERR_BADPAR;
422
423   irc = fpga_irc[0]->count;
424   ptofs = (int16_t)(mcs->pxms_ptofs - irc) + irc;
425
426   ptirc = mcs->pxms_ptirc;
427   ull = (1ULL << 32) * mcs->pxms_ptper;
428   ptreci = (ull + ptirc / 2) / ptirc;
429
430   fpga_tumbl_dmem[0] = 0;
431   fpga_tumbl_dmem[1] = (pwm_d << 16) | (pwm_q & 0xffff);
432
433   fpga_tumbl_dmem[4] = ptirc;
434   fpga_tumbl_dmem[5] = ptreci;
435   fpga_tumbl_dmem[6] = ptofs;
436
437   pxmc_clear_flags(mcs,PXMS_ENO_m|PXMS_ENG_m|PXMS_ENR_m|PXMS_BSY_m);
438
439   fpga_tumbl_dmem[0] = 1;
440
441   printf("spd %ld\n",mcs->pxms_as);
442
443   return 0;
444 }
445
446 #define CK_IRC_WORDS 16
447 #define CK_TX_WORDS  16
448 #define CK_RX_WORDS  16
449
450 #define CK_IRC_START ((uint32_t*)fpga_irc[0])
451 #define CK_TX_START  (fpga_lx_master_transmitter_base+9)
452 #define CK_RX_START  (fpga_lx_master_receiver_base+44)
453
454 typedef struct ck_state_t {
455   uint32_t ck_irc_base[CK_IRC_WORDS];
456   uint32_t ck_irc_read[CK_IRC_WORDS];
457   uint32_t ck_tx_base[CK_TX_WORDS];
458   uint32_t ck_tx_read[CK_TX_WORDS];
459   uint32_t ck_rx_base[CK_RX_WORDS];
460   uint32_t ck_rx_read[CK_RX_WORDS];
461
462   uint32_t ck_irc_err;
463   uint32_t ck_tx_err;
464   uint32_t ck_rx_err;
465 } ck_state_t;
466
467 int cmd_do_testtumblebus(cmd_io_t *cmd_io, const struct cmd_des *des, char *param[])
468 {
469   int i;
470   int cycles = 10000;
471   static ck_state_t *ckst = NULL;
472   if (ckst == NULL)
473     ckst = malloc(sizeof(*ckst));
474   if (ckst == NULL)
475     return 1;
476
477   ckst->ck_irc_err = 0;
478   ckst->ck_tx_err = 0;
479   ckst->ck_rx_err = 0;
480
481   for (i = 0; i < CK_IRC_WORDS; i++)
482     ckst->ck_irc_base[i] = CK_IRC_START[i];
483
484   for (i = 0; i < CK_TX_WORDS; i++)
485     ckst->ck_tx_base[i] = CK_TX_START[i];
486
487   for (i = 0; i < CK_RX_WORDS; i++)
488     ckst->ck_rx_base[i] = CK_RX_START[i];
489
490   while (cycles--) {
491     if (!ckst->ck_irc_err) {
492       for (i = 0; i < CK_IRC_WORDS; i++)
493         ckst->ck_irc_read[i] = CK_IRC_START[i];
494       for (i = 0; i < CK_IRC_WORDS; i++)
495         if (ckst->ck_irc_read[i] != ckst->ck_irc_base[i]) {
496           ckst->ck_irc_err++;
497           printf("irc+%x %08"PRIx32" != %08"PRIx32"\n",
498                  i, ckst->ck_irc_read[i], ckst->ck_irc_base[i]);
499         }
500     }
501
502     if (!ckst->ck_tx_err) {
503       for (i = 0; i < CK_TX_WORDS; i++)
504         ckst->ck_tx_read[i] = CK_TX_START[i];
505       for (i = 0; i < CK_TX_WORDS; i++)
506         if (ckst->ck_tx_read[i] != ckst->ck_tx_base[i]) {
507           ckst->ck_tx_err++;
508           printf("tx+%x %08"PRIx32" != %08"PRIx32"\n",
509                  i, ckst->ck_tx_read[i], ckst->ck_tx_base[i]);
510         }
511     }
512
513     if (!ckst->ck_rx_err) {
514       for (i = 0; i < CK_RX_WORDS; i++)
515         ckst->ck_rx_read[i] = CK_RX_START[i];
516       for (i = 0; i < CK_RX_WORDS; i++)
517         if (ckst->ck_rx_read[i] != ckst->ck_rx_base[i]) {
518           ckst->ck_rx_err++;
519           printf("rx+%x %08"PRIx32" != %08"PRIx32"\n",
520                  i, ckst->ck_rx_read[i], ckst->ck_rx_base[i]);
521         }
522     }
523   }
524
525   return 0;
526 }
527
528 cmd_des_t const cmd_des_test_memusage = {0, 0,
529                 "memusage", "report memory usage", cmd_do_test_memusage,
530 {
531   0,
532   0
533 }
534                                         };
535
536 cmd_des_t const cmd_des_test_adc = {0, 0,
537                                     "testadc", "adc test", cmd_do_test_adc,
538 {
539   0,
540   0
541 }
542                                    };
543
544 #ifdef APPL_WITH_DISTORE_EEPROM_USER
545 cmd_des_t const cmd_des_test_distore = {0, 0,
546                                         "testdistore", "test DINFO store", cmd_do_test_distore,
547 {
548   0,
549   0
550 }
551                                        };
552
553 cmd_des_t const cmd_des_test_diload = {0, 0,
554                                        "testdiload", "test DINFO load", cmd_do_test_diload,
555 {
556   0,
557   0
558 }
559                                       };
560 #endif /*APPL_WITH_DISTORE_EEPROM_USER*/
561
562 cmd_des_t const cmd_des_test_loglevel = {0, 0,
563                 "loglevel", "select logging level",
564                 cmd_do_test_loglevel, {}
565                                         };
566
567 cmd_des_t const cmd_des_spimst = {0, CDESM_OPCHR | CDESM_WR,
568                                   "SPIMST", "SPI master communication request",
569                                   cmd_do_spimst_blocking, {(void *)0}
570                                  };
571
572 cmd_des_t const cmd_des_spimstx = {0, CDESM_OPCHR | CDESM_WR,
573                                    "SPIMST#", "SPI# master communication request",
574                                    cmd_do_spimst_blocking, {(void *) - 1}
575                                   };
576
577 #ifdef SDRAM_BASE
578 cmd_des_t const cmd_des_testsdram = {0, 0,
579                                      "testsdram", "test SDRAM",
580                                      cmd_do_testsdram, {(void *)0}
581                                     };
582 #endif /*SDRAM_BASE*/
583
584
585 cmd_des_t const cmd_des_testlxpwrrx = {0, 0,
586                                      "testlxpwrrx", "capture data stream from lxpwr",
587                                      cmd_do_testlxpwrrx, {(void *)0}
588                                     };
589
590 cmd_des_t const cmd_des_testlxpwrstat = {0, 0,
591                                      "testlxpwrstat", "lxpwr interrupt statistic",
592                                      cmd_do_testlxpwrstat, {(void *)0}
593                                     };
594
595 cmd_des_t const cmd_des_testfncapprox = {0, 0,
596                                      "testfncapprox", "test of function approximator",
597                                      cmd_do_testfncapprox, {(void *)0}
598                                     };
599
600 cmd_des_t const cmd_des_testtumblefw = {0, 0,
601                                      "testtumblefw", "test Tumble coprocesor firmware",
602                                      cmd_do_testtumblefw, {(void *)0}
603                                     };
604
605 cmd_des_t const cmd_des_testtumblebus = {0, 0,
606                                      "testtumblebus", "test Tumble coprocesor bus",
607                                      cmd_do_testtumblebus, {(void *)0}
608                                     };
609
610
611 cmd_des_t const *const cmd_appl_tests[] =
612 {
613   &cmd_des_test_memusage,
614   &cmd_des_test_adc,
615 #ifdef APPL_WITH_DISTORE_EEPROM_USER
616   &cmd_des_test_distore,
617   &cmd_des_test_diload,
618 #endif /*APPL_WITH_DISTORE_EEPROM_USER*/
619   &cmd_des_test_loglevel,
620   &cmd_des_spimst,
621   &cmd_des_spimstx,
622 #ifdef SDRAM_BASE
623   &cmd_des_testsdram,
624 #endif /*SDRAM_BASE*/
625   &cmd_des_testlxpwrrx,
626   &cmd_des_testlxpwrstat,
627   &cmd_des_testfncapprox,
628   &cmd_des_testtumblefw,
629   &cmd_des_testtumblebus,
630   NULL
631 };