instaspin_foc
proj_lab11a.c
Go to the documentation of this file.
1 /* --COPYRIGHT--,BSD
2  * Copyright (c) 2015, Texas Instruments Incorporated
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  *
9  * * Redistributions of source code must retain the above copyright
10  * notice, this list of conditions and the following disclaimer.
11  *
12  * * Redistributions in binary form must reproduce the above copyright
13  * notice, this list of conditions and the following disclaimer in the
14  * documentation and/or other materials provided with the distribution.
15  *
16  * * Neither the name of Texas Instruments Incorporated nor the names of
17  * its contributors may be used to endorse or promote products derived
18  * from this software without specific prior written permission.
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
22  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
23  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
24  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
27  * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
28  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
29  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
30  * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  * --/COPYRIGHT--*/
36 
38 
39 
44 
45 // **************************************************************************
46 // the includes
47 
48 // system includes
49 #include <math.h>
50 #include "main.h"
51 
52 #ifdef FLASH
53 #pragma CODE_SECTION(mainISR,"ramfuncs");
54 #endif
55 
56 // Include header files used in the main function
57 
58 // **************************************************************************
59 // the defines
60 
61 // **************************************************************************
62 // the globals
63 
66 
69 
72 
74 
77 
80 uint16_t pidCntSpeed;
81 
84 
87 
90 
93 
96 
99 
100 #ifdef F2802xF
101 #pragma DATA_SECTION(halHandle,"rom_accessed_data");
102 #endif
104 
105 HAL_PwmData_t gPwmData = {_IQ(0.0), _IQ(0.0), _IQ(0.0)};
106 
108 
109 MATH_vec3 gOffsets_I_pu = {_IQ(0.0), _IQ(0.0), _IQ(0.0)};
110 
111 MATH_vec3 gOffsets_V_pu = {_IQ(0.0), _IQ(0.0), _IQ(0.0)};
112 
113 MATH_vec2 gIdq_ref_pu = {_IQ(0.0), _IQ(0.0)};
114 
115 MATH_vec2 gVdq_out_pu = {_IQ(0.0), _IQ(0.0)};
116 
117 MATH_vec2 gIdq_pu = {_IQ(0.0), _IQ(0.0)};
118 
119 #ifdef F2802xF
120 #pragma DATA_SECTION(gUserParams,"rom_accessed_data");
121 #endif
123 
125 
126 #ifdef FLASH
127 // Used for running BackGround in flash, and ISR in RAM
128 extern uint16_t *RamfuncsLoadStart, *RamfuncsLoadEnd, *RamfuncsRunStart;
129 
130 #ifdef F2802xF
131 extern uint16_t *econst_start, *econst_end, *econst_ram_load;
132 extern uint16_t *switch_start, *switch_end, *switch_ram_load;
133 #endif
134 
135 #endif
136 
137 // set the offset, default value of 1 microsecond
138 int16_t gCmpOffset = (int16_t)(1.0 * USER_SYSTEM_FREQ_MHz);
139 
140 MATH_vec3 gIavg = {_IQ(0.0), _IQ(0.0), _IQ(0.0)};
141 uint16_t gIavg_shift = 1;
142 
143 #ifdef DRV8301_SPI
144 // Watch window interface to the 8301 SPI
145 DRV_SPI_8301_Vars_t gDrvSpi8301Vars;
146 #endif
147 
148 #ifdef DRV8305_SPI
149 // Watch window interface to the 8305 SPI
150 DRV_SPI_8305_Vars_t gDrvSpi8305Vars;
151 #endif
152 
154 
156 
158 
160 
162 
164 
166 
170 
171 uint32_t gOffsetCalcCount = 0;
172 
173 volatile bool gFlag_enableRsOnLine = false;
174 
175 volatile bool gFlag_updateRs = false;
176 
177 volatile _iq gRsOnLineFreq_Hz = _IQ(0.2);
178 
179 volatile _iq gRsOnLineId_mag_A = _IQ(0.5);
180 
181 volatile _iq gRsOnLinePole_Hz = _IQ(0.2);
182 
183 // **************************************************************************
184 // the functions
185 void main(void)
186 {
187  // Only used if running from FLASH
188  // Note that the variable FLASH is defined by the project
189  #ifdef FLASH
190  // Copy time critical code and Flash setup code to RAM
191  // The RamfuncsLoadStart, RamfuncsLoadEnd, and RamfuncsRunStart
192  // symbols are created by the linker. Refer to the linker files.
193  memCopy((uint16_t *)&RamfuncsLoadStart,(uint16_t *)&RamfuncsLoadEnd,(uint16_t *)&RamfuncsRunStart);
194 
195  #ifdef F2802xF
196  //copy .econst to unsecure RAM
197  if(*econst_end - *econst_start)
198  {
199  memCopy((uint16_t *)&econst_start,(uint16_t *)&econst_end,(uint16_t *)&econst_ram_load);
200  }
201 
202  //copy .switch ot unsecure RAM
203  if(*switch_end - *switch_start)
204  {
205  memCopy((uint16_t *)&switch_start,(uint16_t *)&switch_end,(uint16_t *)&switch_ram_load);
206  }
207  #endif
208 
209  #endif
210 
211  // initialize the hardware abstraction layer
212  halHandle = HAL_init(&hal,sizeof(hal));
213 
214  // check for errors in user parameters
215  USER_checkForErrors(&gUserParams);
216 
217 
218  // store user parameter error in global variable
219  gMotorVars.UserErrorCode = USER_getErrorCode(&gUserParams);
220 
221 
222  // do not allow code execution if there is a user parameter error
223  if(gMotorVars.UserErrorCode != USER_ErrorCode_NoError)
224  {
225  for(;;)
226  {
227  gMotorVars.Flag_enableSys = false;
228  }
229  }
230 
231  // initialize the Clarke modules
232  clarkeHandle_I = CLARKE_init(&clarke_I,sizeof(clarke_I));
233  clarkeHandle_V = CLARKE_init(&clarke_V,sizeof(clarke_V));
234 
235  // initialize the estimator
236  estHandle = EST_init((void *)USER_EST_HANDLE_ADDRESS, 0x200);
237 
238  // initialize the user parameters
239  USER_setParams(&gUserParams);
240 
241  // set the hardware abstraction layer parameters
242  HAL_setParams(halHandle,&gUserParams);
243 
244 #ifdef FAST_ROM_V1p6
245  {
246  CTRL_Handle ctrlHandle = CTRL_init((void *)USER_CTRL_HANDLE_ADDRESS, 0x200);
247  CTRL_Obj *obj = (CTRL_Obj *)ctrlHandle;
248  obj->estHandle = estHandle;
249 
250  // initialize the estimator through the controller
251  CTRL_setParams(ctrlHandle,&gUserParams);
252  CTRL_setUserMotorParams(ctrlHandle);
253  CTRL_setupEstIdleState(ctrlHandle);
254  }
255 #else
256  {
257  // initialize the estimator
258  EST_setEstParams(estHandle,&gUserParams);
260  }
261 #endif
262 
263  // disable Rs recalculation by default
264  gMotorVars.Flag_enableRsRecalc = false;
266 
267  // configure RsOnLine
268  EST_setFlag_enableRsOnLine(estHandle,gFlag_enableRsOnLine);
269  EST_setFlag_updateRs(estHandle,gFlag_updateRs);
272 
273  // Calculate coefficients for all filters
274  {
275  _iq b0 = _IQmpy(gRsOnLinePole_Hz, _IQ(1.0/USER_ISR_FREQ_Hz));
276  _iq a1 = b0 - _IQ(1.0);
277  EST_setRsOnLineFilterParams(estHandle,EST_RsOnLineFilterType_Current,b0,a1,_IQ(0.0),b0,a1,_IQ(0.0));
278  EST_setRsOnLineFilterParams(estHandle,EST_RsOnLineFilterType_Voltage,b0,a1,_IQ(0.0),b0,a1,_IQ(0.0));
279  }
280 
281  // set the number of current sensors
282  setupClarke_I(clarkeHandle_I,USER_NUM_CURRENT_SENSORS);
283 
284  // set the number of voltage sensors
285  setupClarke_V(clarkeHandle_V,USER_NUM_VOLTAGE_SENSORS);
286 
287  // set the pre-determined current and voltage feeback offset values
288  gOffsets_I_pu.value[0] = _IQ(I_A_offset);
289  gOffsets_I_pu.value[1] = _IQ(I_B_offset);
290  gOffsets_I_pu.value[2] = _IQ(I_C_offset);
291  gOffsets_V_pu.value[0] = _IQ(V_A_offset);
292  gOffsets_V_pu.value[1] = _IQ(V_B_offset);
293  gOffsets_V_pu.value[2] = _IQ(V_C_offset);
294 
295  // initialize the PID controllers
296  {
297  _iq maxCurrent_pu = _IQ(USER_MOTOR_MAX_CURRENT / USER_IQ_FULL_SCALE_CURRENT_A);
298  _iq maxVoltage_pu = _IQ(USER_MAX_VS_MAG_PU * USER_VD_SF);
299  float_t fullScaleCurrent = USER_IQ_FULL_SCALE_CURRENT_A;
300  float_t fullScaleVoltage = USER_IQ_FULL_SCALE_VOLTAGE_V;
301  float_t IsrPeriod_sec = 1.0 / USER_ISR_FREQ_Hz;
302  float_t Ls_d = USER_MOTOR_Ls_d;
303  float_t Ls_q = USER_MOTOR_Ls_q;
304  float_t Rs = USER_MOTOR_Rs;
305  float_t RoverLs_d = Rs/Ls_d;
306  float_t RoverLs_q = Rs/Ls_q;
307  _iq Kp_Id = _IQ((0.25*Ls_d*fullScaleCurrent)/(IsrPeriod_sec*fullScaleVoltage));
308  _iq Ki_Id = _IQ(RoverLs_d*IsrPeriod_sec);
309  _iq Kp_Iq = _IQ((0.25*Ls_q*fullScaleCurrent)/(IsrPeriod_sec*fullScaleVoltage));
310  _iq Ki_Iq = _IQ(RoverLs_q*IsrPeriod_sec);
311 
312  pidHandle[0] = PID_init(&pid[0],sizeof(pid[0]));
313  pidHandle[1] = PID_init(&pid[1],sizeof(pid[1]));
314  pidHandle[2] = PID_init(&pid[2],sizeof(pid[2]));
315 
316  PID_setGains(pidHandle[0],_IQ(1.0),_IQ(0.01),_IQ(0.0));
317  PID_setMinMax(pidHandle[0],-maxCurrent_pu,maxCurrent_pu);
318  PID_setUi(pidHandle[0],_IQ(0.0));
319  pidCntSpeed = 0;
320 
321  PID_setGains(pidHandle[1],Kp_Id,Ki_Id,_IQ(0.0));
322  PID_setMinMax(pidHandle[1],-maxVoltage_pu,maxVoltage_pu);
323  PID_setUi(pidHandle[1],_IQ(0.0));
324 
325  PID_setGains(pidHandle[2],Kp_Iq,Ki_Iq,_IQ(0.0));
326  PID_setMinMax(pidHandle[2],_IQ(0.0),_IQ(0.0));
327  PID_setUi(pidHandle[2],_IQ(0.0));
328  }
329 
330  // initialize the speed reference in kilo RPM where base speed is USER_IQ_FULL_SCALE_FREQ_Hz
331  gMotorVars.SpeedRef_krpm = _IQmpy(_IQ(10.0), gSpeed_hz_to_krpm_sf);
332 
333  // initialize the inverse Park module
334  iparkHandle = IPARK_init(&ipark,sizeof(ipark));
335 
336  // initialize and configure offsets using filters
337  {
338  uint16_t cnt = 0;
339  _iq b0 = _IQ(gUserParams.offsetPole_rps/(float_t)gUserParams.ctrlFreq_Hz);
340  _iq a1 = (b0 - _IQ(1.0));
341  _iq b1 = _IQ(0.0);
342 
343  for(cnt=0;cnt<6;cnt++)
344  {
345  filterHandle[cnt] = FILTER_FO_init(&filter[cnt],sizeof(filter[0]));
346  FILTER_FO_setDenCoeffs(filterHandle[cnt],a1);
347  FILTER_FO_setNumCoeffs(filterHandle[cnt],b0,b1);
348  FILTER_FO_setInitialConditions(filterHandle[cnt],_IQ(0.0),_IQ(0.0));
349  }
350 
351  gMotorVars.Flag_enableOffsetcalc = false;
352  }
353 
354  // initialize the space vector generator module
355  svgenHandle = SVGEN_init(&svgen,sizeof(svgen));
356 
357  // Initialize and setup the 100% SVM generator
358  svgencurrentHandle = SVGENCURRENT_init(&svgencurrent,sizeof(svgencurrent));
359 
360  // setup svgen current
361  {
362  float_t minWidth_microseconds = 2.0;
363  uint16_t minWidth_counts = (uint16_t)(minWidth_microseconds * USER_SYSTEM_FREQ_MHz);
364 
365  SVGENCURRENT_setMinWidth(svgencurrentHandle, minWidth_counts);
366  SVGENCURRENT_setIgnoreShunt(svgencurrentHandle, use_all);
367  }
368 
369  // initialize the speed reference trajectory
370  trajHandle_spd = TRAJ_init(&traj_spd,sizeof(traj_spd));
371 
372  // configure the speed reference trajectory
373  TRAJ_setTargetValue(trajHandle_spd,_IQ(0.0));
374  TRAJ_setIntValue(trajHandle_spd,_IQ(0.0));
375  TRAJ_setMinValue(trajHandle_spd,_IQ(-1.0));
376  TRAJ_setMaxValue(trajHandle_spd,_IQ(1.0));
378 
379  // initialize the Id reference trajectory
380  trajHandle_Id = TRAJ_init(&traj_Id,sizeof(traj_Id));
381 
382  if(USER_MOTOR_TYPE == MOTOR_Type_Pm)
383  {
384  // configure the Id reference trajectory
385  TRAJ_setTargetValue(trajHandle_Id,_IQ(0.0));
386  TRAJ_setIntValue(trajHandle_Id,_IQ(0.0));
387  TRAJ_setMinValue(trajHandle_Id,_IQ(-USER_MOTOR_MAX_CURRENT / USER_IQ_FULL_SCALE_CURRENT_A));
388  TRAJ_setMaxValue(trajHandle_Id,_IQ(USER_MOTOR_MAX_CURRENT / USER_IQ_FULL_SCALE_CURRENT_A));
390 
391  // Initialize field weakening
392  fwHandle = FW_init(&fw,sizeof(fw));
393  FW_setFlag_enableFw(fwHandle, false); // Disable field weakening
394  FW_clearCounter(fwHandle); // Clear field weakening counter
395  FW_setNumIsrTicksPerFwTick(fwHandle, FW_NUM_ISR_TICKS_PER_CTRL_TICK); // Set the number of ISR per field weakening ticks
396  FW_setDeltas(fwHandle, FW_INC_DELTA, FW_DEC_DELTA); // Set the deltas of field weakening
397  FW_setOutput(fwHandle, _IQ(0.0)); // Set initial output of field weakening to zero
398  FW_setMinMax(fwHandle,_IQ(USER_MAX_NEGATIVE_ID_REF_CURRENT_A/USER_IQ_FULL_SCALE_CURRENT_A),_IQ(0.0)); // Set the field weakening controller limits
399  }
400  else
401  {
402  // configure the Id reference trajectory
403  TRAJ_setTargetValue(trajHandle_Id,_IQ(0.0));
404  TRAJ_setIntValue(trajHandle_Id,_IQ(0.0));
405  TRAJ_setMinValue(trajHandle_Id,_IQ(0.0));
408  }
409 
410  // initialize the CPU usage module
411  cpu_usageHandle = CPU_USAGE_init(&cpu_usage,sizeof(cpu_usage));
412  CPU_USAGE_setParams(cpu_usageHandle,
413  (uint32_t)USER_SYSTEM_FREQ_MHz * 1000000, // timer period, cnts
414  (uint32_t)USER_ISR_FREQ_Hz); // average over 1 second of ISRs
415 
416  // setup faults
417  HAL_setupFaults(halHandle);
418 
419  // initialize the interrupt vector table
420  HAL_initIntVectorTable(halHandle);
421 
422  // enable the ADC interrupts
423  HAL_enableAdcInts(halHandle);
424 
425  // enable global interrupts
426  HAL_enableGlobalInts(halHandle);
427 
428  // enable debug interrupts
429  HAL_enableDebugInt(halHandle);
430 
431  // disable the PWM
432  HAL_disablePwm(halHandle);
433 
434  // compute scaling factors for flux and torque calculations
435  gFlux_pu_to_Wb_sf = USER_computeFlux_pu_to_Wb_sf();
436  gFlux_pu_to_VpHz_sf = USER_computeFlux_pu_to_VpHz_sf();
437  gTorque_Ls_Id_Iq_pu_to_Nm_sf = USER_computeTorque_Ls_Id_Iq_pu_to_Nm_sf();
438  gTorque_Flux_Iq_pu_to_Nm_sf = USER_computeTorque_Flux_Iq_pu_to_Nm_sf();
439 
440  // enable the system by default
441  gMotorVars.Flag_enableSys = true;
442 
443 #ifdef DRV8301_SPI
444  // turn on the DRV8301 if present
445  HAL_enableDrv(halHandle);
446  // initialize the DRV8301 interface
447  HAL_setupDrvSpi(halHandle,&gDrvSpi8301Vars);
448 #endif
449 
450 #ifdef DRV8305_SPI
451  // turn on the DRV8305 if present
452  HAL_enableDrv(halHandle);
453  // initialize the DRV8305 interface
454  HAL_setupDrvSpi(halHandle,&gDrvSpi8305Vars);
455 #endif
456 
457  // Begin the background loop
458  for(;;)
459  {
460  // Waiting for enable system flag to be set
461  while(!(gMotorVars.Flag_enableSys));
462 
463  // loop while the enable system flag is true
464  while(gMotorVars.Flag_enableSys)
465  {
466  if(gMotorVars.Flag_Run_Identify)
467  {
468  // disable Rs recalculation
470 
471  // update estimator state
473 
474  #ifdef FAST_ROM_V1p6
475  // call this function to fix 1p6
477  #endif
478 
479  // enable the PWM
480  HAL_enablePwm(halHandle);
481 
482  // set trajectory target for speed reference
483  TRAJ_setTargetValue(trajHandle_spd,_IQmpy(gMotorVars.SpeedRef_krpm, gSpeed_krpm_to_pu_sf));
484 
485  if(USER_MOTOR_TYPE == MOTOR_Type_Pm)
486  {
487  // set trajectory target for Id reference
488  TRAJ_setTargetValue(trajHandle_Id,gIdq_ref_pu.value[0]);
489  }
490  else
491  {
492  if(gMotorVars.Flag_enablePowerWarp)
493  {
494  _iq Id_target_pw_pu = EST_runPowerWarp(estHandle,TRAJ_getIntValue(trajHandle_Id),gIdq_pu.value[1]);
495  TRAJ_setTargetValue(trajHandle_Id,Id_target_pw_pu);
497  TRAJ_setMaxDelta(trajHandle_Id,_IQ(USER_MOTOR_MAGNETIZING_CURRENT * 0.3 / USER_IQ_FULL_SCALE_CURRENT_A / USER_ISR_FREQ_Hz));
498  }
499  else
500  {
501  // set trajectory target for Id reference
503  TRAJ_setMinValue(trajHandle_Id,_IQ(0.0));
505  }
506  }
507  }
508  else if(gMotorVars.Flag_enableRsRecalc)
509  {
510  // set angle to zero
512 
513  // enable or disable Rs recalculation
515 
516  // update estimator state
518 
519  #ifdef FAST_ROM_V1p6
520  // call this function to fix 1p6
522  #endif
523 
524  // enable the PWM
525  HAL_enablePwm(halHandle);
526 
527  // set trajectory target for speed reference
528  TRAJ_setTargetValue(trajHandle_spd,_IQ(0.0));
529 
530  // set trajectory target for Id reference
532 
533  // if done with Rs recalculation, disable flag
534  if(EST_getState(estHandle) == EST_State_OnLine) gMotorVars.Flag_enableRsRecalc = false;
535  }
536  else
537  {
538  // set estimator to Idle
540 
541  // disable the PWM
542  HAL_disablePwm(halHandle);
543 
544  // clear the speed reference trajectory
545  TRAJ_setTargetValue(trajHandle_spd,_IQ(0.0));
546  TRAJ_setIntValue(trajHandle_spd,_IQ(0.0));
547 
548  // clear the Id reference trajectory
549  TRAJ_setTargetValue(trajHandle_Id,_IQ(0.0));
550  TRAJ_setIntValue(trajHandle_Id,_IQ(0.0));
551 
552  // configure trajectory Id defaults depending on motor type
553  if(USER_MOTOR_TYPE == MOTOR_Type_Pm)
554  {
555  TRAJ_setMinValue(trajHandle_Id,_IQ(-USER_MOTOR_MAX_CURRENT / USER_IQ_FULL_SCALE_CURRENT_A));
557  }
558  else
559  {
560  TRAJ_setMinValue(trajHandle_Id,_IQ(0.0));
562  }
563 
564  // clear integral outputs
565  PID_setUi(pidHandle[0],_IQ(0.0));
566  PID_setUi(pidHandle[1],_IQ(0.0));
567  PID_setUi(pidHandle[2],_IQ(0.0));
568 
569  // clear Id and Iq references
570  gIdq_ref_pu.value[0] = _IQ(0.0);
571  gIdq_ref_pu.value[1] = _IQ(0.0);
572 
573  // disable RsOnLine flags
574  gFlag_enableRsOnLine = false;
575  gFlag_updateRs = false;
576 
577  // disable PowerWarp flag
578  gMotorVars.Flag_enablePowerWarp = false;
579  }
580 
581  // update the global variables
583 
584  // set field weakening enable flag depending on user's input
585  FW_setFlag_enableFw(fwHandle,gMotorVars.Flag_enableFieldWeakening);
586 
587  // update CPU usage
588  updateCPUusage();
589 
590  // enable/disable the forced angle
592 
593  // enable or disable RsOnLine
594  EST_setFlag_enableRsOnLine(estHandle,gFlag_enableRsOnLine);
595 
596  // set slow rotating frequency for RsOnLine
597  EST_setRsOnLineAngleDelta_pu(estHandle,_IQmpy(gRsOnLineFreq_Hz, _IQ(1.0/USER_ISR_FREQ_Hz)));
598 
599  // set current amplitude for RsOnLine
601 
602  // set flag that updates Rs from RsOnLine value
603  EST_setFlag_updateRs(estHandle,gFlag_updateRs);
604 
605  // clear Id for RsOnLine if disabled
606  if(!gFlag_enableRsOnLine) EST_setRsOnLineId_pu(estHandle,_IQ(0.0));
607 
608 #ifdef DRV8301_SPI
609  HAL_writeDrvData(halHandle,&gDrvSpi8301Vars);
610 
611  HAL_readDrvData(halHandle,&gDrvSpi8301Vars);
612 #endif
613 #ifdef DRV8305_SPI
614  HAL_writeDrvData(halHandle,&gDrvSpi8305Vars);
615 
616  HAL_readDrvData(halHandle,&gDrvSpi8305Vars);
617 #endif
618 
619  } // end of while(gFlag_enableSys) loop
620 
621  // disable the PWM
622  HAL_disablePwm(halHandle);
623 
624  gMotorVars.Flag_Run_Identify = false;
625  } // end of for(;;) loop
626 } // end of main() function
627 
628 
630 interrupt void mainISR(void)
631 {
632  _iq angle_pu = _IQ(0.0);
633  _iq speed_pu = _IQ(0.0);
634  _iq oneOverDcBus;
635  MATH_vec2 Iab_pu;
636  MATH_vec2 Vab_pu;
637  MATH_vec2 phasor;
638  uint32_t timer1Cnt;
639 
640  // read the timer 1 value and update the CPU usage module
641  timer1Cnt = HAL_readTimerCnt(halHandle,1);
642  CPU_USAGE_updateCnts(cpu_usageHandle,timer1Cnt);
643 
644  // acknowledge the ADC interrupt
645  HAL_acqAdcInt(halHandle,ADC_IntNumber_1);
646 
647  // convert the ADC data
648  HAL_readAdcDataWithOffsets(halHandle,&gAdcData);
649 
650  // remove offsets
651  gAdcData.I.value[0] = gAdcData.I.value[0] - gOffsets_I_pu.value[0];
652  gAdcData.I.value[1] = gAdcData.I.value[1] - gOffsets_I_pu.value[1];
653  gAdcData.I.value[2] = gAdcData.I.value[2] - gOffsets_I_pu.value[2];
654  gAdcData.V.value[0] = gAdcData.V.value[0] - gOffsets_V_pu.value[0];
655  gAdcData.V.value[1] = gAdcData.V.value[1] - gOffsets_V_pu.value[1];
656  gAdcData.V.value[2] = gAdcData.V.value[2] - gOffsets_V_pu.value[2];
657 
658  // run the current reconstruction algorithm
660 
661  // run Clarke transform on current
662  CLARKE_run(clarkeHandle_I,&gAdcData.I,&Iab_pu);
663 
664  // run Clarke transform on voltage
665  CLARKE_run(clarkeHandle_V,&gAdcData.V,&Vab_pu);
666 
667  // run a trajectory for Id reference, so the reference changes with a ramp instead of a step
668  TRAJ_run(trajHandle_Id);
669 
670  // run a trajectory for speed reference, so the reference changes with a ramp instead of a step
671  TRAJ_run(trajHandle_spd);
672 
673  // run the estimator
675  &Iab_pu,
676  &Vab_pu,
677  gAdcData.dcBus,
678  TRAJ_getIntValue(trajHandle_spd));
679 
680  // generate the motor electrical angle
681  angle_pu = EST_getAngle_pu(estHandle);
682  speed_pu = EST_getFm_pu(estHandle);
683 
684  // get Idq from estimator to avoid sin and cos
685  EST_getIdq_pu(estHandle,&gIdq_pu);
686 
687  // run the appropriate controller
688  if((gMotorVars.Flag_Run_Identify) || (gMotorVars.Flag_enableRsRecalc))
689  {
690  _iq refValue;
691  _iq fbackValue;
692  _iq outMax_pu;
693 
694  // when appropriate, run the PID speed controller
696  {
697  // calculate Id reference squared
698  _iq Id_ref_squared_pu = _IQmpy(PID_getRefValue(pidHandle[1]),PID_getRefValue(pidHandle[1]));
699 
700  // Take into consideration that Iq^2+Id^2 = Is^2
701  _iq Iq_Max_pu = _IQsqrt(gIs_Max_squared_pu - Id_ref_squared_pu);
702 
703  // clear counter
704  pidCntSpeed = 0;
705 
706  // Set new min and max for the speed controller output
707  PID_setMinMax(pidHandle[0], -Iq_Max_pu, Iq_Max_pu);
708 
709  // run speed controller
710  PID_run_spd(pidHandle[0],TRAJ_getIntValue(trajHandle_spd),speed_pu,&(gIdq_ref_pu.value[1]));
711  }
712 
713  // get the reference value from the trajectory module
714  refValue = TRAJ_getIntValue(trajHandle_Id) + EST_getRsOnLineId_pu(estHandle);
715 
716  // get the feedback value
717  fbackValue = gIdq_pu.value[0];
718 
719  // run the Id PID controller
720  PID_run(pidHandle[1],refValue,fbackValue,&(gVdq_out_pu.value[0]));
721 
722  // set Iq reference to zero when doing Rs recalculation
723  if(gMotorVars.Flag_enableRsRecalc) gIdq_ref_pu.value[1] = _IQ(0.0);
724 
725  // get the Iq reference value
726  refValue = gIdq_ref_pu.value[1];
727 
728  // get the feedback value
729  fbackValue = gIdq_pu.value[1];
730 
731  // calculate Iq controller limits, and run Iq controller
732  outMax_pu = _IQsqrt(_IQ(USER_MAX_VS_MAG_PU * USER_MAX_VS_MAG_PU) - _IQmpy(gVdq_out_pu.value[0],gVdq_out_pu.value[0]));
733  PID_setMinMax(pidHandle[2],-outMax_pu,outMax_pu);
734  PID_run(pidHandle[2],refValue,fbackValue,&(gVdq_out_pu.value[1]));
735 
736  // compensate angle for PWM delay
737  angle_pu = angleDelayComp(speed_pu, angle_pu);
738 
739  // compute the sin/cos phasor
740  phasor.value[0] = _IQcosPU(angle_pu);
741  phasor.value[1] = _IQsinPU(angle_pu);
742 
743  // set the phasor in the inverse Park transform
744  IPARK_setPhasor(iparkHandle,&phasor);
745 
746  // run the inverse Park module
747  IPARK_run(iparkHandle,&gVdq_out_pu,&Vab_pu);
748 
749  // run the space Vector Generator (SVGEN) module
750  oneOverDcBus = EST_getOneOverDcBus_pu(estHandle);
751  Vab_pu.value[0] = _IQmpy(Vab_pu.value[0],oneOverDcBus);
752  Vab_pu.value[1] = _IQmpy(Vab_pu.value[1],oneOverDcBus);
753  SVGEN_run(svgenHandle,&Vab_pu,&(gPwmData.Tabc));
754  }
755  else if(gMotorVars.Flag_enableOffsetcalc == true)
756  {
758  }
759  else
760  {
761  // disable the PWM
762  HAL_disablePwm(halHandle);
763 
764  // Set the PWMs to 50% duty cycle
765  gPwmData.Tabc.value[0] = _IQ(0.0);
766  gPwmData.Tabc.value[1] = _IQ(0.0);
767  gPwmData.Tabc.value[2] = _IQ(0.0);
768  }
769 
770  // write the PWM compare values
771  HAL_writePwmData(halHandle,&gPwmData);
772 
773  // run the current ignore algorithm
775 
776  // run function to set next trigger
777  if(!gMotorVars.Flag_enableRsRecalc) runSetTrigger();
778 
779  // run field weakening
780  if(USER_MOTOR_TYPE == MOTOR_Type_Pm) runFieldWeakening();
781 
782  // read the timer 1 value and update the CPU usage module
783  timer1Cnt = HAL_readTimerCnt(halHandle,1);
784  CPU_USAGE_updateCnts(cpu_usageHandle,timer1Cnt);
785 
786  // run the CPU usage module
787  CPU_USAGE_run(cpu_usageHandle);
788 
789  return;
790 } // end of mainISR() function
791 
792 
793 _iq angleDelayComp(const _iq fm_pu, const _iq angleUncomp_pu)
794 {
795  _iq angleDelta_pu = _IQmpy(fm_pu,_IQ(USER_IQ_FULL_SCALE_FREQ_Hz/(USER_PWM_FREQ_kHz*1000.0)));
796  _iq angleCompFactor = _IQ(1.0 + (float_t)USER_NUM_PWM_TICKS_PER_ISR_TICK * 0.5);
797  _iq angleDeltaComp_pu = _IQmpy(angleDelta_pu, angleCompFactor);
798  uint32_t angleMask = ((uint32_t)0xFFFFFFFF >> (32 - GLOBAL_Q));
799  _iq angleComp_pu;
800  _iq angleTmp_pu;
801 
802  // increment the angle
803  angleTmp_pu = angleUncomp_pu + angleDeltaComp_pu;
804 
805  // mask the angle for wrap around
806  // note: must account for the sign of the angle
807  angleComp_pu = _IQabs(angleTmp_pu) & angleMask;
808 
809  // account for sign
810  if(angleTmp_pu < _IQ(0.0))
811  {
812  angleComp_pu = -angleComp_pu;
813  }
814 
815  return(angleComp_pu);
816 } // end of angleDelayComp() function
817 
818 
820 {
821  uint16_t cmp1 = HAL_readPwmCmpA(halHandle,PWM_Number_1);
822  uint16_t cmp2 = HAL_readPwmCmpA(halHandle,PWM_Number_2);
823  uint16_t cmp3 = HAL_readPwmCmpA(halHandle,PWM_Number_3);
824  uint16_t cmpM1 = HAL_readPwmCmpAM(halHandle,PWM_Number_1);
825  uint16_t cmpM2 = HAL_readPwmCmpAM(halHandle,PWM_Number_2);
826  uint16_t cmpM3 = HAL_readPwmCmpAM(halHandle,PWM_Number_3);
827 
828  // run the current ignore algorithm
829  SVGENCURRENT_RunIgnoreShunt(svgencurrentHandle,cmp1,cmp2,cmp3,cmpM1,cmpM2,cmpM3);
830 
831  return;
832 } // end of runCurrentIgnore() function
833 
834 
836 {
837  SVGENCURRENT_IgnoreShunt_e ignoreShuntThisCycle = SVGENCURRENT_getIgnoreShunt(svgencurrentHandle);
838  SVGENCURRENT_RunRegenCurrent(svgencurrentHandle, (MATH_vec3 *)(gAdcData.I.value));
839 
840  gIavg.value[0] += (gAdcData.I.value[0] - gIavg.value[0])>>gIavg_shift;
841  gIavg.value[1] += (gAdcData.I.value[1] - gIavg.value[1])>>gIavg_shift;
842  gIavg.value[2] += (gAdcData.I.value[2] - gIavg.value[2])>>gIavg_shift;
843 
844  if(ignoreShuntThisCycle == ignore_ab)
845  {
846  gAdcData.I.value[0] = gIavg.value[0];
847  gAdcData.I.value[1] = gIavg.value[1];
848  }
849  else if(ignoreShuntThisCycle == ignore_ac)
850  {
851  gAdcData.I.value[0] = gIavg.value[0];
852  gAdcData.I.value[2] = gIavg.value[2];
853  }
854  else if(ignoreShuntThisCycle == ignore_bc)
855  {
856  gAdcData.I.value[1] = gIavg.value[1];
857  gAdcData.I.value[2] = gIavg.value[2];
858  }
859 
860  return;
861 } // end of runCurrentReconstruction() function
862 
863 
865 {
866  if(FW_getFlag_enableFw(fwHandle) == true)
867  {
868  FW_incCounter(fwHandle);
869 
870  if(FW_getCounter(fwHandle) > FW_getNumIsrTicksPerFwTick(fwHandle))
871  {
872  _iq refValue;
873  _iq fbackValue;
874 
875  FW_clearCounter(fwHandle);
876 
877  refValue = gMotorVars.VsRef;
878 
879  fbackValue = gMotorVars.Vs;
880 
881  FW_run(fwHandle, refValue, fbackValue, &(gIdq_ref_pu.value[0]));
882 
883  gMotorVars.IdRef_A = _IQmpy(gIdq_ref_pu.value[0], _IQ(USER_IQ_FULL_SCALE_CURRENT_A));
884  }
885  }
886  else
887  {
888  gIdq_ref_pu.value[0] = _IQmpy(gMotorVars.IdRef_A, _IQ(1.0/USER_IQ_FULL_SCALE_CURRENT_A));
889  }
890 
891  return;
892 } // end of runFieldWeakening() function
893 
894 
896 {
897  uint16_t cnt;
898 
899  // enable the PWM
900  HAL_enablePwm(halHandle);
901 
902  for(cnt=0;cnt<3;cnt++)
903  {
904  // Set the PWMs to 50% duty cycle
905  gPwmData.Tabc.value[cnt] = _IQ(0.0);
906 
907  // reset offsets used
908  gOffsets_I_pu.value[cnt] = _IQ(0.0);
909  gOffsets_V_pu.value[cnt] = _IQ(0.0);
910 
911  // run offset estimation
912  FILTER_FO_run(filterHandle[cnt],gAdcData.I.value[cnt]);
913  FILTER_FO_run(filterHandle[cnt+3],gAdcData.V.value[cnt]);
914  }
915 
916  if(gOffsetCalcCount++ >= gUserParams.ctrlWaitTime[CTRL_State_OffLine])
917  {
918  gMotorVars.Flag_enableOffsetcalc = false;
919  gOffsetCalcCount = 0;
920 
921  for(cnt=0;cnt<3;cnt++)
922  {
923  // get calculated offsets from filter
924  gOffsets_I_pu.value[cnt] = FILTER_FO_get_y1(filterHandle[cnt]);
925  gOffsets_V_pu.value[cnt] = FILTER_FO_get_y1(filterHandle[cnt+3]);
926 
927  // clear filters
928  FILTER_FO_setInitialConditions(filterHandle[cnt],_IQ(0.0),_IQ(0.0));
929  FILTER_FO_setInitialConditions(filterHandle[cnt+3],_IQ(0.0),_IQ(0.0));
930  }
931  }
932 
933  return;
934 } // end of runOffsetsCalculation() function
935 
936 
938 {
940  float_t Ls_coarse_max = _IQ30toF(EST_getLs_coarse_max_pu(handle));
941  int_least8_t lShift = ceil(log(USER_MOTOR_Ls_d/(Ls_coarse_max*fullScaleInductance))/log(2.0));
942  uint_least8_t Ls_qFmt = 30 - lShift;
943  float_t L_max = fullScaleInductance * pow(2.0,lShift);
944  _iq Ls_d_pu = _IQ30(USER_MOTOR_Ls_d / L_max);
945  _iq Ls_q_pu = _IQ30(USER_MOTOR_Ls_q / L_max);
946 
947 
948  // store the results
949  EST_setLs_d_pu(handle,Ls_d_pu);
950  EST_setLs_q_pu(handle,Ls_q_pu);
951  EST_setLs_qFmt(handle,Ls_qFmt);
952 
953  return;
954 } // end of softwareUpdate1p6() function
955 
956 
957 void runSetTrigger(void)
958 {
959  int16_t minwidth = SVGENCURRENT_getMinWidth(svgencurrentHandle);
960  SVGENCURRENT_IgnoreShunt_e ignoreShuntNextCycle = SVGENCURRENT_getIgnoreShunt(svgencurrentHandle);
961 
962  // Set trigger point in the middle of the low side pulse
963  HAL_setTrigger(halHandle,ignoreShuntNextCycle,minwidth,gCmpOffset);
964 
965  return;
966 } // end of runSetTrigger() function
967 
968 
972 void setupClarke_I(CLARKE_Handle handle,const uint_least8_t numCurrentSensors)
973 {
974  _iq alpha_sf,beta_sf;
975 
976  // initialize the Clarke transform module for current
977  if(numCurrentSensors == 3)
978  {
979  alpha_sf = _IQ(MATH_ONE_OVER_THREE);
980  beta_sf = _IQ(MATH_ONE_OVER_SQRT_THREE);
981  }
982  else if(numCurrentSensors == 2)
983  {
984  alpha_sf = _IQ(1.0);
985  beta_sf = _IQ(MATH_ONE_OVER_SQRT_THREE);
986  }
987  else
988  {
989  alpha_sf = _IQ(0.0);
990  beta_sf = _IQ(0.0);
991  }
992 
993  // set the parameters
994  CLARKE_setScaleFactors(handle,alpha_sf,beta_sf);
995  CLARKE_setNumSensors(handle,numCurrentSensors);
996 
997  return;
998 } // end of setupClarke_I() function
999 
1000 
1004 void setupClarke_V(CLARKE_Handle handle,const uint_least8_t numVoltageSensors)
1005 {
1006  _iq alpha_sf,beta_sf;
1007 
1008  // initialize the Clarke transform module for voltage
1009  if(numVoltageSensors == 3)
1010  {
1011  alpha_sf = _IQ(MATH_ONE_OVER_THREE);
1012  beta_sf = _IQ(MATH_ONE_OVER_SQRT_THREE);
1013  }
1014  else
1015  {
1016  alpha_sf = _IQ(0.0);
1017  beta_sf = _IQ(0.0);
1018  }
1019 
1020  // set the parameters
1021  CLARKE_setScaleFactors(handle,alpha_sf,beta_sf);
1022  CLARKE_setNumSensors(handle,numVoltageSensors);
1023 
1024  return;
1025 } // end of setupClarke_V() function
1026 
1027 
1031 {
1032  // get the speed estimate
1033  gMotorVars.Speed_krpm = EST_getSpeed_krpm(handle);
1034 
1035  // get the torque estimate
1036  {
1037  _iq Flux_pu = EST_getFlux_pu(handle);
1038  _iq Id_pu = PID_getFbackValue(pidHandle[1]);
1039  _iq Iq_pu = PID_getFbackValue(pidHandle[2]);
1040  _iq Ld_minus_Lq_pu = _IQ30toIQ(EST_getLs_d_pu(handle)-EST_getLs_q_pu(handle));
1041  _iq Torque_Flux_Iq_Nm = _IQmpy(_IQmpy(Flux_pu,Iq_pu),gTorque_Flux_Iq_pu_to_Nm_sf);
1042  _iq Torque_Ls_Id_Iq_Nm = _IQmpy(_IQmpy(_IQmpy(Ld_minus_Lq_pu,Id_pu),Iq_pu),gTorque_Ls_Id_Iq_pu_to_Nm_sf);
1043  _iq Torque_Nm = Torque_Flux_Iq_Nm + Torque_Ls_Id_Iq_Nm;
1044 
1045  gMotorVars.Torque_Nm = Torque_Nm;
1046  }
1047 
1048  // get the magnetizing current
1049  gMotorVars.MagnCurr_A = EST_getIdRated(handle);
1050 
1051  // get the rotor resistance
1052  gMotorVars.Rr_Ohm = EST_getRr_Ohm(handle);
1053 
1054  // get the stator resistance
1055  gMotorVars.Rs_Ohm = EST_getRs_Ohm(handle);
1056 
1057  // get the online stator resistance
1058  gMotorVars.RsOnLine_Ohm = EST_getRsOnLine_Ohm(handle);
1059 
1060  // get the stator inductance in the direct coordinate direction
1061  gMotorVars.Lsd_H = EST_getLs_d_H(handle);
1062 
1063  // get the stator inductance in the quadrature coordinate direction
1064  gMotorVars.Lsq_H = EST_getLs_q_H(handle);
1065 
1066  // get the flux in V/Hz in floating point
1067  gMotorVars.Flux_VpHz = EST_getFlux_VpHz(handle);
1068 
1069  // get the flux in Wb in fixed point
1070  gMotorVars.Flux_Wb = _IQmpy(EST_getFlux_pu(handle),gFlux_pu_to_Wb_sf);
1071 
1072  // get the estimator state
1073  gMotorVars.EstState = EST_getState(handle);
1074 
1075  // Get the DC buss voltage
1076  gMotorVars.VdcBus_kV = _IQmpy(gAdcData.dcBus,_IQ(USER_IQ_FULL_SCALE_VOLTAGE_V/1000.0));
1077 
1078  // read Vd and Vq vectors per units
1079  gMotorVars.Vd = gVdq_out_pu.value[0];
1080  gMotorVars.Vq = gVdq_out_pu.value[1];
1081 
1082  // calculate vector Vs in per units
1083  gMotorVars.Vs = _IQsqrt(_IQmpy(gMotorVars.Vd, gMotorVars.Vd) + _IQmpy(gMotorVars.Vq, gMotorVars.Vq));
1084 
1085  // read Id and Iq vectors in amps
1086  gMotorVars.Id_A = _IQmpy(gIdq_pu.value[0], _IQ(USER_IQ_FULL_SCALE_CURRENT_A));
1087  gMotorVars.Iq_A = _IQmpy(gIdq_pu.value[1], _IQ(USER_IQ_FULL_SCALE_CURRENT_A));
1088 
1089  // calculate vector Is in amps
1090  gMotorVars.Is_A = _IQsqrt(_IQmpy(gMotorVars.Id_A, gMotorVars.Id_A) + _IQmpy(gMotorVars.Iq_A, gMotorVars.Iq_A));
1091 
1092  return;
1093 } // end of updateGlobalVariables() function
1094 
1095 
1096 void updateCPUusage(void)
1097 {
1098  uint32_t minDeltaCntObserved = CPU_USAGE_getMinDeltaCntObserved(cpu_usageHandle);
1099  uint32_t avgDeltaCntObserved = CPU_USAGE_getAvgDeltaCntObserved(cpu_usageHandle);
1100  uint32_t maxDeltaCntObserved = CPU_USAGE_getMaxDeltaCntObserved(cpu_usageHandle);
1101  uint16_t pwmPeriod = HAL_readPwmPeriod(halHandle,PWM_Number_1);
1102  float_t cpu_usage_den = (float_t)pwmPeriod * (float_t)USER_NUM_PWM_TICKS_PER_ISR_TICK * 2.0;
1103 
1104  // calculate the minimum cpu usage percentage
1105  gCpuUsagePercentageMin = (float_t)minDeltaCntObserved / cpu_usage_den * 100.0;
1106 
1107  // calculate the average cpu usage percentage
1108  gCpuUsagePercentageAvg = (float_t)avgDeltaCntObserved / cpu_usage_den * 100.0;
1109 
1110  // calculate the maximum cpu usage percentage
1111  gCpuUsagePercentageMax = (float_t)maxDeltaCntObserved / cpu_usage_den * 100.0;
1112 
1113  return;
1114 } // end of updateCPUusage() function
1115 
1116 
1118 // end of file
1119 
1120 
1121 
float_t EST_getFlux_VpHz(EST_Handle handle)
CPU_USAGE_Obj cpu_usage
Definition: proj_lab11a.c:71
#define USER_SYSTEM_FREQ_MHz
CLOCKS & TIMERS.
Definition: user.h:140
float_t EST_getRsOnLine_Ohm(EST_Handle handle)
#define USER_NUM_CURRENT_SENSORS
Defines the number of current sensors used.
Definition: user.h:116
void EST_setFlag_enableForceAngle(EST_Handle handle, const bool state)
IPARK_Handle IPARK_init(void *pMemory, const size_t numBytes)
_iq EST_getLs_coarse_max_pu(EST_Handle handle)
HAL_AdcData_t gAdcData
contains three current values, three voltage values and one DC buss value
Definition: proj_lab11a.c:107
static void TRAJ_setTargetValue(TRAJ_Handle handle, const _iq targetValue)
#define _IQsinPU(A)
void HAL_enableGlobalInts(HAL_Handle handle)
void HAL_enableAdcInts(HAL_Handle handle)
static _iq PID_getRefValue(PID_Handle handle)
USER_ErrorCode_e UserErrorCode
Definition: main.h:150
#define USER_MAX_NEGATIVE_ID_REF_CURRENT_A
LIMITS.
Definition: user.h:239
float_t RsOnLine_Ohm
Definition: main.h:170
float_t Lsq_H
Definition: main.h:172
#define USER_MOTOR_Ls_d
Definition: user.h:401
float_t gCpuUsagePercentageMin
Definition: proj_lab11a.c:167
static void HAL_readAdcDataWithOffsets(HAL_Handle handle, HAL_AdcData_t *pAdcData)
HAL_Handle halHandle
the handle for the hardware abstraction layer (HAL)
Definition: proj_lab11a.c:103
_iq USER_computeFlux_pu_to_VpHz_sf(void)
Computes the scale factor needed to convert from per unit to V/Hz.
_iq gTorque_Ls_Id_Iq_pu_to_Nm_sf
Definition: proj_lab11a.c:157
MATH_vec3 gOffsets_V_pu
contains the offsets for the voltage feedback
Definition: proj_lab11a.c:111
TRAJ_Handle trajHandle_Id
the handle for the id reference trajectory
Definition: proj_lab11a.c:94
#define _IQ(A)
static void TRAJ_setMaxDelta(TRAJ_Handle handle, const _iq maxDelta)
_iq Iq_A
Definition: main.h:195
CLARKE_Obj clarke_I
the current Clarke transform object
Definition: proj_lab11a.c:65
static void PID_setUi(PID_Handle handle, const _iq Ui)
#define FW_INC_DELTA
int16_t gCmpOffset
Definition: proj_lab11a.c:138
bool Flag_Run_Identify
Definition: main.h:137
_iq EST_getSpeed_krpm(EST_Handle handle)
void EST_setRsOnLineAngleDelta_pu(EST_Handle handle, const _iq angleDelta_pu)
volatile _iq gRsOnLineId_mag_A
Definition: proj_lab11a.c:179
#define FW_DEC_DELTA
static uint16_t HAL_readPwmCmpAM(HAL_Handle handle, const PWM_Number_e pwmNumber)
void EST_setRsOnLineId_mag_pu(EST_Handle handle, const _iq Id_mag_pu)
FW_Handle FW_init(void *pMemory, const size_t numBytes)
static _iq TRAJ_getIntValue(TRAJ_Handle handle)
void EST_setupEstIdleState(EST_Handle handle)
float_t gCpuUsagePercentageMax
Definition: proj_lab11a.c:169
static bool FW_getFlag_enableFw(FW_Handle fwHandle)
static uint32_t FW_getNumIsrTicksPerFwTick(FW_Handle fwHandle)
_iq Iq_Max_pu
Definition: proj_lab09.c:117
void softwareUpdate1p6(EST_Handle handle)
Updates version 1p6 of library.
Definition: proj_lab11a.c:937
bool Flag_enablePowerWarp
Definition: main.h:144
static void HAL_writePwmData(HAL_Handle handle, HAL_PwmData_t *pPwmData)
CLARKE_Obj clarke_V
the voltage Clarke transform object
Definition: proj_lab11a.c:68
static void FW_setOutput(FW_Handle fwHandle, const _iq output)
_iq value[3]
struct _EST_Obj_ * EST_Handle
void EST_setIdle(EST_Handle handle)
void HAL_writeDrvData(HAL_Handle handle, DRV_SPI_8301_Vars_t *Spi_8301_Vars)
IPARK_Handle iparkHandle
the handle for the inverse Park transform
Definition: proj_lab11a.c:82
TRAJ_Obj traj_Id
the id reference trajectory object
Definition: proj_lab11a.c:95
#define USER_VD_SF
Defines the direct voltage (Vd) scale factor.
Definition: user.h:165
static void HAL_acqAdcInt(HAL_Handle handle, const ADC_IntNumber_e intNumber)
uint_least32_t ctrlWaitTime[CTRL_numStates]
#define USER_IQ_FULL_SCALE_VOLTAGE_V
Defines full scale value for the IQ30 variable of Voltage inside the system.
Definition: user.h:88
#define _IQcosPU(A)
MATH_vec2 gIdq_ref_pu
contains the Id and Iq references
Definition: proj_lab11a.c:113
MATH_vec3 gIavg
Definition: proj_lab11a.c:140
#define USER_MOTOR_NUM_POLE_PAIRS
Definition: user.h:398
volatile bool gFlag_enableRsOnLine
Definition: proj_lab11a.c:173
CLARKE_Handle clarkeHandle_I
the handle for the current Clarke transform
Definition: proj_lab11a.c:64
static void FW_run(FW_Handle fwHandle, const _iq refValue, const _iq fbackValue, _iq *pOutValue)
void memCopy(uint16_t *srcStartAddr, uint16_t *srcEndAddr, uint16_t *dstAddr)
EST_Handle estHandle
float_t gCpuUsagePercentageAvg
Definition: proj_lab11a.c:168
bool Flag_enableForceAngle
Definition: main.h:139
FW_Handle fwHandle
Definition: proj_lab11a.c:75
#define USER_PWM_FREQ_kHz
Defines the Pulse Width Modulation (PWM) frequency, kHz.
Definition: user.h:147
static void PID_setMinMax(PID_Handle handle, const _iq outMin, const _iq outMax)
static void SVGEN_run(SVGEN_Handle handle, const MATH_vec2 *pVab, MATH_vec3 *pT)
static uint32_t CPU_USAGE_getAvgDeltaCntObserved(CPU_USAGE_Handle handle)
static _iq FILTER_FO_run(FILTER_FO_Handle handle, const _iq inputValue)
static _iq PID_getFbackValue(PID_Handle handle)
CPU_USAGE_Handle cpu_usageHandle
Definition: proj_lab11a.c:70
#define V_B_offset
Definition: user.h:133
long _iq
void updateCPUusage(void)
Updates CPU usage.
Definition: proj_lab11a.c:1096
#define MATH_ONE_OVER_THREE
void USER_setParams(USER_Params *pUserParams)
Sets the user parameter values.
void EST_setLs_qFmt(EST_Handle handle, const uint_least8_t Ls_qFmt)
EST_State_e EstState
Definition: main.h:148
#define USER_MAX_ACCEL_Hzps
Defines the starting maximum acceleration AND deceleration for the speed profiles, Hz/s.
Definition: user.h:258
void EST_setFlag_updateRs(EST_Handle handle, const bool state)
static _iq FILTER_FO_get_y1(FILTER_FO_Handle handle)
volatile MOTOR_Vars_t gMotorVars
the global motor variables that are defined in main.h and used for display in the debugger's watch wi...
Definition: proj_lab11a.c:124
float_t Rs_Ohm
Definition: main.h:169
FILTER_FO_Handle FILTER_FO_init(void *pMemory, const size_t numBytes)
#define V_A_offset
ADC voltage offsets for A, B, and C phases.
Definition: user.h:132
_iq EST_getLs_d_pu(EST_Handle handle)
#define I_A_offset
ADC current offsets for A, B, and C phases.
Definition: user.h:125
static void CLARKE_setScaleFactors(CLARKE_Handle handle, const _iq alpha_sf, const _iq beta_sf)
Defines the structures, global initialization, and functions used in MAIN.
#define USER_MOTOR_Rs
Definition: user.h:400
void runCurrentReconstruction(void)
Definition: proj_lab11a.c:835
TRAJ_Handle TRAJ_init(void *pMemory, const size_t numBytes)
CTRL_Handle CTRL_init(void *pMemory, const size_t numBytes)
void HAL_setupFaults(HAL_Handle handle)
EST_Handle EST_init(void *pMemory, const size_t numBytes)
float_t EST_getLs_d_H(EST_Handle handle)
void EST_setFlag_enableRsRecalc(EST_Handle handle, const bool state)
static void TRAJ_setIntValue(TRAJ_Handle handle, const _iq intValue)
MATH_vec3 Tabc
static void PID_setGains(PID_Handle handle, const _iq Kp, const _iq Ki, const _iq Kd)
static void HAL_enablePwm(HAL_Handle handle)
#define USER_MAX_VS_MAG_PU
Defines the maximum Voltage vector (Vs) magnitude allowed. This value sets the maximum magnitude for ...
Definition: user.h:157
void CTRL_setParams(CTRL_Handle handle, USER_Params *pUserParams)
#define _IQmpy(A, B)
SVGEN_Handle svgenHandle
the handle for the space vector generator
Definition: proj_lab11a.c:91
SVGENCURRENT_Obj svgencurrent
Definition: proj_lab11a.c:88
USER_ErrorCode_e USER_getErrorCode(USER_Params *pUserParams)
Gets the error code in the user parameters.
void HAL_enableDrv(HAL_Handle handle)
_iq value[2]
_iq VdcBus_kV
Definition: main.h:192
_iq Torque_Nm
Definition: main.h:165
void FILTER_FO_setNumCoeffs(FILTER_FO_Handle handle, const _iq b0, const _iq b1)
_iq SpeedRef_krpm
Definition: main.h:157
_iq IdRef_A
Definition: main.h:154
void updateGlobalVariables(EST_Handle handle)
Update the global variables (gMotorVars).
Definition: proj_lab11a.c:1030
_iq VsRef
Definition: main.h:191
_iq EST_getOneOverDcBus_pu(EST_Handle handle)
MATH_vec3 gOffsets_I_pu
contains the offsets for the current feedback
Definition: proj_lab11a.c:109
_iq EST_getFlux_pu(EST_Handle handle)
void HAL_setupDrvSpi(HAL_Handle handle, DRV_SPI_8301_Vars_t *Spi_8301_Vars)
_iq gTorque_Flux_Iq_pu_to_Nm_sf
Definition: proj_lab11a.c:159
float_t EST_getLs_q_H(EST_Handle handle)
#define USER_EST_HANDLE_ADDRESS
Defines the address of estimator handle.
Definition: user.h:161
void HAL_enableDebugInt(HAL_Handle handle)
_iq gSpeed_hz_to_krpm_sf
Definition: proj_lab11a.c:163
void CTRL_setupEstIdleState(CTRL_Handle handle)
#define USER_NUM_CTRL_TICKS_PER_SPEED_TICK
Defines the number of controller clock ticks per speed controller clock tick.
Definition: user.h:206
CLARKE_Handle CLARKE_init(void *pMemory, const size_t numBytes)
static void FW_incCounter(FW_Handle fwHandle)
void CTRL_setUserMotorParams(CTRL_Handle handle)
#define I_C_offset
Definition: user.h:127
SVGENCURRENT_IgnoreShunt_e
float_t Flux_VpHz
Definition: main.h:173
#define _IQ30toIQ(A)
static void IPARK_run(IPARK_Handle handle, const MATH_vec2 *pInVec, MATH_vec2 *pOutVec)
PID_Obj pid[3]
three handles for PID controllers 0 - Speed, 1 - Id, 2 - Iq
Definition: proj_lab11a.c:78
#define FW_NUM_ISR_TICKS_PER_CTRL_TICK
float_t offsetPole_rps
EST_State_e EST_getState(EST_Handle handle)
bool Flag_enableOffsetcalc
Definition: main.h:143
#define I_B_offset
Definition: user.h:126
_iq EST_getFm_pu(EST_Handle handle)
TRAJ_Handle trajHandle_spd
the handle for the speed reference trajectory
Definition: proj_lab11a.c:97
PID_Handle pidHandle[3]
three objects for PID controllers 0 - Speed, 1 - Id, 2 - Iq
Definition: proj_lab11a.c:79
void runSetTrigger(void)
Definition: proj_lab11a.c:957
#define MOTOR_Vars_INIT
Initialization values of global variables.
Definition: main.h:76
volatile _iq gRsOnLineFreq_Hz
Definition: proj_lab11a.c:177
#define _IQabs(A)
#define V_C_offset
Definition: user.h:134
void EST_setFlag_enableRsOnLine(EST_Handle handle, const bool state)
CLARKE_Handle clarkeHandle_V
the handle for the voltage Clarke transform
Definition: proj_lab11a.c:67
_iq USER_computeTorque_Flux_Iq_pu_to_Nm_sf(void)
Computes the scale factor needed to convert from torque created by flux and Iq, from per unit to Nm...
_iq Speed_krpm
Definition: main.h:160
float_t EST_getIdRated(EST_Handle handle)
_iq Is_A
Definition: main.h:196
#define USER_MOTOR_RES_EST_CURRENT
Definition: user.h:405
uint32_t gOffsetCalcCount
Definition: proj_lab11a.c:171
static uint32_t HAL_readTimerCnt(HAL_Handle handle, const uint_least8_t timerNumber)
_iq EST_getLs_q_pu(EST_Handle handle)
static void CLARKE_setNumSensors(CLARKE_Handle handle, const uint_least8_t numSensors)
float_t Rr_Ohm
Definition: main.h:168
float_t EST_getRs_Ohm(EST_Handle handle)
FILTER_FO_Handle filterHandle[6]
the handles for the 3-current and 3-voltage filters for offset calculation
Definition: proj_lab11a.c:85
float_t Lsd_H
Definition: main.h:171
#define USER_MOTOR_MAGNETIZING_CURRENT
Definition: user.h:404
#define _IQ30(A)
uint16_t gIavg_shift
Definition: proj_lab11a.c:141
#define USER_IQ_FULL_SCALE_FREQ_Hz
CURRENTS AND VOLTAGES.
Definition: user.h:78
IPARK_Obj ipark
the inverse Park transform object
Definition: proj_lab11a.c:83
void CPU_USAGE_setParams(CPU_USAGE_Handle handle, const uint32_t timerPeriod_cnts, const uint32_t numDeltaCntsAvg)
USER_Params gUserParams
The user parameters.
Definition: proj_lab11a.c:122
SVGEN_Obj svgen
the space vector generator object
Definition: proj_lab11a.c:92
static void FW_setFlag_enableFw(FW_Handle fwHandle, const bool state)
#define USER_ISR_FREQ_Hz
Defines the Interrupt Service Routine (ISR) frequency, Hz.
Definition: user.h:173
static void IPARK_setPhasor(IPARK_Handle handle, const MATH_vec2 *pPhasor)
interrupt void mainISR(void)
The main ISR that implements the motor control.
Definition: proj_lab11a.c:630
static void FW_clearCounter(FW_Handle fwHandle)
CPU_USAGE_Handle CPU_USAGE_init(void *pMemory, const size_t numBytes)
void setupClarke_I(CLARKE_Handle handle, const uint_least8_t numCurrentSensors)
Setup the Clarke transform for either 2 or 3 sensors.
Definition: proj_lab11a.c:972
_iq EST_getAngle_pu(EST_Handle handle)
static void HAL_disablePwm(HAL_Handle handle)
float_t EST_runPowerWarp(EST_Handle handle, const float_t Id_int_A, const float_t Iq_A)
void FILTER_FO_setInitialConditions(FILTER_FO_Handle handle, const _iq x1, const _iq y1)
static void TRAJ_setMaxValue(TRAJ_Handle handle, const _iq maxValue)
static void FW_setDeltas(FW_Handle fwHandle, const _iq delta_inc, const _iq delta_dec)
PID_Handle PID_init(void *pMemory, const size_t numBytes)
HAL_Handle HAL_init(void *pMemory, const size_t numBytes)
static void CLARKE_run(CLARKE_Handle handle, const MATH_vec3 *pInVec, MATH_vec2 *pOutVec)
void EST_setAngle_pu(EST_Handle handle, const _iq angle_pu)
static uint32_t CPU_USAGE_getMaxDeltaCntObserved(CPU_USAGE_Handle handle)
void runCurrentIgnore(void)
Definition: proj_lab11a.c:819
#define _IQsqrt(A)
static uint16_t HAL_readPwmCmpA(HAL_Handle handle, const PWM_Number_e pwmNumber)
#define USER_MOTOR_TYPE
Definition: user.h:397
#define USER_VOLTAGE_FILTER_POLE_rps
Defines the analog voltage filter pole location, rad/s.
Definition: user.h:305
#define USER_NUM_VOLTAGE_SENSORS
Defines the number of voltage (phase) sensors.
Definition: user.h:120
void EST_setLs_q_pu(EST_Handle handle, const _iq Ls_q_pu)
EST_Handle estHandle
the handle for the estimator
Definition: proj_lab11a.c:73
uint_least32_t ctrlFreq_Hz
#define USER_IQ_FULL_SCALE_CURRENT_A
Defines the full scale current for the IQ variables, A.
Definition: user.h:102
float_t MagnCurr_A
Definition: main.h:167
HAL_Obj hal
static void HAL_setTrigger(HAL_Handle handle, const SVGENCURRENT_IgnoreShunt_e ignoreShunt, const int16_t minwidth, const int16_t cmpOffset)
static void PID_run_spd(PID_Handle handle, const _iq refValue, const _iq fbackValue, _iq *pOutValue)
CTRL_Handle ctrlHandle
The controller handle.
volatile _iq gRsOnLinePole_Hz
Definition: proj_lab11a.c:181
_iq EST_getRsOnLineId_pu(EST_Handle handle)
static void CPU_USAGE_updateCnts(CPU_USAGE_Handle handle, const uint32_t cnt)
bool Flag_enableSys
Definition: main.h:136
_iq Id_A
Definition: main.h:194
_iq gFlux_pu_to_Wb_sf
Definition: proj_lab11a.c:153
static uint32_t CPU_USAGE_getMinDeltaCntObserved(CPU_USAGE_Handle handle)
#define MATH_ONE_OVER_SQRT_THREE
void setupClarke_V(CLARKE_Handle handle, const uint_least8_t numVoltageSensors)
Setup the Clarke transform for either 2 or 3 sensors.
Definition: proj_lab11a.c:1004
static uint32_t FW_getCounter(FW_Handle fwHandle)
bool Flag_enableRsRecalc
Definition: main.h:141
static void HAL_initIntVectorTable(HAL_Handle handle)
uint16_t pidCntSpeed
count variable to decimate the execution of the speed PID controller
Definition: proj_lab11a.c:80
void FILTER_FO_setDenCoeffs(FILTER_FO_Handle handle, const _iq a1)
SVGENCURRENT_Handle SVGENCURRENT_init(void *pMemory, const size_t numBytes)
static void FW_setNumIsrTicksPerFwTick(FW_Handle fwHandle, const uint32_t numIsrTicksPerFwTick)
#define USER_MOTOR_Ls_q
Definition: user.h:402
_iq gSpeed_krpm_to_pu_sf
Definition: proj_lab11a.c:161
static uint16_t HAL_readPwmPeriod(HAL_Handle handle, const PWM_Number_e pwmNumber)
bool EST_updateState(EST_Handle handle, const _iq Id_target_pu)
TRAJ_Obj traj_spd
the speed reference trajectory object
Definition: proj_lab11a.c:98
float_t EST_getRr_Ohm(EST_Handle handle)
volatile bool gFlag_updateRs
Definition: proj_lab11a.c:175
void HAL_setParams(HAL_Handle handle, const USER_Params *pUserParams)
static void CPU_USAGE_run(CPU_USAGE_Handle handle)
void EST_setRsOnLineId_pu(EST_Handle handle, const _iq Id_pu)
FILTER_FO_Obj filter[6]
the 3-current and 3-voltage filters for offset calculation
Definition: proj_lab11a.c:86
void HAL_readDrvData(HAL_Handle handle, DRV_SPI_8301_Vars_t *Spi_8301_Vars)
void EST_setRsOnLineFilterParams(EST_Handle handle, const EST_RsOnLineFilterType_e filterType, const _iq filter_0_b0, const _iq filter_0_a1, const _iq filter_0_y1, const _iq filter_1_b0, const _iq filter_1_a1, const _iq filter_1_y1)
MATH_vec2 gVdq_out_pu
contains the output Vd and Vq from the current controllers
Definition: proj_lab11a.c:115
bool Flag_enableFieldWeakening
Definition: main.h:140
static void TRAJ_run(TRAJ_Handle handle)
HAL_PwmData_t gPwmData
contains the three pwm values -1.0 - 0%, 1.0 - 100%
Definition: proj_lab11a.c:105
#define USER_MOTOR_MAX_CURRENT
Definition: user.h:407
static void FW_setMinMax(FW_Handle fwHandle, const _iq outMin, const _iq outMax)
_iq angleDelayComp(const _iq fm_pu, const _iq angleUncomp_pu)
The angleDelayComp function compensates for the delay introduced.
Definition: proj_lab11a.c:793
void EST_getIdq_pu(EST_Handle handle, MATH_vec2 *pIdq_pu)
float _IQ30toF(long A)
FW_Obj fw
Definition: proj_lab11a.c:76
void main(void)
Definition: proj_lab11a.c:185
void runFieldWeakening(void)
Definition: proj_lab11a.c:864
void USER_checkForErrors(USER_Params *pUserParams)
Checks for errors in the user parameter values.
MATH_vec2 gIdq_pu
contains the Id and Iq measured values
Definition: proj_lab11a.c:117
_iq gIs_Max_squared_pu
Definition: proj_lab11a.c:165
SVGEN_Handle SVGEN_init(void *pMemory, const size_t numBytes)
void EST_setEstParams(EST_Handle handle, USER_Params *pUserParams)
_iq Flux_Wb
Definition: main.h:164
#define GLOBAL_Q
_iq USER_computeTorque_Ls_Id_Iq_pu_to_Nm_sf(void)
Computes the scale factor needed to convert from torque created by Ld, Lq, Id and Iq...
_iq USER_computeFlux_pu_to_Wb_sf(void)
Computes the scale factor needed to convert from per unit to Wb.
SVGENCURRENT_Handle svgencurrentHandle
Definition: proj_lab11a.c:89
void EST_setLs_d_pu(EST_Handle handle, const _iq Ls_d_pu)
void runOffsetsCalculation(void)
Definition: proj_lab11a.c:895
float float_t
static void PID_run(PID_Handle handle, const _iq refValue, const _iq fbackValue, _iq *pOutValue)
static void TRAJ_setMinValue(TRAJ_Handle handle, const _iq minValue)
void EST_run(EST_Handle handle, const MATH_vec2 *pIab_pu, const MATH_vec2 *pVab_pu, const _iq dcBus_pu, const _iq speed_ref_pu)
#define USER_NUM_PWM_TICKS_PER_ISR_TICK
DECIMATION.
Definition: user.h:184
_iq gFlux_pu_to_VpHz_sf
Definition: proj_lab11a.c:155