Project added for completion
This commit is contained in:
parent
47d08fa8f6
commit
83189c41da
|
@ -0,0 +1,106 @@
|
|||
#include <stdlib.h>
|
||||
|
||||
#include "rtos.h"
|
||||
|
||||
#include "clock.h"
|
||||
#include "cpu.h"
|
||||
#include "timer_a1.h"
|
||||
|
||||
#include "inc/msp432p401r.h"
|
||||
|
||||
#define THREADS 2
|
||||
#define PERIODIC_THREADS 2
|
||||
#define SIZE 100
|
||||
|
||||
typedef struct Tcb {
|
||||
int32_t *sp; // stack pointer
|
||||
struct Tcb *next; // linked-list
|
||||
int32_t *blocked; // shows on which semaphore it is blocked
|
||||
} Tcb_t;
|
||||
|
||||
PeriodicEvent_t periodic_event_threads[PERIODIC_THREADS];
|
||||
|
||||
Tcb_t tcbs[THREADS];
|
||||
Tcb_t *run_pt;
|
||||
int32_t stacks[THREADS][SIZE];
|
||||
|
||||
void RunPeriodicEvents(void);
|
||||
|
||||
void __attribute__((naked))
|
||||
SysTick_Handler(void) { // 1) Saves R0-R3,R12,LR,PC,PSR
|
||||
__asm( // 2) Prevent interrupt during switch
|
||||
// 3) Save remaining regs r4-11
|
||||
// 4) R0=pointer to run_pt, old thread
|
||||
// 5) Save SP into TCB
|
||||
// 6) R1 = run_pt, new thread
|
||||
// 7) new thread SP; SP = run_pt->sp;
|
||||
// 8) restore regs r4-11
|
||||
// 9) tasks run with interrupts enabled
|
||||
); // 10) restore R0-R3,R12,LR,PC,PSR
|
||||
}
|
||||
|
||||
void __attribute__((naked))
|
||||
StartOS(void) {
|
||||
__asm(// currently running thread
|
||||
// R2 = value of run_pt
|
||||
// new thread SP; SP = run_pt->sp;
|
||||
// restore regs r4-11
|
||||
// restore regs r0-3
|
||||
// discard LR from initial stack
|
||||
// start location
|
||||
// discard PSR
|
||||
// Enable interrupts at processor level
|
||||
); // start first thread
|
||||
}
|
||||
|
||||
void SetInitialStack(int idx) {
|
||||
// Write this code
|
||||
}
|
||||
|
||||
// Initialize operating system, disable interrupts
|
||||
// Initialize OS controlled I/O: systick, bus clock as fast as possible
|
||||
void RoundRobinInit(void) {
|
||||
CPU_cpsid();
|
||||
ClockInit48MHz();
|
||||
// Write TimerA1Init here 1000 Hz
|
||||
}
|
||||
|
||||
void AddThreads(void (**threads)(void)) {
|
||||
// Write this code
|
||||
}
|
||||
|
||||
void AddPeriodicEventThreads(PeriodicEvent_t *periodic_events) {
|
||||
// Write this code
|
||||
}
|
||||
|
||||
void RoundRobinLaunch(uint32_t time_slice_cycles) {
|
||||
SysTick->CTRL = 0; // 1) disable SysTick during setup
|
||||
SysTick->LOAD = time_slice_cycles - 1; // 2) reload value sets period
|
||||
SysTick->VAL = 0; // 3) any write to current clears it
|
||||
SCB->SHP[11] = 7 << 5; // set priority into top 3 bits of 8-bit register
|
||||
SysTick->CTRL = 0x00000007; // 4) enable SysTick with core clock and interrupts
|
||||
StartOS(); // start on the first task
|
||||
}
|
||||
|
||||
void RunPeriodicEvents(void) {
|
||||
// Write this code (no sleep decreasing)
|
||||
}
|
||||
|
||||
void Scheduler(void) {
|
||||
// Write this code (no sleep check)
|
||||
}
|
||||
|
||||
void Suspend(void) {
|
||||
SysTick->VAL = 0; // any write to current clears it
|
||||
SCB->ICSR |= SCB_ICSR_PENDSTSET_Msk; // trigger SysTick
|
||||
}
|
||||
|
||||
// Decrement semaphore
|
||||
void Wait(int32_t *sema_pt) {
|
||||
// Write this code similar to RTOS3
|
||||
}
|
||||
|
||||
// Increment semaphore
|
||||
void Signal(int32_t *sema_pt) {
|
||||
// Write this code similar to RTOS3
|
||||
}
|
|
@ -0,0 +1,18 @@
|
|||
#ifndef RTOS_H
|
||||
#define RTOS_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
typedef struct PeriodicEvent {
|
||||
void (*event)(void);
|
||||
uint32_t period_ms;
|
||||
} PeriodicEvent_t;
|
||||
|
||||
void RoundRobinInit(void);
|
||||
void AddThreads(void (**threads)(void));
|
||||
void AddPeriodicEventThreads(PeriodicEvent_t *periodic_events);
|
||||
void RoundRobinLaunch(uint32_t time_slice_cycles);
|
||||
void Wait(int32_t *sema_pt);
|
||||
void Signal(int32_t *sema_pt);
|
||||
|
||||
#endif /* RTOS_H */
|
|
@ -0,0 +1,77 @@
|
|||
CC = arm-none-eabi-gcc
|
||||
|
||||
# The location of the C compiler
|
||||
# ARMGCC_ROOT is used by some makefiles that need to know where the compiler
|
||||
# is installed.
|
||||
ARMGCC_BIN := ${shell which ${CC}}
|
||||
ifeq (${shell test -h ${ARMGCC_BIN} && echo "true" || echo "false"}, true)
|
||||
ARMGCC_ROOT := ${shell dirname ${shell readlink ${ARMGCC_BIN}}}/..
|
||||
else
|
||||
ARMGCC_ROOT := ${shell dirname ${ARMGCC_BIN}}/..
|
||||
endif
|
||||
|
||||
# Search for source files that are not in this directory
|
||||
VPATH = ../common/
|
||||
|
||||
OBJECTS = main.o rtos.o timer_a1.o bump.o reflectance.o delay.o motor.o pwm.o cpu.o clock.o system.o startup.o syscalls.o
|
||||
|
||||
NAME = lab
|
||||
|
||||
CFLAGS = -I.. -I../inc -I../common \
|
||||
-D__MSP432P401R__ \
|
||||
-DDeviceFamily_MSP432P401x \
|
||||
-mcpu=cortex-m4 \
|
||||
-march=armv7e-m \
|
||||
-mthumb \
|
||||
-std=c99 \
|
||||
-mfloat-abi=hard \
|
||||
-mfpu=fpv4-sp-d16 \
|
||||
-ffunction-sections \
|
||||
-fdata-sections \
|
||||
-gstrict-dwarf \
|
||||
-Wall \
|
||||
-I$(ARMGCC_ROOT)/arm-none-eabi/include/newlib-nano \
|
||||
-I$(ARMGCC_ROOT)/arm-none-eabi/include
|
||||
|
||||
LFLAGS = -Wl,-T,../config.lds \
|
||||
-Wl,-Map,$(NAME).map \
|
||||
-march=armv7e-m \
|
||||
-mthumb \
|
||||
-mfloat-abi=hard \
|
||||
-mfpu=fpv4-sp-d16 \
|
||||
-static \
|
||||
-Wl,--gc-sections \
|
||||
-lgcc \
|
||||
-lc \
|
||||
-lm \
|
||||
-lnosys \
|
||||
--specs=nano.specs
|
||||
|
||||
all: $(NAME).out
|
||||
@echo "SUCCESS: Compilation completed successfully."
|
||||
|
||||
%.o: %.c
|
||||
@$(CC) $(CFLAGS) -g $< -c -o $@
|
||||
|
||||
cpu.o: ../common/cpu.c
|
||||
@$(CC) $(CFLAGS) $< -c -o $@
|
||||
|
||||
clock.o: ../common/clock.c
|
||||
@$(CC) $(CFLAGS) $< -c -o $@
|
||||
|
||||
system.o: ../system.c
|
||||
@$(CC) $(CFLAGS) $< -c -o $@
|
||||
|
||||
startup.o: ../startup.c
|
||||
@$(CC) $(CFLAGS) $< -c -o $@
|
||||
|
||||
syscalls.o: ../syscalls.c
|
||||
@$(CC) $(CFLAGS) $< -c -o $@
|
||||
|
||||
$(NAME).out: $(OBJECTS)
|
||||
@$(CC) $(OBJECTS) $(LFLAGS) -o $(NAME).out
|
||||
|
||||
clean: # Redirecting both the stderr and stdout to /dev/null
|
||||
@rm -f $(OBJECTS) > /dev/null 2>&1
|
||||
@rm -f $(NAME).out > /dev/null 2>&1
|
||||
@rm -f $(NAME).map > /dev/null 2>&1
|
|
@ -0,0 +1,107 @@
|
|||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "rtos.h"
|
||||
#include "pwm.h"
|
||||
#include "bump.h"
|
||||
#include "reflectance.h"
|
||||
#include "motor.h"
|
||||
#include "delay.h"
|
||||
|
||||
#include "inc/msp432p401r.h"
|
||||
|
||||
// bit-banded addresses, positive logic
|
||||
#define SW2IN ((*((volatile uint8_t *)(0x42098010)))^1)
|
||||
#define SW1IN ((*((volatile uint8_t *)(0x42098004)))^1)
|
||||
|
||||
// bit-banded address
|
||||
#define REDLED (*((volatile uint8_t *)(0x42098040)))
|
||||
|
||||
// bit-banded addresses
|
||||
#define BLUEOUT (*((volatile uint8_t *)(0x42098068)))
|
||||
#define GREENOUT (*((volatile uint8_t *)(0x42098064)))
|
||||
#define REDOUT (*((volatile uint8_t *)(0x42098060)))
|
||||
|
||||
#define START_REFLECTANCE 9
|
||||
|
||||
int32_t bump_pressed; // semaphore
|
||||
|
||||
uint8_t bump_data, reflectance_data;
|
||||
|
||||
void SwitchInit(void) {
|
||||
P1->SEL0 &= ~0x12;
|
||||
P1->SEL1 &= ~0x12; // 1) configure P1.4 and P1.1 as GPIO
|
||||
P1->DIR &= ~0x12; // 2) make P1.4 and P1.1 in
|
||||
P1->REN |= 0x12; // 3) enable pull resistors on P1.4 and P1.1
|
||||
P1->OUT |= 0x12; // P1.4 and P1.1 are pull-up
|
||||
}
|
||||
|
||||
void RedLEDInit(void) {
|
||||
P1->SEL0 &= ~0x01;
|
||||
P1->SEL1 &= ~0x01; // 1) configure P1.0 as GPIO
|
||||
P1->DIR |= 0x01; // 2) make P1.0 out
|
||||
}
|
||||
|
||||
void ColorLEDInit(void) {
|
||||
P2->SEL0 &= ~0x07;
|
||||
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 Task1(void) {
|
||||
while (true) {
|
||||
if (SW1IN && SW2IN) {
|
||||
GREENOUT = 1;
|
||||
} else {
|
||||
GREENOUT = 0;
|
||||
}
|
||||
if (SW1IN || SW2IN) {
|
||||
REDLED = 1;
|
||||
} else {
|
||||
REDLED = 0;
|
||||
}
|
||||
if (SW1IN) {
|
||||
BLUEOUT = 1;
|
||||
} else {
|
||||
BLUEOUT = 0;
|
||||
}
|
||||
if (SW2IN) {
|
||||
REDOUT = 1;
|
||||
} else {
|
||||
REDOUT = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Task2(void) {
|
||||
while (true) {
|
||||
// Motor goes forward and waits until bump is pressed
|
||||
// When pressed, go backward for some time and turn left for some time
|
||||
}
|
||||
}
|
||||
|
||||
void Task3(void) {
|
||||
// Read reflectance similar to Lab 3
|
||||
}
|
||||
|
||||
void Task4(void) {
|
||||
// Read bump and signal if any pressed
|
||||
}
|
||||
|
||||
int main(void) {
|
||||
BumpInit();
|
||||
ReflectanceInit();
|
||||
PWMInitMotor(?);
|
||||
MotorInit();
|
||||
RedLEDInit();
|
||||
ColorLEDInit();
|
||||
SwitchInit();
|
||||
RoundRobinInit();
|
||||
AddThreads((void (*[])(void)){Task1, Task2});
|
||||
AddPeriodicEventThreads((PeriodicEvent_t []){{Task3, 1}, {Task4, 100}});
|
||||
RoundRobinLaunch(48000); // 1ms
|
||||
return 0; // never executes
|
||||
}
|
Loading…
Reference in New Issue