1. 用於步進電機的 PWM 斬波介紹 前面的博文介紹了此節的內容,本文將不再重複,可以搜索博文《使用 LPC5536 的 eFlexPWM 外設生成用於步進電機的 PWM 斬波》。 可以把 LPC5536 中的 SCTimer(state control Timer) 看成半定製的定時器, SCTimer 是一個功能強大、靈活的定時器模塊,能夠創建複雜的 PWM 波形,並在最少或無需 CPU 干預的情況下執行其他高級定時和控制操作。 SCT 可以作為單個 32 位計數器操作,也可以作為兩個獨立的 16 位計數器在單向或雙向模式下操作。與大多數定時器一樣,SCT 支持選擇可與計數值進行比較的匹配寄存器,以及在檢測到某些預定義條件時可記錄當前計數值的捕獲寄存器。SCT 模塊支持多個單獨的事件,
下圖是步進電機其中一相的 H 橋的 PWM 信號,由 SCT 的 SCT0_OUT0 和 SCT0_OUT1 輸出。 匹配寄存器 MATCH[14] 定義了 PWM 的頻率,counter 計數到 MATCH[14] 時其將重新計數,同時拉低所有的 IO 信號, MATCH[1] 定義上半周 PWM 拉高的位置, MATCH[0] 定義了半周期的時刻,一般放在整個 PWM 周期的中點,當 counter 計數到 MATCH[0] 時拉低 PWM 信號。 各寄存器影響 PWM 波形如下圖所示: 初始化代碼: 通過設置 MATCH 寄存器不同的值即可改變 PWM 不同的占空比。
(0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[3].CTRL = temp; /* Event 4,PWM4 */ temp = SCT0->EV[4].CTRL; temp &= 0xFF800000; temp |= (4UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[4].CTRL = temp; /* Event 5,PWM5 */ temp = SCT0->EV[5].CTRL; temp &= 0xFF800000; temp |= (5UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[5].CTRL = temp; /* Event 6,PWM6 */ temp = SCT0->EV[6].CTRL; temp &= 0xFF800000; temp |= (6UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[6].CTRL = temp; /* Event 7,PWM7 */ temp = SCT0->EV[7].CTRL; temp &= 0xFF800000; temp |= (7UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[7].CTRL = temp; /* Event 8,PWM8 */ temp = SCT0->EV[8].CTRL; temp &= 0xFF800000; temp |= (8UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[8].CTRL = temp; /* SCT_OUT4 ---> PWM0 EXT_Sync NO AUTOLIMIT: EVENT 9(MATCH[9]) ---> SCT_OUT4 Fall EVENT 14(MATCH[14]) ---> SCT_OUT4 Rise */ SCT0->MATCH[9] = (uint32_t)(MCU_CLOCK_FREQ/M1_PWM_FREQ/2UL - 1UL); SCT0->MATCHREL[9] = (uint32_t)(MCU_CLOCK_FREQ/M1_PWM_FREQ/2UL - 1UL); /* Event 9, Sync eFlexPWM0 */ temp = SCT0->EV[9].CTRL; temp &= 0xFF800000; temp |= (9UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[9].CTRL = temp; /* SCT0_OUT4 */ SCT0->OUT[4].SET = (1UL << 14UL); SCT0->OUT[4].CLR = (1UL << 9UL); /* Event 10 */ temp = SCT0->EV[10].CTRL; temp &= 0xFF800000; temp |= (10UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[10].CTRL = temp; /* Event 11 */ temp = SCT0->EV[11].CTRL; temp &= 0xFF800000; temp |= (11UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[11].CTRL = temp; /* Event 12 */ temp = SCT0->EV[12].CTRL; temp &= 0xFF800000; temp |= (12UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[12].CTRL = temp; /* Event 13 */ temp = SCT0->EV[13].CTRL; temp &= 0xFF800000; temp |= (13UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[13].CTRL = temp; /* Event 15 */ temp = SCT0->EV[15].CTRL; temp &= 0xFF800000; temp |= (15UL << 0UL)| /* MATCHSEL select MATCH register */ (0UL << 4UL)| /* HEVENT Select L/H counter. Do not set this bit if UNIFY = 1 */ (0UL << 5UL)| /* OUTSEL Input 0/output 1 select */ (0UL << 6UL)| /* IOSEL Selects the input or output signal number */ (0UL << 10UL)| /* IOCOND Selects the I/O condition for event n, 00 Low,01 Rise,10 Fall,11 High */ (0x01UL<< 12UL)| /* COMBMODE Selects how the specified match and I/O condition are used and combined. 01 match Only */ (0x0UL << 14UL)| /* STATELD STATEV value is added (0) or loaded (1) into STATE */ (0x0UL << 15UL)| /* STATEV This value is loaded into or added to the state */ (0x0UL << 20UL)| /* MATCHMEM If this bit is zero, a match is only be active during the cycle */ (0x0UL << 21UL); /* DIRECTION BIDIR mode,0 Direction independent.1 Counting up.2 Counting down. */ SCT0->EV[15].CTRL = temp; /* Configure the OUT registers for the SCT outputs */ /* selects event m to set output n,bit 0 with event 0, etc.). */ /* PWM1 OUT0 */ SCT0->OUT[0].SET = 0UL; SCT0->OUT[0].CLR = 0UL; /* PWM2 OUT1 */ SCT0->OUT[1].SET = 0UL; SCT0->OUT[1].CLR = 0UL; //PWM3 OUT2 SCT0->OUT[2].SET = 0UL; SCT0->OUT[2].CLR = 0; /* PWM4 OUT3 */ SCT0->OUT[3].SET = 0UL; SCT0->OUT[3].CLR = 0UL; /* PWM5 OUT5 */ SCT0->OUT[5].SET = 0UL; SCT0->OUT[5].CLR = 0UL; /* PWM6 OUT6 */ SCT0->OUT[6].SET = 0UL; SCT0->OUT[6].CLR = 0UL; /* PWM7 OUT7 */ SCT0->OUT[7].SET = 0UL; SCT0->OUT[7].CLR = 0UL; /* PWM8 OUT8 */ SCT0->OUT[8].SET = 0UL; SCT0->OUT[8].CLR = 0UL; /* OUT9 */ SCT0->OUT[9].SET = 0UL; SCT0->OUT[9].CLR = 0UL; /* FINALLY ... now let's run it. Clearing bit 2 of the CTRL register takes it out of HALT. */ SCT0->CTRL &= (uint32_t)(~(1UL << 2UL)); /* HALT_L = 0,START COUNTER */ // NVIC_SetPriority (SCT0_IRQn, 0UL); // NVIC_EnableIRQ(SCT0_IRQn); }
3. 實際效果 以上是使用 SCT生成需要的 PWM 的波形的過程,在完整的步進電機控制中這種 PWM 斬波模式可以實現比較好的電流波形,紋波比較小,藍色為 PWM 信號,黃色為電流信號。 https://www.nxp.com.cn/docs/en/reference-manual/LPC553xRM.pdf |