123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623 |
- /************************************************************************
- Project: Welling Motor Control Paltform
- Filename: mathtool.c
- Partner Filename: mathtool.h
- Description: The math function
- Complier: IAR Embedded Workbench for ARM 7.80, IAR Systems.
- CPU TYPE : GD32F3x0
- *************************************************************************
- Copyright (c) 2018 Welling Motor Technology(Shanghai) Co. Ltd.
- All rights reserved.
- *************************************************************************
- *************************************************************************
- Revising History (ECL of this file):
- ************************************************************************/
- /************************************************************************
- Beginning of File, do not put anything above here except notes
- Compiler Directives:
- *************************************************************************/
- #ifndef _MATHTOOL_C_
- #define _MATHTOOL_C_
- #endif
- /************************************************************************
- Included File:
- *************************************************************************/
- #include "syspar.h"
- #include "user.h"
- /************************************************************************
- Constant Table:
- *************************************************************************/
- static const SWORD mth_swSinTab[SINTABSIZE] = {
- 0, // 0
- 804, // 1
- 1608, // 2
- 2411, // 3
- 3212, // 4
- 4011, // 5
- 4808, // 6
- 5602, // 7
- 6393, // 8
- 7180, // 9
- 7962, // 10
- 8740, // 11
- 9512, // 12
- 10279, // 13
- 11039, // 14
- 11793, // 15
- 12540, // 16
- 13279, // 17
- 14010, // 18
- 14733, // 19
- 15447, // 20
- 16151, // 21
- 16846, // 22
- 17531, // 23
- 18205, // 24
- 18868, // 25
- 19520, // 26
- 20160, // 27
- 20788, // 28
- 21403, // 29
- 22006, // 30
- 22595, // 31
- 23170, // 32
- 23732, // 33
- 24279, // 34
- 24812, // 35
- 25330, // 36
- 25833, // 37
- 26320, // 38
- 26791, // 39
- 27246, // 40
- 27684, // 41
- 28106, // 42
- 28511, // 43
- 28899, // 44
- 29269, // 45
- 29622, // 46
- 29957, // 47
- 30274, // 48
- 30572, // 49
- 30853, // 50
- 31114, // 51
- 31357, // 52
- 31581, // 53
- 31786, // 54
- 31972, // 55
- 32138, // 56
- 32286, // 57
- 32413, // 58
- 32522, // 59
- 32610, // 60
- 32679, // 61
- 32729, // 62
- 32758, // 63
- 32767, // 64
- 32758, // 65
- 32729, // 66
- 32679, // 67
- 32610, // 68
- 32522, // 69
- 32413, // 70
- 32286, // 71
- 32138, // 72
- 31972, // 73
- 31786, // 74
- 31581, // 75
- 31357, // 76
- 31114, // 77
- 30853, // 78
- 30572, // 79
- 30274, // 80
- 29957, // 81
- 29622, // 82
- 29269, // 83
- 28899, // 84
- 28511, // 85
- 28106, // 86
- 27684, // 87
- 27246, // 88
- 26791, // 89
- 26320, // 90
- 25833, // 91
- 25330, // 92
- 24812, // 93
- 24279, // 94
- 23732, // 95
- 23170, // 96
- 22595, // 97
- 22006, // 98
- 21403, // 99
- 20788, // 100
- 20160, // 101
- 19520, // 102
- 18868, // 103
- 18205, // 104
- 17531, // 105
- 16846, // 106
- 16151, // 107
- 15447, // 108
- 14733, // 109
- 14010, // 110
- 13279, // 111
- 12540, // 112
- 11793, // 113
- 11039, // 114
- 10279, // 115
- 9512, // 116
- 8740, // 117
- 7962, // 118
- 7180, // 119
- 6393, // 120
- 5602, // 121
- 4808, // 122
- 4011, // 123
- 3212, // 124
- 2411, // 125
- 1608, // 126
- 804, // 127
- 0, // 128
- -804, // 129
- -1608, // 130
- -2411, // 131
- -3212, // 132
- -4011, // 133
- -4808, // 134
- -5602, // 135
- -6393, // 136
- -7180, // 137
- -7962, // 138
- -8740, // 139
- -9512, // 140
- -10279, // 141
- -11039, // 142
- -11793, // 143
- -12540, // 144
- -13279, // 145
- -14010, // 146
- -14733, // 147
- -15447, // 148
- -16151, // 149
- -16846, // 150
- -17531, // 151
- -18205, // 152
- -18868, // 153
- -19520, // 154
- -20160, // 155
- -20788, // 156
- -21403, // 157
- -22006, // 158
- -22595, // 159
- -23170, // 160
- -23732, // 161
- -24279, // 162
- -24812, // 163
- -25330, // 164
- -25833, // 165
- -26320, // 166
- -26791, // 167
- -27246, // 168
- -27684, // 169
- -28106, // 170
- -28511, // 171
- -28899, // 172
- -29269, // 173
- -29622, // 174
- -29957, // 175
- -30274, // 176
- -30572, // 177
- -30853, // 178
- -31114, // 179
- -31357, // 180
- -31581, // 181
- -31786, // 182
- -31972, // 183
- -32138, // 184
- -32286, // 185
- -32413, // 186
- -32522, // 187
- -32610, // 188
- -32679, // 189
- -32729, // 190
- -32758, // 191
- -32768, // 192
- -32758, // 193
- -32729, // 194
- -32679, // 195
- -32610, // 196
- -32522, // 197
- -32413, // 198
- -32286, // 199
- -32138, // 200
- -31972, // 201
- -31786, // 202
- -31581, // 203
- -31357, // 204
- -31114, // 205
- -30853, // 206
- -30572, // 207
- -30274, // 208
- -29957, // 209
- -29622, // 210
- -29269, // 211
- -28899, // 212
- -28511, // 213
- -28106, // 214
- -27684, // 215
- -27246, // 216
- -26791, // 217
- -26320, // 218
- -25833, // 219
- -25330, // 220
- -24812, // 221
- -24279, // 222
- -23732, // 223
- -23170, // 224
- -22595, // 225
- -22006, // 226
- -21403, // 227
- -20788, // 228
- -20160, // 229
- -19520, // 230
- -18868, // 231
- -18205, // 232
- -17531, // 233
- -16846, // 234
- -16151, // 235
- -15447, // 236
- -14733, // 237
- -14010, // 238
- -13279, // 239
- -12540, // 240
- -11793, // 241
- -11039, // 242
- -10279, // 243
- -9512, // 244
- -8740, // 245
- -7962, // 246
- -7180, // 247
- -6393, // 248
- -5602, // 249
- -4808, // 250
- -4011, // 251
- -3212, // 252
- -2411, // 253
- -1608, // 254
- -804, // 255
- 0 // 256
- };
- static const UWORD mth_uwArctanTab[ARCTANTABSIZE] = {
- 8192, // 0
- 4836, // 1
- 2555, // 2
- 1297, // 3
- 651, // 4
- 326, // 5
- 163, // 6
- 81, // 7
- 41, // 8
- 20, // 9
- 10, // 10
- 5, // 11
- 3, // 12
- 1, // 13
- 1, // 14
- 0 // 15
- };
- /************************************************************************
- Exported Functions:
- *************************************************************************/
- /***************************************************************
- Function: math_voSinCos;
- Description: SIN & COS table.
- Call by: ...;
- Input Variables: Angle
- Output/Return Variables: SIN, COS
- Subroutine Call: N/A;
- Reference: N/A
- ****************************************************************/
- void mth_voSinCos(UWORD angle, SINCOS *v)
- {
- SWORD mth_swThsEntPu, mth_swNxtEntPu, mth_swDltAngPu;
- UWORD mth_uwIpValPu;
- //=======================================================================
- // Calculate Cos(theta_p)
- //=======================================================================
- mth_swThsEntPu = mth_swSinTab[((angle + 8192) & 0x7fff) >> 7]; // High 8 bit, 32767 to 255 Q15-Q7=Q8
- mth_swNxtEntPu = mth_swSinTab[(((angle + 8192) & 0x7fff) >> 7) + 1];
- mth_swDltAngPu = mth_swNxtEntPu - mth_swThsEntPu;
- mth_uwIpValPu = (angle & 0x007f) * 256; // Low 7 bit, 127 to 32512
- v->swCosPu = (SWORD)(((SLONG)mth_swDltAngPu * (SLONG)mth_uwIpValPu >> 15) + mth_swThsEntPu);
- //=======================================================================
- // Calculate Sin(theta_p)
- //=======================================================================
- mth_swThsEntPu = mth_swSinTab[(angle & 0x7fff) >> 7]; // High 8 bit, 32767 to 255 Q15-Q7=Q8
- mth_swNxtEntPu = mth_swSinTab[((angle & 0x7fff) >> 7) + 1];
- mth_swDltAngPu = mth_swNxtEntPu - mth_swThsEntPu;
- mth_uwIpValPu = (angle & 0x007f) * 256; // Low 7 bit, 127 to 32512
- v->swSinPu = (SWORD)(((SLONG)mth_swDltAngPu * (SLONG)mth_uwIpValPu >> 15) + mth_swThsEntPu);
- }
- /***************************************************************
- Function: Lpf;
- Description: LowPass filter cof calculation;
- Call by: repeated functions;
- Input Variables: ulLpfTime_us, uwExeFreq(Hz),uwLPFCof
- Output/Return Variables: SLONG *slpLpfOut
- Subroutine Call: N/A;
- Reference: N/A
- ****************************************************************/
- void mth_voLPFilterCoef(ULONG ulLpfTime_us, ULONG ulExeFreq, UWORD *uwLPFCof)
- {
- // y(n) = y(n-1) + T/(T+tao)*[x(n) - y(n-1)] = T/(T+tao)*x(n) + tao/(T+tao)*y(n-1)
- // uwLPFCof = T/(T+tao) //Q15
- // ulExeFreq range(50Hz,50KHz)
- ULONG ulTCtrl_us; // control time: us
- if (ulExeFreq < 1)
- {
- ulExeFreq = 1;
- }
- ulTCtrl_us = 1000000 / ulExeFreq; // Unit:1us
- if ((ulTCtrl_us < 1) && (ulLpfTime_us < 1))
- {
- ulLpfTime_us = 1;
- }
- *uwLPFCof = (UWORD)((ulTCtrl_us << 15) / (ulTCtrl_us + ulLpfTime_us)); // Q15
- }
- /***************************************************************
- Function: Lpf;
- Description: LowPass filter;
- Call by: repeated functions;
- Input Variables: swLpfIn,uwLPFCof
- Output/Return Variables: SLONG *slpLpfOut
- Subroutine Call: N/A;
- Reference: N/A
- ****************************************************************/
- void mth_voLPFilter(SWORD swLpfIn, LPF_OUT *out)
- {
- // swLpfIn(Q15);
- // ulLpfTime_us:Unit:1us (Range0.000ms~20000.000ms)
- // uwExeFreq:Unit:Hz the frequence of call
- // slLpfOut
- UWORD uwKx;
- SLONG_UNION sluTmp;
- SLONG slTmp1;
- uwKx = out->uwKx; // Q15
- sluTmp.sl = out->slY.sl;
- slTmp1 = sluTmp.sl + (uwKx * swLpfIn << 1) - (uwKx * sluTmp.sw.hi << 1) - (uwKx * sluTmp.sw.low >> 15);
- out->slY.sl = slTmp1; // Q31
- }
- /***************************************************************
- Function: mth_slSqrt;
- Description: sqrt;
- Call by: repeated functions;
- Input Variables:
- Output/Return Variables:
- Subroutine Call: N/A;
- Reference: N/A
- ****************************************************************/
- SLONG mth_slSqrt(SLONG slInput)
- {
- SLONG slRemainder;
- SLONG slRoot;
- SWORD swN;
- slRoot = 0;
- if (slInput < 0)
- {
- slInput = 0;
- }
- if ((slInput - 2147352578) > 0) // slInput>(32767*32767*2)
- {
- slRoot = 46339;
- return slRoot;
- }
- if (slInput > 0)
- {
- for (swN = 15; swN >= 0; swN--)
- {
- slRemainder = slInput - (SLONG)slRoot * slRoot;
- if (slRemainder > 0)
- {
- slRoot = slRoot + (1 << swN);
- }
- else
- {
- slRoot = slRoot - (1 << swN);
- if (slRoot <= 0)
- {
- slRoot = 0;
- }
- }
- }
- }
- else
- {
- slRoot = 0;
- }
- return slRoot;
- }
- /***************************************************************
- Function: mth_slRamp;
- Description: ramp;
- Call by: repeated functions;
- Input Variables:
- Output/Return Variables:
- Subroutine Call: N/A;
- Reference: N/A
- ****************************************************************/
- SLONG mth_slRamp(SLONG slInput, SLONG slDelta, SLONG slOutputLimit)
- {
- SLONG slOutput;
- slOutput = slInput + slDelta;
- if (slOutput > slOutputLimit)
- {
- slOutput = slOutputLimit;
- }
- return slOutput;
- }
- /***************************************************************
- Function: mth_voArctan;
- Description: arctan;
- Call by: repeated functions;
- Input Variables:
- Output/Return Variables:
- Subroutine Call: N/A;
- Reference: N/A
- ****************************************************************/
- UWORD mth_voArctan(const ARCTAN_IN *in) /* parasoft-suppress METRICS-28 "本项目圈复杂度无法更改,后续避免" */
- {
- UWORD uwQuadrant, uwStep;
- SLONG slX, slY, slCurAngle, slNewX;
- UWORD uwEstThetaPu;
- slCurAngle = 0;
- slX = in->swAlphaPu;
- slY = in->swBetaPu;
- if ((slX == 0) || (slY == 0))
- {
- if (slX == 0)
- {
- if (slY > 0)
- {
- uwEstThetaPu = 8192; // Q15
- }
- else if (slY < 0)
- {
- uwEstThetaPu = 24576; // Q15
- }
- else
- {
- uwEstThetaPu = 0;
- }
- }
- if (slY == 0)
- {
- if (slX > 0)
- {
- uwEstThetaPu = 0; // Q15
- }
- else if (slX < 0)
- {
- uwEstThetaPu = 16384; // Q15
- }
- else
- {
- //do nothing
- }
- }
- }
- else
- {
- if ((slX > 0) && (slY > 0)) // Quadrant 0, 0 < angle < 90
- {
- uwQuadrant = 0;
- }
- else if ((slX < 0) && (slY > 0)) // Quadrant 1, 90 < angle < 180
- {
- uwQuadrant = 1;
- slX = -slX;
- }
- else if ((slX < 0) && (slY < 0)) // Quadrant 2, 180 < angle < 270
- {
- uwQuadrant = 2;
- slX = -slX;
- slY = -slY;
- }
- else //if ((slX > 0) && (slY < 0)) // Quadrant 3, 270 < angle < 360
- {
- uwQuadrant = 3;
- slY = -slY;
- }
- for (uwStep = 0; uwStep < (ARCTANTABSIZE - 1); uwStep++)
- {
- if (slY > 0)
- {
- slNewX = slX + (slY >> uwStep);
- slY = slY - (slX >> uwStep);
- slX = slNewX;
- slCurAngle += mth_uwArctanTab[uwStep];
- }
- else if (slY < 0)
- {
- slNewX = slX - (slY >> uwStep);
- slY = slY + (slX >> uwStep);
- slX = slNewX;
- slCurAngle -= mth_uwArctanTab[uwStep];
- }
- else
- {
- slCurAngle = slCurAngle;
- }
- }
- switch (uwQuadrant)
- {
- case 0:
- slCurAngle = slCurAngle;
- break;
- case 1:
- slCurAngle = 32767 - slCurAngle;
- break;
- case 2:
- slCurAngle = 32767 + slCurAngle;
- break;
- case 3:
- slCurAngle = 65534 - slCurAngle;
- break;
- default:
- break;
- }
- slCurAngle = slCurAngle >> 1;
- if (slCurAngle > 32767)
- {
- slCurAngle = 32767;
- }
- else if (slCurAngle < 0)
- {
- slCurAngle = slCurAngle + 32768;
- }
- else
- {
- //do nothing
- }
- uwEstThetaPu = (UWORD)slCurAngle;
- }
- return uwEstThetaPu;
- }
- /************************************************************************
- Local Functions: N/A
- *************************************************************************/
- /*************************************************************************
- Copyright (c) 2018 Welling Motor Technology(Shanghai) Co., Ltd.
- All rights reserved.
- *************************************************************************/
- #ifdef _MATHTOOL_C_
- #undef _MATHTOOL_C_ /* parasoft-suppress MISRA2004-19_6 "本项目中无法更改,后续避免使用" */
- #endif
- /*************************************************************************
- End of this File (EOF):
- Do not put anything after this part!
- *************************************************************************/
|