]> rtime.felk.cvut.cz Git - fpga/lx-cpu1/lx-rocon.git/commitdiff
Optimize PXMCC firmware to use only 32-bit types and change mode selection back.
authorPavel Pisa <ppisa@pikron.com>
Sun, 4 Jan 2015 09:20:50 +0000 (10:20 +0100)
committerPavel Pisa <ppisa@pikron.com>
Sun, 4 Jan 2015 09:20:50 +0000 (10:20 +0100)
Gain 5% time reduction by integration of multiplication
of array indexes by element size into index computation
expressions.

Signed-off-by: Pavel Pisa <ppisa@pikron.com>
hw/lx-rocon_firmware/firmware.c
hw/lx-rocon_firmware/pxmcc_types.h
sw/app/rocon/appl_tests.c

index 82de62647094662835756e39651d714a25505883..2e1822dc99afe3a84636190e1e7ef2a4023255fc 100644 (file)
@@ -33,6 +33,9 @@
 /* 1 / (2 * k3) * 65536 */
 #define RECI16_2_K3  37837
 
+#define offsbychar(_ptr, _offs) \
+   ((typeof(&(_ptr)[0]))((char*)(_ptr) + (_offs)))
+
 pxmcc_data_t pxmcc_data;
 
 void init_defvals(void)
@@ -79,20 +82,24 @@ void main(void)
   uint32_t last_rx_done_sqn = 0;
   pxmcc_axis_data_t *pxmcc;
 
-  pxmcc_data.common.fwversion = PXMCC_FWVERSION;
   pxmcc_data.common.pwm_cycle = 2500;
   pxmcc_data.common.min_idle = 0x7fff;
-  pxmcc = pxmcc_data.axis;
-  pxmcc->ccflg = 0;
-  pxmcc->ptindx = 0;
-  /*pxmcc->ptofs = *FPGA_IRC0;*/
-  pxmcc->ptirc = 1000;
-  pxmcc->ptreci = 4294967; /* (1LL<<32)*ptper/ptirc */
-  pxmcc->pwm_dq = 0;
   pxmcc_data.curadc[0].siroladc_offs = 0x0c17;
   pxmcc_data.curadc[1].siroladc_offs = 0x0c66;
   pxmcc_data.curadc[2].siroladc_offs = 0x0c66;
 
+  pxmcc = pxmcc_data.axis;
+  do {
+    pxmcc->ccflg  = 0;
+    pxmcc->mode   = 1;
+    pxmcc->ptirc  = 1000;
+    pxmcc->ptreci = 4294967; /* (1LL<<32)*ptper/ptirc */
+    pxmcc->pwm_dq = 0;
+    pxmcc++;
+  } while(pxmcc != pxmcc_data.axis + PXMCC_AXIS_COUNT);
+
+  asm volatile("": : : "memory");
+  pxmcc_data.common.fwversion = PXMCC_FWVERSION;
   asm volatile("": : : "memory");
 
  #if 0
@@ -155,7 +162,7 @@ void main(void)
         pwm_alp = pwm_d * pxmcc->ptcos - pwm_q * pxmcc->ptsin;
         pwm_bet = pwm_d * pxmcc->ptsin + pwm_q * pxmcc->ptcos;
 
-        if (pxmcc->mode) {
+        if (!pxmcc->mode) {
           pwm_bet_div_2_k3 = RECI16_2_K3 * (pwm_bet >> 16);
 
          #ifndef SUPPRESS_CONDITIONALS
@@ -296,7 +303,7 @@ void main(void)
           *uptr = pwm4 | 0x4000;
         }
       } else {
-        if (pxmcc->mode) {
+        if (!pxmcc->mode) {
           pwmtx_info = pxmcc->pwmtx_info;
           uptr = FPGA_LX_MASTER_TX + ((pwmtx_info >>  0) & 0xff);
           pxmcc->pwm_prew[1] = *uptr & 0x3fff;
@@ -343,13 +350,13 @@ void main(void)
       int i;
       pxmcc_curadc_data_t *curadc = pxmcc_data.curadc;
       volatile uint32_t *siroladc = FPGA_LX_MASTER_RX_ADC0;
-      uint16_t val;
+      uint32_t val;
 
       for (i = 0; i < PXMCC_CURADC_CHANNELS; ) {
         val = *siroladc;
 
-        curadc->cur_val = (int16_t)(val - curadc->siroladc_last
-                                        - curadc->siroladc_offs);
+        curadc->cur_val = (uint16_t)(val - curadc->siroladc_last) -
+                          curadc->siroladc_offs;
         curadc->siroladc_last = val;
 
         i++;
@@ -385,7 +392,7 @@ void main(void)
      #endif /*COMPUTE_PHASE_SECTOR*/
 
       out_info = pxmcc->out_info;
-      if (pxmcc->mode) {
+      if (!pxmcc->mode) {
 
         pwm1 = pxmcc->pwm_prew[0];
         pwm2 = pxmcc->pwm_prew[1];
@@ -457,10 +464,18 @@ void main(void)
           uint32_t u2gtu3 = (int32_t)(pwm3 - pwm2) >> 31;
           uint32_t state50_msk = u1gtu2 & u1gtu3;
           uint32_t pwm_reci_bits;
+          uint32_t sz4idx = sizeof(*pxmcc->pwm_prew);
+          uint32_t sz4cur = sizeof(*pxmcc_data.curadc);
+          uint32_t curmult_idx2curadc;
 
+         #if 0
           curmult_idx = (((u1gtu3 ^ u1gtu2) | 1) ^ u2gtu3 ^ u1gtu2) & 3;
-
           pwm_reci = pxmcc_data.common.pwm_cycle - pxmcc->pwm_prew[curmult_idx];
+         #else
+          /* Variant where curmult_idx is directly computed as byte offset to uint32_t array */
+          curmult_idx = (((u1gtu3 ^ u1gtu2) | (1 * sz4idx)) ^ u2gtu3 ^ u1gtu2) & (3 * sz4idx);
+          pwm_reci = pxmcc_data.common.pwm_cycle - *offsbychar(pxmcc->pwm_prew, curmult_idx);
+         #endif
 
          #if 0
           pwm_reci_bits = __builtin_clzl(pwm_reci);
@@ -485,8 +500,17 @@ void main(void)
            * so it is destructive and has not to be applied twice,
            * but it is much better optimized
            */
+         #if 0
           curmult_idx = (0x102 >> (curmult_idx * 4)) & 3;
           pcurmult = &pxmcc_data.curadc[out_info + curmult_idx].cur_val;
+         #else
+          curmult_idx2curadc = ((2 * sz4cur) << (0 * sz4idx)) |
+                               ((0 * sz4cur) << (1 * sz4idx)) |
+                               ((1 * sz4cur) << (2 * sz4idx));
+          curmult_idx = (curmult_idx2curadc >> curmult_idx) & (sz4cur | (sz4cur << 1));
+          pcurmult = &pxmcc_data.curadc[out_info].cur_val;
+          pcurmult = offsbychar(pcurmult, curmult_idx);
+         #endif
           *pcurmult = (int32_t)(pwm_reci * (*pcurmult)) >> 16;
 
           cur2 = pxmcc_data.curadc[out_info + 0].cur_val;
index 33be1681ee1872d44eb03e8f73fb776d0aa0ab96..284e8da6eaba0d1e6d3a97d4b423b48859e56c9e 100644 (file)
@@ -47,13 +47,13 @@ typedef struct pxmcc_axis_data_t {
   uint32_t  inp_info;  /* which irc to use */
   uint32_t  out_info;  /* output index */
   uint32_t  pwmtx_info;        /* offsets of pwm1 .. pwm4 from FPGA_LX_MASTER_TX */
-  uint16_t  pwm_prew[4];
+  uint32_t  pwm_prew[4];
 } pxmcc_axis_data_t;
 
 typedef struct pxmcc_curadc_data_t {
   int32_t   cur_val;
-  uint16_t  siroladc_offs;
-  uint16_t  siroladc_last;
+  int32_t   siroladc_offs;
+  uint32_t  siroladc_last;
 } pxmcc_curadc_data_t;
 
 typedef struct pxmcc_data_t {
index 71af788eaa2c5df06f82dbd7a796447125069c82..b7686d89337c16f5e12469b38918d48b16887c81 100644 (file)
@@ -433,7 +433,7 @@ int cmd_do_testtumblefw(cmd_io_t *cmd_io, const struct cmd_des *des, char *param
 
   pwmtx_info = (9 << 0) | (10 << 8) | (11 << 16);
 
-  mcc_axis->mode = 1;
+  mcc_axis->mode = 0;
 
   mcc_axis->inp_info = mcs->pxms_inp_info;
   mcc_axis->out_info = mcs->pxms_out_info;
@@ -454,17 +454,17 @@ int cmd_do_testtumblefw(cmd_io_t *cmd_io, const struct cmd_des *des, char *param
     mcc_data->axis[1].inp_info = 1;
     mcc_data->axis[1].out_info = 3;
     mcc_data->axis[1].pwmtx_info = (12 << 0) | (13 << 8) | (14 << 16);
-    mcc_data->axis[1].mode = 1;
+    mcc_data->axis[1].mode = 0;
     mcc_data->axis[1].ccflg = 1;
     mcc_data->axis[2].inp_info = 2;
     mcc_data->axis[2].out_info = 6;
     mcc_data->axis[2].pwmtx_info = (15 << 0) | (16 << 8) | (18 << 16);
-    mcc_data->axis[2].mode = 1;
+    mcc_data->axis[2].mode = 0;
     mcc_data->axis[2].ccflg = 1;
     mcc_data->axis[3].inp_info = 3;
     mcc_data->axis[3].out_info = 9;
     mcc_data->axis[3].pwmtx_info = (19 << 0) | (20 << 8) | (21 << 16);
-    mcc_data->axis[3].mode = 1;
+    mcc_data->axis[3].mode = 0;
     mcc_data->axis[3].ccflg = 1;
   }