/* * This program controls the rotational speed and direction of * a DC motor. * * The EduBase board has a quad half-H-bridge motor driver * (TB6612FNG), which is capable of driving two DC motors * or a stepper motor with up to 15V and 1.2A continuous current. * * The enable pins of the half-bridge are connected to PB7-4. * These pins are shared with the LEDs. * The PWM inputs are connected to PB0 and PB1. * * The four output pins of the motor driver device are connected to * the blue terminals marked M1, M2, M3, and M4. Use of external * power supply for motor is recommended. External power should be * connected to the terminal T3 and the jumper J4 should be at EXT. * * This program uses PB5, 4 for direction control and PB0 for * PWM control. The outputs are terminals M3 and M4. * The PWM is generated by TIM8_CH2. * * PWM1 - PB0 - TIM8_CH2 - AF3 * LED1 - PB5 * LED0 - PB4 * * PWM2 - PB1 - TIM8_CH3 - AF3 * LED2 - PB6 * LED3 - PB7 */ #include "stm32f4xx.h" void delayMs(int n); int main(void) { int pw = 0; RCC->AHB1ENR |= 2; /* enable GPIOB clock */ // set pins as output to control H-bridge GPIOB->MODER &= ~0x0000ff00; /* clear pin mode */ GPIOB->MODER |= 0x00005500; /* set pins to output mode */ // configure PB0 as TIM8_CH2 PWM output GPIOB->AFR[0] &= ~0x0000000F; GPIOB->AFR[0] |= 0x00000003; /* PB0 pin for TIM8 */ GPIOB->MODER &= ~0x00000003; GPIOB->MODER |= 0x00000002; /* use alternate function */ /* setup TIM8_CH2 */ RCC->APB2ENR |= 2; /* enable TIM8 clock */ TIM8->PSC = 0; /* divided by 10 */ TIM8->ARR = 4000 - 1; /* divided by 3636 */ TIM8->CNT = 0; /* clear counter */ TIM8->CCMR1 = 0x6000; /* PWM mode */ TIM8->CCER = 0x0050; /* enable PWM Ch2N and output */ TIM8->CCR2 = 100 - 1; /* pulse width 1/3 of the period */ TIM8->BDTR |= 0x8000; /* enable output */ TIM8->CR1 = 1; /* enable timer */ while(1) { /* decrease the pulse width gradually */ for (pw = 3900; pw >100; pw -= 20) { TIM8->CCR2 = pw; delayMs(50); } /* increase the pulse width gradually */ for (pw = 100; pw < 3900; pw += 20) { TIM8->CCR2 = pw; delayMs(50); } /* reverse the direction */ GPIOB->BSRR = 0x00100000; GPIOB->BSRR = 0x00000020; /* decrease the pulse width gradually */ for (pw = 3900; pw >100; pw -= 20) { TIM8->CCR2 = pw; delayMs(50); } /* increase the pulse width gradually */ for (pw = 100; pw < 3900; pw += 20) { TIM8->CCR2 = pw; delayMs(50); } /* reverse the direction */ GPIOB->BSRR = 0x00000010; GPIOB->BSRR = 0x00200000; } } /* 16 MHz SYSCLK */ void delayMs(int n) { int i; for (; n > 0; n--) for (i = 0; i < 3195; i++) ; }