lab6 fixpoint
This commit is contained in:
parent
3b38f6bfc4
commit
7fb97bcab7
|
@ -9,16 +9,13 @@ void (*capture_task)(uint16_t time);
|
||||||
// acknowledges the interrupt and calls a user function.
|
// acknowledges the interrupt and calls a user function.
|
||||||
void TimerA0CaptureInit(void (*task)(uint16_t time)) {
|
void TimerA0CaptureInit(void (*task)(uint16_t time)) {
|
||||||
capture_task = task;
|
capture_task = task;
|
||||||
|
|
||||||
P7->SEL0 |= 0x08;
|
P7->SEL0 |= 0x08;
|
||||||
P7->SEL1 &= ~0x08; // configure P7.3 as TA0CCP0
|
P7->SEL1 &= ~0x08; // configure P7.3 as TA0CCP0
|
||||||
P7->DIR &= ~0x08;
|
P7->DIR &= ~0x08;
|
||||||
|
|
||||||
TIMER_A0->CTL &= ~0x30; // halt Timer A0
|
TIMER_A0->CTL &= ~0x30; // halt Timer A0
|
||||||
TIMER_A0->CTL = 0x200; // SMCLK
|
TIMER_A0->CTL = 0x200; // SMCLK
|
||||||
|
|
||||||
TIMER_A0->CCTL[0] = 0x4910; // capture on rising edge, synchronous capture, capture mode, interrupt enabled
|
TIMER_A0->CCTL[0] = 0x4910; // capture on rising edge, synchronous capture, capture mode, interrupt enabled
|
||||||
|
|
||||||
TIMER_A0->EX0 &= ~0x7; // input clock divider /1
|
TIMER_A0->EX0 &= ~0x7; // input clock divider /1
|
||||||
|
|
||||||
NVIC->IP[2] = (NVIC->IP[2] & 0xFFFFFF00) | 0x00000002; // priority 2
|
NVIC->IP[2] = (NVIC->IP[2] & 0xFFFFFF00) | 0x00000002; // priority 2
|
||||||
|
@ -51,69 +48,59 @@ void TimerA3CaptureInit(void (*task0)(uint16_t time),
|
||||||
void (*task1)(uint16_t time)) {
|
void (*task1)(uint16_t time)) {
|
||||||
capture_task0 = task0;
|
capture_task0 = task0;
|
||||||
capture_task1 = task1;
|
capture_task1 = task1;
|
||||||
|
|
||||||
// Configure P10.4 and P10.5 as TA3.CCP0 and TA3.CCP1
|
|
||||||
P10->SEL0 |= 0x30; // Set SEL0 for bits 4 and 5
|
P10->SEL0 |= 0x30; // Set SEL0 for bits 4 and 5
|
||||||
P10->SEL1 &= ~0x30; // Clear SEL1 for bits 4 and 5
|
P10->SEL1 &= ~0x30; // Clear SEL1 for bits 4 and 5
|
||||||
P10->DIR &= ~0x30; // Set as inputs
|
P10->DIR &= ~0x30; // Set as inputs
|
||||||
|
|
||||||
// Halt Timer A3 and configure clock source
|
TIMER_A3->CTL &= ~0x30; // halt Timer A3
|
||||||
TIMER_A3->CTL &= ~0x0030; // Halt Timer A3
|
TIMER_A3->CTL = 0x200; // SMCLK
|
||||||
TIMER_A3->CTL = 0x0200; // Use SMCLK (12 MHz)
|
TIMER_A3->CCTL[0] = 0x4910; // rising, sync, capture, interrupt
|
||||||
|
TIMER_A3->CCTL[1] = 0x4910;
|
||||||
|
TIMER_A3->EX0 &= ~0x7; // input clock divider /1
|
||||||
|
|
||||||
// Configure capture compare channels 0 and 1
|
NVIC->IP[3] = (NVIC->IP[3] & 0xFF0000FF) | 0x00020300; // priority 2 and 3
|
||||||
TIMER_A3->CCTL[0] = 0x4910; // Rising edge, sync, capture, interrupt
|
|
||||||
TIMER_A3->CCTL[1] = 0x4910; // Same for channel 1
|
//? enabling something different??
|
||||||
|
NVIC->ISER[0] = (1 << 13) | (1 << 14); // enable 14 and 15
|
||||||
|
|
||||||
// Set input clock divider to /1
|
|
||||||
TIMER_A3->EX0 &= ~0x0007; // Clear TAIDEX bits
|
|
||||||
// TIMER_A3->EX0 = (TIMER_A3->EX0 & ~0x0007) | 0x0002;
|
|
||||||
|
|
||||||
// Set NVIC priorities for TA3_0 and TA3_N interrupts to priority 2
|
|
||||||
NVIC->IP[10] = (NVIC->IP[10] & 0xFFFF0000) | 0x00000202;
|
|
||||||
|
|
||||||
// Enable interrupts in NVIC
|
|
||||||
NVIC->ISER[1] = 0x0300; // Enable IRQ40 and IRQ41
|
|
||||||
|
|
||||||
// Start Timer A3 in continuous mode with clear
|
// Start Timer A3 in continuous mode with clear
|
||||||
TIMER_A3->CTL |= 0x0024; // TACLR | MC__CONTINUOUS
|
TIMER_A3->CTL |= 0x0024; // TACLR | MC__CONTINUOUS
|
||||||
}
|
}
|
||||||
|
|
||||||
// // The rising edge of P10.4 will cause an interrupt
|
// The rising edge of P10.4 will cause an interrupt
|
||||||
|
void TA3_0_IRQHandler(void) {
|
||||||
|
TIMER_A3->CCTL[0] &= ~0x0001; // ack
|
||||||
|
capture_task0(TIMER_A3->CCR[0]);
|
||||||
|
}
|
||||||
|
|
||||||
|
// The rising edge of P10.5 will cause an interrupt
|
||||||
|
void TA3_N_IRQHandler(void) {
|
||||||
|
TIMER_A3->CCTL[1] &= ~0x0001; // ack
|
||||||
|
capture_task1(TIMER_A3->CCR[1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
// #define PRESCALER_FACTOR 3
|
||||||
|
// static uint16_t prev_capture0 = 0;
|
||||||
|
// static uint16_t prev_capture1 = 0;
|
||||||
|
// // ISR for TA3 CCR0 (P10.4 rising edge)
|
||||||
// void TA3_0_IRQHandler(void) {
|
// void TA3_0_IRQHandler(void) {
|
||||||
|
// uint16_t current_capture = TIMER_A3->CCR[0];
|
||||||
|
// uint16_t period = current_capture - prev_capture0;
|
||||||
|
// prev_capture0 = current_capture;
|
||||||
|
|
||||||
// TIMER_A3->CCTL[0] &= ~0x0001; // Acknowledge interrupt
|
// TIMER_A3->CCTL[0] &= ~0x0001; // Acknowledge interrupt
|
||||||
// capture_task0(TIMER_A3->CCR[0]); // Execute user task
|
// capture_task0(period * PRESCALER_FACTOR); // Apply prescaler
|
||||||
// }
|
// }
|
||||||
|
|
||||||
// // The rising edge of P10.5 will cause an interrupt
|
// // ISR for TA3 CCR1 (P10.5 rising edge)
|
||||||
// void TA3_N_IRQHandler(void) {
|
// void TA3_N_IRQHandler(void) {
|
||||||
// if (TIMER_A3->CCTL[1] & 0x0001) { // Check if CCIFG1 is set
|
// if (TIMER_A3->CCTL[1] & 0x0001) { // Check CCIFG1
|
||||||
// TIMER_A3->CCTL[1] &= ~0x0001; // Acknowledge interrupt
|
// uint16_t current_capture = TIMER_A3->CCR[1];
|
||||||
// capture_task1(TIMER_A3->CCR[1]); // Execute task
|
// uint16_t period = current_capture - prev_capture1;
|
||||||
|
// prev_capture1 = current_capture;
|
||||||
|
|
||||||
|
// TIMER_A3->CCTL[1] &= ~0x0001; // Acknowledge interrupt
|
||||||
|
// capture_task1(period * PRESCALER_FACTOR); // Apply prescaler
|
||||||
// }
|
// }
|
||||||
// }
|
// }
|
||||||
|
|
||||||
#define PRESCALER_FACTOR 3
|
|
||||||
static uint16_t prev_capture0 = 0;
|
|
||||||
static uint16_t prev_capture1 = 0;
|
|
||||||
// ISR for TA3 CCR0 (P10.4 rising edge)
|
|
||||||
void TA3_0_IRQHandler(void) {
|
|
||||||
uint16_t current_capture = TIMER_A3->CCR[0];
|
|
||||||
uint16_t period = current_capture - prev_capture0;
|
|
||||||
prev_capture0 = current_capture;
|
|
||||||
|
|
||||||
TIMER_A3->CCTL[0] &= ~0x0001; // Acknowledge interrupt
|
|
||||||
capture_task0(period * PRESCALER_FACTOR); // Apply prescaler
|
|
||||||
}
|
|
||||||
|
|
||||||
// ISR for TA3 CCR1 (P10.5 rising edge)
|
|
||||||
void TA3_N_IRQHandler(void) {
|
|
||||||
if (TIMER_A3->CCTL[1] & 0x0001) { // Check CCIFG1
|
|
||||||
uint16_t current_capture = TIMER_A3->CCR[1];
|
|
||||||
uint16_t period = current_capture - prev_capture1;
|
|
||||||
prev_capture1 = current_capture;
|
|
||||||
|
|
||||||
TIMER_A3->CCTL[1] &= ~0x0001; // Acknowledge interrupt
|
|
||||||
capture_task1(period * PRESCALER_FACTOR); // Apply prescaler
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
191
lab5/main.c
191
lab5/main.c
|
@ -1,92 +1,147 @@
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
|
|
||||||
#include "timer_a1.h"
|
#include "../common/cpu.h"
|
||||||
#include "pwm.h"
|
#include "../common/motor.h"
|
||||||
#include "motor.h"
|
#include "../common/pwm.h"
|
||||||
#include "clock.h"
|
#include "../common/clock.h"
|
||||||
#include "cpu.h"
|
#include "../common/input_capture.h"
|
||||||
#include "bump.h"
|
#include "../common/timer_a1.h"
|
||||||
#include "delay.h"
|
#include "../common/tachometer.h"
|
||||||
|
|
||||||
#include "inc/msp432p401r.h"
|
#include "inc/msp432p401r.h"
|
||||||
|
|
||||||
// bit-banded addresses, positive logic
|
|
||||||
#define SW2IN ((*((volatile uint8_t *)(0x42098010)))^1)
|
|
||||||
#define SW1IN ((*((volatile uint8_t *)(0x42098004)))^1)
|
|
||||||
|
|
||||||
#define REDLED (*((volatile uint8_t *)(0x42098040)))
|
|
||||||
|
|
||||||
void TimedWaitTouchRelease(uint32_t time) {
|
|
||||||
Delay1ms(time); // run for a while and then stop
|
|
||||||
MotorStop();
|
|
||||||
while (!(SW1IN || SW2IN)) {} // wait for touch
|
|
||||||
while (SW1IN || SW2IN) {} // wait for release
|
|
||||||
}
|
|
||||||
|
|
||||||
void RedLEDInit(void) {
|
void RedLEDInit(void) {
|
||||||
P1->SEL0 &= ~0x01;
|
P1->SEL0 &= ~0x01;
|
||||||
P1->SEL1 &= ~0x01; // 1) configure P1.0 as GPIO
|
P1->SEL1 &= ~0x01; // 1) configure P1.0 as GPIO
|
||||||
P1->DIR |= 0x01; // 2) make P1.0 out
|
P1->DIR |= 0x01; // 2) make P1.0 out
|
||||||
}
|
}
|
||||||
|
|
||||||
void SwitchInit(void) {
|
// bit-banded address
|
||||||
P1->SEL0 &= ~0x12;
|
#define REDLED (*((volatile uint8_t *)(0x42098040)))
|
||||||
P1->SEL1 &= ~0x12; // 1) configure P1.4 and P1.1 as GPIO
|
|
||||||
P1->DIR &= ~0x12; // 2) make P1.4 and P1.1 in
|
void ColorLEDInit(void) {
|
||||||
P1->REN |= 0x12; // 3) enable pull resistors on P1.4 and P1.1
|
P2->SEL0 &= ~0x07;
|
||||||
P1->OUT |= 0x12; // P1.4 and P1.1 are pull-up
|
P2->SEL1 &= ~0x07; // 1) configure P2.2-P2.0 as GPIO
|
||||||
|
P2->DIR |= 0x07; // 2) make P2.2-P2.0 out
|
||||||
|
P2->DS |= 0x07; // 3) activate increased drive strength
|
||||||
|
P2->OUT &= ~0x07; // all LEDs off
|
||||||
}
|
}
|
||||||
|
|
||||||
void Task(void) {
|
// bit-banded addresses
|
||||||
static uint32_t time;
|
#define BLUEOUT (*((volatile uint8_t *)(0x42098068)))
|
||||||
++time;
|
#define GREENOUT (*((volatile uint8_t *)(0x42098064)))
|
||||||
|
#define REDOUT (*((volatile uint8_t *)(0x42098060)))
|
||||||
|
|
||||||
|
uint16_t period0, period1; // (1/SMCLK) units = 83.3 ns units
|
||||||
|
uint16_t first0, first1; // Timer A3 first edge, P10.4/.5
|
||||||
|
bool done0, done1; // set each rising
|
||||||
|
|
||||||
|
// max period is (2^16-1)*83.3 ns = 5.4612 ms
|
||||||
|
// min period determined by time to run ISR, which is about 1 us
|
||||||
|
void PeriodMeasure0(uint16_t time) {
|
||||||
|
REDOUT ^= 1;
|
||||||
|
period0 = time - first0; // 83.3 ns resolution
|
||||||
|
first0 = time; // setup for next
|
||||||
|
done0 = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// max period is (2^16-1)*83.3 ns = 5.4612 ms
|
||||||
|
// min period determined by time to run ISR, which is about 1 us
|
||||||
|
void PeriodMeasure1(uint16_t time) {
|
||||||
REDLED ^= 1;
|
REDLED ^= 1;
|
||||||
|
period1 = time - first1; // 83.3 ns resolution
|
||||||
|
first1 = time; // setup for next
|
||||||
|
done1 = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
int main_f(void) {
|
void dummy() {
|
||||||
ClockInit48MHz();
|
volatile int i = 1;
|
||||||
RedLEDInit();
|
i = i + 2;
|
||||||
TimerA1Init(&Task, 500); // 1000 Hz
|
return;
|
||||||
CPU_cpsie(); // Enable interrupts
|
|
||||||
while (true) {}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int main_s(void) {
|
|
||||||
ClockInit48MHz();
|
|
||||||
SwitchInit();
|
|
||||||
PWMInitMotor(7502); // your function
|
|
||||||
MotorInit(); // your function
|
|
||||||
while (true) {
|
|
||||||
TimedWaitTouchRelease(1000);
|
|
||||||
MotorForward(1500, 1500); // your function
|
|
||||||
TimedWaitTouchRelease(2000);
|
|
||||||
MotorBackward(1500, 1500); // your function
|
|
||||||
TimedWaitTouchRelease(2000);
|
|
||||||
MotorLeft(1200, 1200); // your function
|
|
||||||
TimedWaitTouchRelease(1000);
|
|
||||||
MotorRight(1200, 1200); // your function
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void checkBump() {
|
|
||||||
uint8_t bump = BumpRead();
|
|
||||||
if (~bump & BUMP_PINS)
|
|
||||||
MotorStop();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Write a program that uses PWM to move the robot
|
|
||||||
// but uses TimerA1 to periodically check the bump switches,
|
|
||||||
// stopping the robot on collision
|
|
||||||
int main(void) {
|
int main(void) {
|
||||||
ClockInit48MHz();
|
CPU_cpsid(); // Disable interrupts
|
||||||
BumpInit();
|
ClockInit48MHz(); // 48 MHz clock; 12 MHz Timer A clock
|
||||||
|
RedLEDInit();
|
||||||
|
ColorLEDInit();
|
||||||
PWMInitMotor(7502);
|
PWMInitMotor(7502);
|
||||||
MotorInit();
|
MotorInit();
|
||||||
MotorForward(1500, 1500);
|
TimerA1Init(&dummy, 1000);
|
||||||
TimerA1Init(checkBump, 15000);
|
TimerA3CaptureInit(&PeriodMeasure0, &PeriodMeasure1);
|
||||||
|
// MotorForward(3751, 3751); // 50%
|
||||||
|
// MotorForward(1000, 1000);
|
||||||
CPU_cpsie(); // Enable interrupts
|
CPU_cpsie(); // Enable interrupts
|
||||||
|
CPU_wfi(); // Wait for interrupt
|
||||||
while (true);
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint16_t speed_buf[500]; // RPM, radius 0.035m wheels
|
||||||
|
uint32_t period_buf[500]; // 1/12MHz = 0.083 usec
|
||||||
|
uint32_t duty; // 0 to 15000
|
||||||
|
uint32_t time; // in 0.01 sec
|
||||||
|
|
||||||
|
void Collect(void) {
|
||||||
|
GREENOUT ^= 1;
|
||||||
|
if (!done0) period0 = 0xFFFF - 1; // stopped
|
||||||
|
if (!done1) period1 = 0xFFFF - 1;
|
||||||
|
done0 = done1 = false; // set on subsequent
|
||||||
|
switch (time) {
|
||||||
|
case 0:
|
||||||
|
duty = 1875; // 25%
|
||||||
|
MotorForward(duty, duty);
|
||||||
|
break;
|
||||||
|
case 100:
|
||||||
|
duty = 3751; // 50%
|
||||||
|
MotorForward(duty, duty);
|
||||||
|
break;
|
||||||
|
case 200:
|
||||||
|
duty = 5626; // 75%
|
||||||
|
MotorForward(duty, duty);
|
||||||
|
break;
|
||||||
|
case 300:
|
||||||
|
duty = 3751; // 50%
|
||||||
|
MotorForward(duty, duty);
|
||||||
|
break;
|
||||||
|
case 400:
|
||||||
|
duty = 1875; // 25%
|
||||||
|
MotorForward(duty, duty);
|
||||||
|
break;
|
||||||
|
case 500:
|
||||||
|
MotorStop();
|
||||||
|
TIMER_A1->CTL &= ~0x30; // Halt timer A1
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
speed_buf[time] = 2000000 / period0;
|
||||||
|
period_buf[time] = period0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
++time;
|
||||||
|
}
|
||||||
|
|
||||||
|
int main_collect(void) {
|
||||||
|
CPU_cpsid(); // Disable interrupts
|
||||||
|
ClockInit48MHz(); // 48 MHz clock; 12 MHz Timer A clock
|
||||||
|
RedLEDInit();
|
||||||
|
ColorLEDInit();
|
||||||
|
PWMInitMotor(7502);
|
||||||
|
MotorInit();
|
||||||
|
TimerA3CaptureInit(&PeriodMeasure0, &PeriodMeasure1);
|
||||||
|
TimerA1Init(&Collect, 5000); // 100 Hz
|
||||||
|
CPU_cpsie(); // Enable interrupts
|
||||||
|
CPU_wfi(); // Wait for interrupt
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int main_tach(void) {
|
||||||
|
CPU_cpsid(); // Disable interrupts
|
||||||
|
ClockInit48MHz();
|
||||||
|
PWMInitMotor(7502);
|
||||||
|
MotorInit();
|
||||||
|
TachometerInit();
|
||||||
|
MotorForward(2000, 2000); // confirm if rotating forward
|
||||||
|
//MotorBackward(2000, 2000); // confirm if rotating backward
|
||||||
|
CPU_cpsie(); // Enable interrupts
|
||||||
|
CPU_wfi(); // Wait for interrupt
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
23
lab6/main.c
23
lab6/main.c
|
@ -1,13 +1,13 @@
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
|
|
||||||
#include "cpu.h"
|
#include "../common/cpu.h"
|
||||||
#include "motor.h"
|
#include "../common/motor.h"
|
||||||
#include "pwm.h"
|
#include "../common/pwm.h"
|
||||||
#include "clock.h"
|
#include "../common/clock.h"
|
||||||
#include "input_capture.h"
|
#include "../common/input_capture.h"
|
||||||
#include "timer_a1.h"
|
#include "../common/timer_a1.h"
|
||||||
#include "tachometer.h"
|
#include "../common/tachometer.h"
|
||||||
|
|
||||||
#include "inc/msp432p401r.h"
|
#include "inc/msp432p401r.h"
|
||||||
|
|
||||||
|
@ -56,8 +56,11 @@ void PeriodMeasure1(uint16_t time) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void dummy() {
|
void dummy() {
|
||||||
int i = 1;
|
volatile int i = 1;
|
||||||
|
i = i + 2;
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(void) {
|
int main(void) {
|
||||||
CPU_cpsid(); // Disable interrupts
|
CPU_cpsid(); // Disable interrupts
|
||||||
ClockInit48MHz(); // 48 MHz clock; 12 MHz Timer A clock
|
ClockInit48MHz(); // 48 MHz clock; 12 MHz Timer A clock
|
||||||
|
@ -65,8 +68,8 @@ int main(void) {
|
||||||
ColorLEDInit();
|
ColorLEDInit();
|
||||||
PWMInitMotor(7502);
|
PWMInitMotor(7502);
|
||||||
MotorInit();
|
MotorInit();
|
||||||
TimerA1Init(&dummy, 1000);
|
// TimerA1Init(&dummy, 1000);
|
||||||
// TimerA3CaptureInit(&PeriodMeasure0, &PeriodMeasure1);
|
TimerA3CaptureInit(&PeriodMeasure0, &PeriodMeasure1);
|
||||||
// MotorForward(3751, 3751); // 50%
|
// MotorForward(3751, 3751); // 50%
|
||||||
// MotorForward(1000, 1000);
|
// MotorForward(1000, 1000);
|
||||||
CPU_cpsie(); // Enable interrupts
|
CPU_cpsie(); // Enable interrupts
|
||||||
|
|
Loading…
Reference in New Issue