Update configs for newer pinout
This commit is contained in:
@@ -10,20 +10,14 @@
|
|||||||
#include "systick.h"
|
#include "systick.h"
|
||||||
#include <IRQ.h>
|
#include <IRQ.h>
|
||||||
|
|
||||||
//2 second filter (ADC is PID_TIM_HZ Hz)
|
void resetWatchdog() {
|
||||||
history<uint16_t, PID_TIM_HZ> rawTempFilter = {{0}, 0, 0};
|
|
||||||
|
|
||||||
void resetWatchdog()
|
|
||||||
{
|
|
||||||
//TODO
|
//TODO
|
||||||
}
|
}
|
||||||
|
|
||||||
uint16_t getTipInstantTemperature()
|
uint16_t getTipInstantTemperature() {
|
||||||
{
|
|
||||||
uint16_t sum = 0; // 12 bit readings * 8 -> 15 bits
|
uint16_t sum = 0; // 12 bit readings * 8 -> 15 bits
|
||||||
|
|
||||||
for (int i = 0; i < 4; i++)
|
for (int i = 0; i < 4; i++) {
|
||||||
{
|
|
||||||
sum += adc_inserted_data_read(ADC0, i);
|
sum += adc_inserted_data_read(ADC0, i);
|
||||||
sum += adc_inserted_data_read(ADC1, i);
|
sum += adc_inserted_data_read(ADC1, i);
|
||||||
}
|
}
|
||||||
@@ -34,113 +28,21 @@ uint16_t getTipInstantTemperature()
|
|||||||
// TODO
|
// TODO
|
||||||
// Handle callback of the PWM modulator to enable / disable the output PWM
|
// Handle callback of the PWM modulator to enable / disable the output PWM
|
||||||
|
|
||||||
uint16_t getTipRawTemp(uint8_t refresh)
|
void unstick_I2C() {
|
||||||
{
|
|
||||||
if (refresh)
|
|
||||||
{
|
|
||||||
uint16_t lastSample = getTipInstantTemperature();
|
|
||||||
rawTempFilter.update(lastSample);
|
|
||||||
return lastSample;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return rawTempFilter.average();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
void unstick_I2C()
|
|
||||||
{
|
|
||||||
// TODO
|
// TODO
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t getButtonA()
|
uint8_t getButtonA() {
|
||||||
{
|
return (gpio_input_bit_get(KEY_A_GPIO_Port, KEY_A_Pin) == SET) ? 1 : 0;
|
||||||
return (gpio_input_bit_get(KEY_A_GPIO_Port, KEY_A_Pin) == RESET) ? 1 : 0;
|
|
||||||
}
|
}
|
||||||
uint8_t getButtonB()
|
uint8_t getButtonB() {
|
||||||
{
|
return (gpio_input_bit_get(KEY_B_GPIO_Port, KEY_B_Pin) == SET) ? 1 : 0;
|
||||||
return (gpio_input_bit_get(KEY_B_GPIO_Port, KEY_B_Pin) == RESET) ? 1 : 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void reboot()
|
void reboot() {
|
||||||
{
|
|
||||||
// TODO
|
// TODO
|
||||||
for (;;)
|
for (;;) {
|
||||||
{
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void delay_ms(uint16_t count) { delay_1ms(count); }
|
void delay_ms(uint16_t count) { delay_1ms(count); }
|
||||||
|
|
||||||
uint16_t getHandleTemperature()
|
|
||||||
{
|
|
||||||
#ifdef TEMP_NTC
|
|
||||||
//TS80P uses 100k NTC resistors instead
|
|
||||||
//NTCG104EF104FT1X from TDK
|
|
||||||
//For now not doing interpolation
|
|
||||||
int32_t result = getADC(0);
|
|
||||||
for (uint32_t i = 0; i < (sizeof(NTCHandleLookup) / (2 * sizeof(uint16_t)));
|
|
||||||
i++)
|
|
||||||
{
|
|
||||||
if (result > NTCHandleLookup[(i * 2) + 0])
|
|
||||||
{
|
|
||||||
return NTCHandleLookup[(i * 2) + 1] * 10;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
#endif
|
|
||||||
#ifdef TEMP_TMP36
|
|
||||||
// We return the current handle temperature in X10 C
|
|
||||||
// TMP36 in handle, 0.5V offset and then 10mV per deg C (0.75V @ 25C for
|
|
||||||
// example) STM32 = 4096 count @ 3.3V input -> But We oversample by 32/(2^2) =
|
|
||||||
// 8 times oversampling Therefore 32768 is the 3.3V input, so 0.1007080078125
|
|
||||||
// mV per count So we need to subtract an offset of 0.5V to center on 0C
|
|
||||||
// (4964.8 counts)
|
|
||||||
//
|
|
||||||
int32_t result = getADC(0);
|
|
||||||
result -= 4965; // remove 0.5V offset
|
|
||||||
// 10mV per C
|
|
||||||
// 99.29 counts per Deg C above 0C
|
|
||||||
result *= 100;
|
|
||||||
result /= 993;
|
|
||||||
return result;
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
uint16_t getInputVoltageX10(uint16_t divisor, uint8_t sample)
|
|
||||||
{
|
|
||||||
// ADC maximum is 32767 == 3.3V at input == 28.05V at VIN
|
|
||||||
// Therefore we can divide down from there
|
|
||||||
// Multiplying ADC max by 4 for additional calibration options,
|
|
||||||
// ideal term is 467
|
|
||||||
#ifdef MODEL_TS100
|
|
||||||
#define BATTFILTERDEPTH 32
|
|
||||||
#else
|
|
||||||
#define BATTFILTERDEPTH 8
|
|
||||||
|
|
||||||
#endif
|
|
||||||
static uint8_t preFillneeded = 10;
|
|
||||||
static uint32_t samples[BATTFILTERDEPTH];
|
|
||||||
static uint8_t index = 0;
|
|
||||||
if (preFillneeded)
|
|
||||||
{
|
|
||||||
for (uint8_t i = 0; i < BATTFILTERDEPTH; i++)
|
|
||||||
samples[i] = getADC(1);
|
|
||||||
preFillneeded--;
|
|
||||||
}
|
|
||||||
if (sample)
|
|
||||||
{
|
|
||||||
samples[index] = getADC(1);
|
|
||||||
index = (index + 1) % BATTFILTERDEPTH;
|
|
||||||
}
|
|
||||||
uint32_t sum = 0;
|
|
||||||
|
|
||||||
for (uint8_t i = 0; i < BATTFILTERDEPTH; i++)
|
|
||||||
sum += samples[i];
|
|
||||||
|
|
||||||
sum /= BATTFILTERDEPTH;
|
|
||||||
if (divisor == 0)
|
|
||||||
{
|
|
||||||
divisor = 1;
|
|
||||||
}
|
|
||||||
return sum * 4 / divisor;
|
|
||||||
}
|
|
||||||
22
workspace/TS100/Core/BSP/Pine64/BSP_PD.c
Normal file
22
workspace/TS100/Core/BSP/Pine64/BSP_PD.c
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
/*
|
||||||
|
* BSP_PD.c
|
||||||
|
*
|
||||||
|
* Created on: 21 Jul 2020
|
||||||
|
* Author: Ralim
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "BSP_PD.h"
|
||||||
|
#include "Model_Config.h"
|
||||||
|
#ifdef POW_PD
|
||||||
|
/*
|
||||||
|
* An array of all of the desired voltages & minimum currents in preferred order
|
||||||
|
*/
|
||||||
|
const uint16_t USB_PD_Desired_Levels[] = {
|
||||||
|
//mV desired input, mA minimum required current
|
||||||
|
12000, 2400, //12V @ 2.4A
|
||||||
|
9000, 2000, //9V @ 2A
|
||||||
|
5000, 100, //5V @ whatever
|
||||||
|
|
||||||
|
};
|
||||||
|
const uint8_t USB_PD_Desired_Levels_Len = 3;
|
||||||
|
#endif
|
||||||
@@ -14,7 +14,7 @@ extern uint32_t SystemCoreClock;
|
|||||||
#define configUSE_TICKLESS_IDLE 0
|
#define configUSE_TICKLESS_IDLE 0
|
||||||
#define configCPU_CLOCK_HZ ((uint32_t)SystemCoreClock)
|
#define configCPU_CLOCK_HZ ((uint32_t)SystemCoreClock)
|
||||||
#define configRTC_CLOCK_HZ ((uint32_t)TIMER_FREQ)
|
#define configRTC_CLOCK_HZ ((uint32_t)TIMER_FREQ)
|
||||||
#define configTICK_RATE_HZ ((TickType_t)100)
|
#define configTICK_RATE_HZ ((TickType_t)1000)
|
||||||
#define configMAX_PRIORITIES (4) //0 - 3 å…±6ç‰çº§ï¼Œidle独å<C2AC> 0,Tmr_svc独å<C2AC> 3
|
#define configMAX_PRIORITIES (4) //0 - 3 å…±6ç‰çº§ï¼Œidle独å<C2AC> 0,Tmr_svc独å<C2AC> 3
|
||||||
#define configMINIMAL_STACK_SIZE ((unsigned short)128)
|
#define configMINIMAL_STACK_SIZE ((unsigned short)128)
|
||||||
#define configMAX_TASK_NAME_LEN 24
|
#define configMAX_TASK_NAME_LEN 24
|
||||||
|
|||||||
@@ -7,13 +7,13 @@
|
|||||||
#include "BSP.h"
|
#include "BSP.h"
|
||||||
#include "Setup.h"
|
#include "Setup.h"
|
||||||
#include <I2C_Wrapper.hpp>
|
#include <I2C_Wrapper.hpp>
|
||||||
#define I2CUSESDMA
|
|
||||||
SemaphoreHandle_t FRToSI2C::I2CSemaphore;
|
SemaphoreHandle_t FRToSI2C::I2CSemaphore;
|
||||||
StaticSemaphore_t FRToSI2C::xSemaphoreBuffer;
|
StaticSemaphore_t FRToSI2C::xSemaphoreBuffer;
|
||||||
|
SemaphoreHandle_t FRToSI2C::I2CSemaphore2;
|
||||||
|
StaticSemaphore_t FRToSI2C::xSemaphoreBuffer2;
|
||||||
#define FLAG_TIMEOUT 1000
|
#define FLAG_TIMEOUT 1000
|
||||||
|
|
||||||
void FRToSI2C::CpltCallback()
|
void FRToSI2C::CpltCallback() {
|
||||||
{
|
|
||||||
//TODO
|
//TODO
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -21,31 +21,28 @@ void FRToSI2C::CpltCallback()
|
|||||||
*
|
*
|
||||||
* @param obj The I2C object
|
* @param obj The I2C object
|
||||||
*/
|
*/
|
||||||
int i2c_start()
|
int i2c_start() {
|
||||||
{
|
|
||||||
int timeout;
|
int timeout;
|
||||||
|
|
||||||
/* clear I2C_FLAG_AERR Flag */
|
/* clear I2C_FLAG_AERR Flag */
|
||||||
i2c_flag_clear(I2C0, I2C_FLAG_AERR);
|
i2c_flag_clear(I2C0, I2C_FLAG_AERR);
|
||||||
|
|
||||||
/* wait until I2C_FLAG_I2CBSY flag is reset */
|
/* wait until I2C_FLAG_I2CBSY flag is reset */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_I2CBSY)) == SET)
|
;
|
||||||
{
|
while ((i2c_flag_get(I2C0, I2C_FLAG_I2CBSY)) == SET) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
|
||||||
|
|
||||||
return (int)-1;
|
return (int) -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* ensure the i2c has been stopped */
|
/* ensure the i2c has been stopped */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT
|
||||||
while ((I2C_CTL0(I2C0) & I2C_CTL0_STOP) == I2C_CTL0_STOP)
|
;
|
||||||
{
|
while ((I2C_CTL0(I2C0) & I2C_CTL0_STOP) == I2C_CTL0_STOP) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
return (int) -1;
|
||||||
return (int)-1;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -53,34 +50,30 @@ int i2c_start()
|
|||||||
i2c_start_on_bus(I2C0);
|
i2c_start_on_bus(I2C0);
|
||||||
|
|
||||||
/* ensure the i2c has been started successfully */
|
/* ensure the i2c has been started successfully */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET)
|
;
|
||||||
{
|
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
return (int) -1;
|
||||||
return (int)-1;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return (int)0;
|
return (int) 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Send STOP command
|
/** Send STOP command
|
||||||
*
|
*
|
||||||
* @param obj The I2C object
|
* @param obj The I2C object
|
||||||
*/
|
*/
|
||||||
int i2c_stop()
|
int i2c_stop() {
|
||||||
{
|
|
||||||
|
|
||||||
/* generate a STOP condition */
|
/* generate a STOP condition */
|
||||||
i2c_stop_on_bus(I2C0);
|
i2c_stop_on_bus(I2C0);
|
||||||
|
|
||||||
/* wait for STOP bit reset */
|
/* wait for STOP bit reset */
|
||||||
int timeout = FLAG_TIMEOUT;
|
int timeout = FLAG_TIMEOUT;
|
||||||
while ((I2C_CTL0(I2C0) & I2C_CTL0_STOP))
|
while ((I2C_CTL0(I2C0) & I2C_CTL0_STOP)) {
|
||||||
{
|
if ((timeout--) == 0) {
|
||||||
if ((timeout--) == 0)
|
|
||||||
{
|
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -94,32 +87,26 @@ int i2c_stop()
|
|||||||
* @param last Acknoledge
|
* @param last Acknoledge
|
||||||
* @return The read byte
|
* @return The read byte
|
||||||
*/
|
*/
|
||||||
int i2c_byte_read(int last)
|
int i2c_byte_read(int last) {
|
||||||
{
|
|
||||||
int timeout;
|
int timeout;
|
||||||
|
|
||||||
if (last)
|
if (last) {
|
||||||
{
|
|
||||||
/* disable acknowledge */
|
/* disable acknowledge */
|
||||||
i2c_ack_config(I2C0, I2C_ACK_DISABLE);
|
i2c_ack_config(I2C0, I2C_ACK_DISABLE);
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
/* enable acknowledge */
|
/* enable acknowledge */
|
||||||
i2c_ack_config(I2C0, I2C_ACK_ENABLE);
|
i2c_ack_config(I2C0, I2C_ACK_ENABLE);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* wait until the byte is received */
|
/* wait until the byte is received */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT;
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_RBNE)) == RESET)
|
while ((i2c_flag_get(I2C0, I2C_FLAG_RBNE)) == RESET) {
|
||||||
{
|
if ((timeout--) == 0) {
|
||||||
if ((timeout--) == 0)
|
|
||||||
{
|
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return (int)i2c_data_receive(I2C0);
|
return (int) i2c_data_receive(I2C0);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Write one byte
|
/** Write one byte
|
||||||
@@ -128,17 +115,15 @@ int i2c_byte_read(int last)
|
|||||||
* @param data Byte to be written
|
* @param data Byte to be written
|
||||||
* @return 0 if NAK was received, 1 if ACK was received, 2 for timeout.
|
* @return 0 if NAK was received, 1 if ACK was received, 2 for timeout.
|
||||||
*/
|
*/
|
||||||
int i2c_byte_write(int data)
|
int i2c_byte_write(int data) {
|
||||||
{
|
|
||||||
int timeout;
|
int timeout;
|
||||||
i2c_data_transmit(I2C0, data);
|
i2c_data_transmit(I2C0, data);
|
||||||
|
|
||||||
/* wait until the byte is transmitted */
|
/* wait until the byte is transmitted */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT;
|
||||||
while (((i2c_flag_get(I2C0, I2C_FLAG_TBE)) == RESET) || ((i2c_flag_get(I2C0, I2C_FLAG_BTC)) == RESET))
|
while (((i2c_flag_get(I2C0, I2C_FLAG_TBE)) == RESET)
|
||||||
{
|
|| ((i2c_flag_get(I2C0, I2C_FLAG_BTC)) == RESET)) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
|
||||||
return 2;
|
return 2;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -147,8 +132,7 @@ int i2c_byte_write(int data)
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
||||||
uint8_t *pData, uint16_t Size)
|
uint8_t *pData, uint16_t Size) {
|
||||||
{
|
|
||||||
if (!lock())
|
if (!lock())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@@ -157,18 +141,13 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
|
|
||||||
/* wait until I2C_FLAG_I2CBSY flag is reset */
|
/* wait until I2C_FLAG_I2CBSY flag is reset */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT;
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_I2CBSY)) == SET)
|
while ((i2c_flag_get(I2C0, I2C_FLAG_I2CBSY)) == SET) {
|
||||||
{
|
if ((timeout--) == 0) {
|
||||||
if ((timeout--) == 0)
|
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
} else {
|
||||||
else
|
if (timeout % 5 == 0) {
|
||||||
{
|
|
||||||
if (timeout % 5 == 0)
|
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -177,11 +156,10 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
i2c_start_on_bus(I2C0);
|
i2c_start_on_bus(I2C0);
|
||||||
|
|
||||||
/* ensure the i2c has been started successfully */
|
/* ensure the i2c has been started successfully */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET)
|
;
|
||||||
{
|
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
@@ -193,11 +171,9 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
|
|
||||||
timeout = 0;
|
timeout = 0;
|
||||||
/* wait until I2C_FLAG_ADDSEND flag is set */
|
/* wait until I2C_FLAG_ADDSEND flag is set */
|
||||||
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND))
|
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND)) {
|
||||||
{
|
|
||||||
timeout++;
|
timeout++;
|
||||||
if (timeout > 100000)
|
if (timeout > 100000) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
@@ -205,8 +181,7 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
}
|
}
|
||||||
bool no_ack = i2c_flag_get(I2C0, I2C_FLAG_AERR);
|
bool no_ack = i2c_flag_get(I2C0, I2C_FLAG_AERR);
|
||||||
no_ack |= i2c_flag_get(I2C0, I2C_FLAG_BERR);
|
no_ack |= i2c_flag_get(I2C0, I2C_FLAG_BERR);
|
||||||
if (no_ack)
|
if (no_ack) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
@@ -216,23 +191,21 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
int status = i2c_byte_write(MemAddress);
|
int status = i2c_byte_write(MemAddress);
|
||||||
no_ack |= i2c_flag_get(I2C0, I2C_FLAG_BERR);
|
no_ack |= i2c_flag_get(I2C0, I2C_FLAG_BERR);
|
||||||
no_ack |= i2c_flag_get(I2C0, I2C_FLAG_LOSTARB);
|
no_ack |= i2c_flag_get(I2C0, I2C_FLAG_LOSTARB);
|
||||||
if (status == 2 || no_ack)
|
if (status == 2 || no_ack) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
//////////////////////////// //Restart into read
|
//////////////////////////// //Restart into read
|
||||||
|
|
||||||
/* generate a START condition */
|
/* generate a START condition */
|
||||||
i2c_start_on_bus(I2C0);
|
i2c_start_on_bus(I2C0);
|
||||||
|
|
||||||
/* ensure the i2c has been started successfully */
|
/* ensure the i2c has been started successfully */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET)
|
;
|
||||||
{
|
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
@@ -244,11 +217,9 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
|
|
||||||
timeout = 0;
|
timeout = 0;
|
||||||
/* wait until I2C_FLAG_ADDSEND flag is set */
|
/* wait until I2C_FLAG_ADDSEND flag is set */
|
||||||
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND))
|
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND)) {
|
||||||
{
|
|
||||||
timeout++;
|
timeout++;
|
||||||
if (timeout > 100000)
|
if (timeout > 100000) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
@@ -258,15 +229,13 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
/* clear ADDSEND */
|
/* clear ADDSEND */
|
||||||
i2c_flag_clear(I2C0, I2C_FLAG_ADDSEND);
|
i2c_flag_clear(I2C0, I2C_FLAG_ADDSEND);
|
||||||
no_ack = i2c_flag_get(I2C0, I2C_FLAG_AERR);
|
no_ack = i2c_flag_get(I2C0, I2C_FLAG_AERR);
|
||||||
if (no_ack)
|
if (no_ack) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
for (count = 0; count < Size; count++)
|
for (count = 0; count < Size; count++) {
|
||||||
{
|
pData[count] = i2c_byte_read(count == (Size - 1));
|
||||||
pData[count] = i2c_byte_read(count == (uint32_t)(Size - 1));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* if not sequential write, then send stop */
|
/* if not sequential write, then send stop */
|
||||||
@@ -275,40 +244,33 @@ bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
unlock();
|
unlock();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
void FRToSI2C::I2C_RegisterWrite(uint8_t address, uint8_t reg, uint8_t data)
|
bool FRToSI2C::I2C_RegisterWrite(uint8_t address, uint8_t reg, uint8_t data) {
|
||||||
{
|
return Mem_Write(address, reg, &data, 1);
|
||||||
Mem_Write(address, reg, &data, 1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t FRToSI2C::I2C_RegisterRead(uint8_t add, uint8_t reg)
|
uint8_t FRToSI2C::I2C_RegisterRead(uint8_t add, uint8_t reg) {
|
||||||
{
|
|
||||||
uint8_t temp = 0;
|
uint8_t temp = 0;
|
||||||
Mem_Read(add, reg, &temp, 1);
|
Mem_Read(add, reg, &temp, 1);
|
||||||
return temp;
|
return temp;
|
||||||
}
|
}
|
||||||
void FRToSI2C::Mem_Write(uint16_t DevAddress, uint16_t MemAddress,
|
bool FRToSI2C::Mem_Write(uint16_t DevAddress, uint16_t MemAddress,
|
||||||
uint8_t *pData, uint16_t Size)
|
uint8_t *pData, uint16_t Size) {
|
||||||
{
|
|
||||||
if (!lock())
|
if (!lock())
|
||||||
return;
|
return false;
|
||||||
|
|
||||||
uint32_t count = 0;
|
uint32_t count = 0;
|
||||||
int timeout = 0;
|
int timeout = 0;
|
||||||
|
|
||||||
/* wait until I2C_FLAG_I2CBSY flag is reset */
|
/* wait until I2C_FLAG_I2CBSY flag is reset */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_I2CBSY)) == SET)
|
;
|
||||||
{
|
while ((i2c_flag_get(I2C0, I2C_FLAG_I2CBSY)) == SET) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return;
|
return false;
|
||||||
}
|
} else {
|
||||||
else
|
if (timeout % 5 == 0) {
|
||||||
{
|
|
||||||
if (timeout % 5 == 0)
|
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -317,14 +279,13 @@ void FRToSI2C::Mem_Write(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
i2c_start_on_bus(I2C0);
|
i2c_start_on_bus(I2C0);
|
||||||
|
|
||||||
/* ensure the i2c has been started successfully */
|
/* ensure the i2c has been started successfully */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET)
|
;
|
||||||
{
|
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -333,28 +294,24 @@ void FRToSI2C::Mem_Write(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
|
|
||||||
timeout = 0;
|
timeout = 0;
|
||||||
/* wait until I2C_FLAG_ADDSEND flag is set */
|
/* wait until I2C_FLAG_ADDSEND flag is set */
|
||||||
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND))
|
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND)) {
|
||||||
{
|
|
||||||
timeout++;
|
timeout++;
|
||||||
if (timeout > 100000)
|
if (timeout > 100000) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* clear ADDSEND */
|
/* clear ADDSEND */
|
||||||
i2c_flag_clear(I2C0, I2C_FLAG_ADDSEND);
|
i2c_flag_clear(I2C0, I2C_FLAG_ADDSEND);
|
||||||
int status = i2c_byte_write(MemAddress);
|
int status = i2c_byte_write(MemAddress);
|
||||||
for (count = 0; count < Size; count++)
|
for (count = 0; count < Size; count++) {
|
||||||
{
|
|
||||||
status = i2c_byte_write(pData[count]);
|
status = i2c_byte_write(pData[count]);
|
||||||
if (status != 1)
|
if (status != 1) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -362,29 +319,24 @@ void FRToSI2C::Mem_Write(uint16_t DevAddress, uint16_t MemAddress,
|
|||||||
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FRToSI2C::Transmit(uint16_t DevAddress, uint8_t *pData, uint16_t Size)
|
bool FRToSI2C::Transmit(uint16_t DevAddress, uint8_t *pData, uint16_t Size) {
|
||||||
{
|
|
||||||
if (!lock())
|
if (!lock())
|
||||||
return;
|
return false;
|
||||||
uint32_t count = 0;
|
uint32_t count = 0;
|
||||||
int timeout = 0;
|
int timeout = 0;
|
||||||
|
|
||||||
/* wait until I2C_FLAG_I2CBSY flag is reset */
|
/* wait until I2C_FLAG_I2CBSY flag is reset */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT;
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_I2CBSY)) == SET)
|
while ((i2c_flag_get(I2C0, I2C_FLAG_I2CBSY)) == SET) {
|
||||||
{
|
if ((timeout--) == 0) {
|
||||||
if ((timeout--) == 0)
|
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return;
|
return false;
|
||||||
}
|
} else {
|
||||||
else
|
if (timeout % 5 == 0) {
|
||||||
{
|
|
||||||
if (timeout % 5 == 0)
|
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -393,14 +345,13 @@ void FRToSI2C::Transmit(uint16_t DevAddress, uint8_t *pData, uint16_t Size)
|
|||||||
i2c_start_on_bus(I2C0);
|
i2c_start_on_bus(I2C0);
|
||||||
|
|
||||||
/* ensure the i2c has been started successfully */
|
/* ensure the i2c has been started successfully */
|
||||||
timeout = FLAG_TIMEOUT;
|
timeout = FLAG_TIMEOUT
|
||||||
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET)
|
;
|
||||||
{
|
while ((i2c_flag_get(I2C0, I2C_FLAG_SBSEND)) == RESET) {
|
||||||
if ((timeout--) == 0)
|
if ((timeout--) == 0) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -409,28 +360,24 @@ void FRToSI2C::Transmit(uint16_t DevAddress, uint8_t *pData, uint16_t Size)
|
|||||||
|
|
||||||
timeout = 0;
|
timeout = 0;
|
||||||
/* wait until I2C_FLAG_ADDSEND flag is set */
|
/* wait until I2C_FLAG_ADDSEND flag is set */
|
||||||
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND))
|
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND)) {
|
||||||
{
|
|
||||||
timeout++;
|
timeout++;
|
||||||
if (timeout > 100000)
|
if (timeout > 100000) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* clear ADDSEND */
|
/* clear ADDSEND */
|
||||||
i2c_flag_clear(I2C0, I2C_FLAG_ADDSEND);
|
i2c_flag_clear(I2C0, I2C_FLAG_ADDSEND);
|
||||||
|
|
||||||
for (count = 0; count < Size; count++)
|
for (count = 0; count < Size; count++) {
|
||||||
{
|
|
||||||
int status = i2c_byte_write(pData[count]);
|
int status = i2c_byte_write(pData[count]);
|
||||||
if (status != 1)
|
if (status != 1) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -438,10 +385,10 @@ void FRToSI2C::Transmit(uint16_t DevAddress, uint8_t *pData, uint16_t Size)
|
|||||||
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FRToSI2C::probe(uint16_t DevAddress)
|
bool FRToSI2C::probe(uint16_t DevAddress) {
|
||||||
{
|
|
||||||
if (!lock())
|
if (!lock())
|
||||||
return false;
|
return false;
|
||||||
i2c_start();
|
i2c_start();
|
||||||
@@ -449,16 +396,14 @@ bool FRToSI2C::probe(uint16_t DevAddress)
|
|||||||
i2c_master_addressing(I2C0, DevAddress, I2C_TRANSMITTER);
|
i2c_master_addressing(I2C0, DevAddress, I2C_TRANSMITTER);
|
||||||
/* wait until ADDSEND bit is set */
|
/* wait until ADDSEND bit is set */
|
||||||
int timeout = FLAG_TIMEOUT;
|
int timeout = FLAG_TIMEOUT;
|
||||||
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND))
|
while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND)) {
|
||||||
{
|
if (i2c_flag_get(I2C0, I2C_FLAG_AERR)
|
||||||
if (i2c_flag_get(I2C0, I2C_FLAG_AERR) || i2c_flag_get(I2C0, I2C_FLAG_BERR))
|
|| i2c_flag_get(I2C0, I2C_FLAG_BERR)) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (timeout-- == 0)
|
if (timeout-- == 0) {
|
||||||
{
|
|
||||||
i2c_stop();
|
i2c_stop();
|
||||||
unlock();
|
unlock();
|
||||||
return false;
|
return false;
|
||||||
@@ -480,21 +425,29 @@ bool FRToSI2C::probe(uint16_t DevAddress)
|
|||||||
return !no_ack;
|
return !no_ack;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FRToSI2C::I2C_Unstick()
|
void FRToSI2C::I2C_Unstick() {
|
||||||
{
|
|
||||||
unstick_I2C();
|
unstick_I2C();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FRToSI2C::lock()
|
bool FRToSI2C::lock() {
|
||||||
{
|
|
||||||
if (I2CSemaphore == nullptr)
|
if (I2CSemaphore == nullptr)
|
||||||
return true;
|
return true;
|
||||||
return xSemaphoreTake(I2CSemaphore, 1000) == pdTRUE;
|
return xSemaphoreTake(I2CSemaphore,1000) == pdTRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FRToSI2C::unlock()
|
void FRToSI2C::unlock() {
|
||||||
{
|
|
||||||
if (I2CSemaphore == nullptr)
|
if (I2CSemaphore == nullptr)
|
||||||
return;
|
return;
|
||||||
xSemaphoreGive(I2CSemaphore);
|
xSemaphoreGive(I2CSemaphore);
|
||||||
}
|
}
|
||||||
|
bool FRToSI2C::lock2() {
|
||||||
|
if (I2CSemaphore2 == nullptr)
|
||||||
|
return true;
|
||||||
|
return xSemaphoreTake(I2CSemaphore2,1000) == pdTRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
void FRToSI2C::unlock2() {
|
||||||
|
if (I2CSemaphore2 == nullptr)
|
||||||
|
return;
|
||||||
|
xSemaphoreGive(I2CSemaphore2);
|
||||||
|
}
|
||||||
|
|||||||
@@ -11,17 +11,14 @@
|
|||||||
* Lookup for mapping features <-> Models
|
* Lookup for mapping features <-> Models
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#if defined(MODEL_Pinecil) > 1
|
#if defined(MODEL_Pinecil) == 0
|
||||||
#error "Multiple models defined!"
|
|
||||||
#elif defined(MODEL_Pinecil) == 0
|
|
||||||
#error "No model defined!"
|
#error "No model defined!"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef MODEL_Pinecil
|
#ifdef MODEL_Pinecil
|
||||||
#define ACCEL_LIS
|
#define POW_PD
|
||||||
#define TEMP_TMP36
|
|
||||||
#define POW_QC
|
#define POW_QC
|
||||||
// #define POW_PD
|
#define TEMP_TMP36
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#endif /* BSP_MINIWARE_MODEL_CONFIG_H_ */
|
#endif /* BSP_MINIWARE_MODEL_CONFIG_H_ */
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
#include "FreeRTOSConfig.h"
|
|
||||||
#include "FreeRTOS.h"
|
#include "FreeRTOS.h"
|
||||||
#include "task.h"
|
#include "task.h"
|
||||||
#include "portmacro.h"
|
#include "portmacro.h"
|
||||||
@@ -7,32 +6,36 @@
|
|||||||
#include "riscv_encoding.h"
|
#include "riscv_encoding.h"
|
||||||
#include "n200_timer.h"
|
#include "n200_timer.h"
|
||||||
#include "n200_eclic.h"
|
#include "n200_eclic.h"
|
||||||
|
|
||||||
/* Standard Includes */
|
/* Standard Includes */
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
|
||||||
|
|
||||||
/* Each task maintains its own interrupt status in the critical nesting variable. */
|
/* Each task maintains its own interrupt status in the critical nesting variable. */
|
||||||
UBaseType_t uxCriticalNesting = 0xaaaaaaaa;
|
UBaseType_t uxCriticalNesting = 0xaaaaaaaa;
|
||||||
|
|
||||||
#if USER_MODE_TASKS
|
#if USER_MODE_TASKS
|
||||||
#ifdef __riscv_flen
|
#ifdef __riscv_flen
|
||||||
unsigned long MSTATUS_INIT = (MSTATUS_MPIE | (0x1 << 13));
|
unsigned long MSTATUS_INIT = (MSTATUS_MPIE | (0x1 << 13));
|
||||||
#else
|
#else
|
||||||
unsigned long MSTATUS_INIT = (MSTATUS_MPIE);
|
unsigned long MSTATUS_INIT = (MSTATUS_MPIE);
|
||||||
#endif
|
#endif
|
||||||
#else
|
#else
|
||||||
#ifdef __riscv_flen
|
#ifdef __riscv_flen
|
||||||
unsigned long MSTATUS_INIT = (MSTATUS_MPP | MSTATUS_MPIE | (0x1 << 13));
|
unsigned long MSTATUS_INIT = (MSTATUS_MPP | MSTATUS_MPIE | (0x1 << 13));
|
||||||
#else
|
#else
|
||||||
unsigned long MSTATUS_INIT = (MSTATUS_MPP | MSTATUS_MPIE);
|
unsigned long MSTATUS_INIT = (MSTATUS_MPP | MSTATUS_MPIE);
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Used to catch tasks that attempt to return from their implementing function.
|
* Used to catch tasks that attempt to return from their implementing function.
|
||||||
*/
|
*/
|
||||||
static void prvTaskExitError(void);
|
static void prvTaskExitError( void );
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief System Call Trap
|
* @brief System Call Trap
|
||||||
@@ -44,51 +47,52 @@ static void prvTaskExitError(void);
|
|||||||
*/
|
*/
|
||||||
unsigned long ulSynchTrap(unsigned long mcause, unsigned long sp, unsigned long arg1)
|
unsigned long ulSynchTrap(unsigned long mcause, unsigned long sp, unsigned long arg1)
|
||||||
{
|
{
|
||||||
switch (mcause & 0X00000fff)
|
switch(mcause&0X00000fff)
|
||||||
{
|
{
|
||||||
//on User and Machine ECALL, handler the request
|
//on User and Machine ECALL, handler the request
|
||||||
case 8:
|
case 8:
|
||||||
case 11:
|
case 11:
|
||||||
{
|
|
||||||
if (arg1 == IRQ_DISABLE)
|
|
||||||
{
|
{
|
||||||
//zero out mstatus.mpie
|
if(arg1==IRQ_DISABLE)
|
||||||
clear_csr(mstatus, MSTATUS_MPIE);
|
{
|
||||||
|
//zero out mstatus.mpie
|
||||||
|
clear_csr(mstatus,MSTATUS_MPIE);
|
||||||
|
}
|
||||||
|
else if(arg1==IRQ_ENABLE)
|
||||||
|
{
|
||||||
|
//set mstatus.mpie
|
||||||
|
set_csr(mstatus,MSTATUS_MPIE);
|
||||||
|
}
|
||||||
|
else if(arg1==PORT_YIELD)
|
||||||
|
{
|
||||||
|
//always yield from machine mode
|
||||||
|
//fix up mepc on sync trap
|
||||||
|
unsigned long epc = read_csr(mepc);
|
||||||
|
vPortYield_from_ulSynchTrap(sp,epc+4);
|
||||||
|
}
|
||||||
|
else if(arg1==PORT_YIELD_TO_RA)
|
||||||
|
{
|
||||||
|
vPortYield_from_ulSynchTrap(sp,(*(unsigned long*)(sp+1*sizeof(sp))));
|
||||||
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
else if (arg1 == IRQ_ENABLE)
|
default:
|
||||||
{
|
{
|
||||||
//set mstatus.mpie
|
/* 异常处理 */
|
||||||
set_csr(mstatus, MSTATUS_MPIE);
|
extern uintptr_t handle_trap(uintptr_t mcause, uintptr_t sp);
|
||||||
|
handle_trap(mcause,sp);
|
||||||
}
|
}
|
||||||
else if (arg1 == PORT_YIELD)
|
|
||||||
{
|
|
||||||
//always yield from machine mode
|
|
||||||
//fix up mepc on sync trap
|
|
||||||
unsigned long epc = read_csr(mepc);
|
|
||||||
vPortYield_from_ulSynchTrap(sp, epc + 4);
|
|
||||||
}
|
|
||||||
else if (arg1 == PORT_YIELD_TO_RA)
|
|
||||||
{
|
|
||||||
vPortYield_from_ulSynchTrap(sp, (*(unsigned long *)(sp + 1 * sizeof(sp))));
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default:
|
|
||||||
{
|
|
||||||
/* 异常处理 */
|
|
||||||
extern uintptr_t handle_trap(uintptr_t mcause, uintptr_t sp);
|
|
||||||
handle_trap(mcause, sp);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//fix mepc and return
|
//fix mepc and return
|
||||||
unsigned long epc = read_csr(mepc);
|
unsigned long epc = read_csr(mepc);
|
||||||
|
|
||||||
write_csr(mepc, epc + 4);
|
write_csr(mepc,epc+4);
|
||||||
return sp;
|
return sp;
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 设置触发软中断
|
* @brief 设置触发软中断
|
||||||
* @note 目的是在软中断内进行任务上下文切换
|
* @note 目的是在软中断内进行任务上下文切换
|
||||||
@@ -96,22 +100,24 @@ unsigned long ulSynchTrap(unsigned long mcause, unsigned long sp, unsigned long
|
|||||||
*/
|
*/
|
||||||
void vPortSetMSIPInt(void)
|
void vPortSetMSIPInt(void)
|
||||||
{
|
{
|
||||||
*(volatile uint8_t *)(TIMER_CTRL_ADDR + TIMER_MSIP) |= 0x01;
|
*(volatile uint8_t *) (TIMER_CTRL_ADDR + TIMER_MSIP) |=0x01;
|
||||||
__asm volatile("fence");
|
__asm volatile("fence");
|
||||||
__asm volatile("fence.i");
|
__asm volatile("fence.i");
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 清除软中断
|
* @brief 清除软中断
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void vPortClearMSIPInt(void)
|
void vPortClearMSIPInt(void)
|
||||||
{
|
{
|
||||||
*(volatile uint8_t *)(TIMER_CTRL_ADDR + TIMER_MSIP) &= ~0x01;
|
*(volatile uint8_t *) (TIMER_CTRL_ADDR + TIMER_MSIP) &= ~0x01;
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 执行任务上下文切换,在portasm.S中被调用
|
* @brief 执行任务上下文切换,在portasm.S中被调用
|
||||||
*
|
*
|
||||||
@@ -119,22 +125,23 @@ void vPortClearMSIPInt(void)
|
|||||||
* @param arg1
|
* @param arg1
|
||||||
* @return unsigned long sp地址
|
* @return unsigned long sp地址
|
||||||
*/
|
*/
|
||||||
unsigned long taskswitch(unsigned long sp, unsigned long arg1)
|
unsigned long taskswitch( unsigned long sp, unsigned long arg1)
|
||||||
{
|
{
|
||||||
//always yield from machine mode
|
//always yield from machine mode
|
||||||
//fix up mepc on
|
//fix up mepc on
|
||||||
unsigned long epc = read_csr(mepc);
|
unsigned long epc = read_csr(mepc);
|
||||||
vPortYield(sp, epc); //never returns
|
vPortYield(sp,epc); //never returns
|
||||||
|
|
||||||
return sp;
|
return sp;
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 调研freertos内建函数vTaskSwitchContext,在portasm.S中被调用
|
* @brief 调研freertos内建函数vTaskSwitchContext,在portasm.S中被调用
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void vDoTaskSwitchContext(void)
|
void vDoTaskSwitchContext( void )
|
||||||
{
|
{
|
||||||
portDISABLE_INTERRUPTS();
|
portDISABLE_INTERRUPTS();
|
||||||
vTaskSwitchContext();
|
vTaskSwitchContext();
|
||||||
@@ -142,42 +149,45 @@ void vDoTaskSwitchContext(void)
|
|||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 进入临界段
|
* @brief 进入临界段
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void vPortEnterCritical(void)
|
void vPortEnterCritical( void )
|
||||||
{
|
{
|
||||||
#if USER_MODE_TASKS
|
#if USER_MODE_TASKS
|
||||||
ECALL(IRQ_DISABLE);
|
ECALL(IRQ_DISABLE);
|
||||||
#else
|
#else
|
||||||
portDISABLE_INTERRUPTS();
|
portDISABLE_INTERRUPTS();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
uxCriticalNesting++;
|
uxCriticalNesting++;
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 退出临界段
|
* @brief 退出临界段
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void vPortExitCritical(void)
|
void vPortExitCritical( void )
|
||||||
{
|
{
|
||||||
configASSERT(uxCriticalNesting);
|
configASSERT( uxCriticalNesting );
|
||||||
uxCriticalNesting--;
|
uxCriticalNesting--;
|
||||||
if (uxCriticalNesting == 0)
|
if( uxCriticalNesting == 0 )
|
||||||
{
|
{
|
||||||
#if USER_MODE_TASKS
|
#if USER_MODE_TASKS
|
||||||
ECALL(IRQ_ENABLE);
|
ECALL(IRQ_ENABLE);
|
||||||
#else
|
#else
|
||||||
portENABLE_INTERRUPTS();
|
portENABLE_INTERRUPTS();
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Clear current interrupt mask and set given mask
|
* @brief Clear current interrupt mask and set given mask
|
||||||
*
|
*
|
||||||
@@ -185,10 +195,11 @@ void vPortExitCritical(void)
|
|||||||
*/
|
*/
|
||||||
void vPortClearInterruptMask(int int_mask)
|
void vPortClearInterruptMask(int int_mask)
|
||||||
{
|
{
|
||||||
eclic_set_mth(int_mask);
|
eclic_set_mth (int_mask);
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Set interrupt mask and return current interrupt enable register
|
* @brief Set interrupt mask and return current interrupt enable register
|
||||||
*
|
*
|
||||||
@@ -196,14 +207,15 @@ void vPortClearInterruptMask(int int_mask)
|
|||||||
*/
|
*/
|
||||||
int xPortSetInterruptMask(void)
|
int xPortSetInterruptMask(void)
|
||||||
{
|
{
|
||||||
int int_mask = 0;
|
int int_mask=0;
|
||||||
int_mask = eclic_get_mth();
|
int_mask=eclic_get_mth();
|
||||||
|
|
||||||
portDISABLE_INTERRUPTS();
|
portDISABLE_INTERRUPTS();
|
||||||
return int_mask;
|
return int_mask;
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 初始化任务栈帧
|
* @brief 初始化任务栈帧
|
||||||
*
|
*
|
||||||
@@ -212,30 +224,30 @@ int xPortSetInterruptMask(void)
|
|||||||
* @param pvParameters 任务参数
|
* @param pvParameters 任务参数
|
||||||
* @return StackType_t* 完成初始化后的栈顶
|
* @return StackType_t* 完成初始化后的栈顶
|
||||||
*/
|
*/
|
||||||
StackType_t *pxPortInitialiseStack(StackType_t *pxTopOfStack, TaskFunction_t pxCode, void *pvParameters)
|
StackType_t *pxPortInitialiseStack( StackType_t *pxTopOfStack, TaskFunction_t pxCode, void *pvParameters )
|
||||||
{
|
{
|
||||||
/* Simulate the stack frame as it would be created by a context switch
|
/* Simulate the stack frame as it would be created by a context switch
|
||||||
interrupt. */
|
interrupt. */
|
||||||
#ifdef __riscv_flen
|
#ifdef __riscv_flen
|
||||||
pxTopOfStack -= 32; /* 浮点寄存器 */
|
pxTopOfStack -= 32; /* 浮点寄存器 */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
pxTopOfStack--;
|
pxTopOfStack--;
|
||||||
*pxTopOfStack = 0xb8000000; /* CSR_MCAUSE */
|
*pxTopOfStack = 0xb8000000; /* CSR_MCAUSE */
|
||||||
|
|
||||||
pxTopOfStack--;
|
pxTopOfStack--;
|
||||||
*pxTopOfStack = 0x40; /* CSR_SUBM */
|
*pxTopOfStack = 0x40; /* CSR_SUBM */
|
||||||
|
|
||||||
pxTopOfStack--;
|
pxTopOfStack--;
|
||||||
*pxTopOfStack = (portSTACK_TYPE)pxCode; /* Start address */
|
*pxTopOfStack = (portSTACK_TYPE)pxCode; /* Start address */
|
||||||
|
|
||||||
pxTopOfStack--;
|
pxTopOfStack--;
|
||||||
*pxTopOfStack = MSTATUS_INIT; /* CSR_MSTATUS */
|
*pxTopOfStack = MSTATUS_INIT; /* CSR_MSTATUS */
|
||||||
|
|
||||||
pxTopOfStack -= 22;
|
pxTopOfStack -= 22;
|
||||||
*pxTopOfStack = (portSTACK_TYPE)pvParameters; /* Register a0 */
|
*pxTopOfStack = (portSTACK_TYPE)pvParameters; /* Register a0 */
|
||||||
|
|
||||||
pxTopOfStack -= 9;
|
pxTopOfStack -=9;
|
||||||
*pxTopOfStack = (portSTACK_TYPE)prvTaskExitError; /* Register ra */
|
*pxTopOfStack = (portSTACK_TYPE)prvTaskExitError; /* Register ra */
|
||||||
pxTopOfStack--;
|
pxTopOfStack--;
|
||||||
|
|
||||||
@@ -243,24 +255,25 @@ StackType_t *pxPortInitialiseStack(StackType_t *pxTopOfStack, TaskFunction_t pxC
|
|||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 任务退出函数
|
* @brief 任务退出函数
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
void prvTaskExitError(void)
|
void prvTaskExitError( void )
|
||||||
{
|
{
|
||||||
/* A function that implements a task must not exit or attempt to return to
|
/* A function that implements a task must not exit or attempt to return to
|
||||||
its caller as there is nothing to return to. If a task wants to exit it
|
its caller as there is nothing to return to. If a task wants to exit it
|
||||||
should instead call vTaskDelete( NULL ).
|
should instead call vTaskDelete( NULL ).
|
||||||
Artificially force an assert() to be triggered if configASSERT() is
|
Artificially force an assert() to be triggered if configASSERT() is
|
||||||
defined, then stop here so application writers can catch the error. */
|
defined, then stop here so application writers can catch the error. */
|
||||||
configASSERT(uxCriticalNesting == ~0UL);
|
configASSERT( uxCriticalNesting == ~0UL );
|
||||||
portDISABLE_INTERRUPTS();
|
portDISABLE_INTERRUPTS();
|
||||||
for (;;)
|
for( ;; );
|
||||||
;
|
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief tick中断
|
* @brief tick中断
|
||||||
* @note 由于该中断配置为向量模式,则中断到来会调用portasm.S的MTIME_HANDLER,进行栈帧保存之后该函数会调用vPortSysTickHandler
|
* @note 由于该中断配置为向量模式,则中断到来会调用portasm.S的MTIME_HANDLER,进行栈帧保存之后该函数会调用vPortSysTickHandler
|
||||||
@@ -268,38 +281,39 @@ void prvTaskExitError(void)
|
|||||||
*/
|
*/
|
||||||
void vPortSysTickHandler(void)
|
void vPortSysTickHandler(void)
|
||||||
{
|
{
|
||||||
volatile uint64_t *mtime = (uint64_t *)(TIMER_CTRL_ADDR + TIMER_MTIME);
|
volatile uint64_t * mtime = (uint64_t*) (TIMER_CTRL_ADDR + TIMER_MTIME);
|
||||||
volatile uint64_t *mtimecmp = (uint64_t *)(TIMER_CTRL_ADDR + TIMER_MTIMECMP);
|
volatile uint64_t * mtimecmp = (uint64_t*) (TIMER_CTRL_ADDR + TIMER_MTIMECMP);
|
||||||
|
|
||||||
UBaseType_t uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR();
|
UBaseType_t uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR();
|
||||||
|
|
||||||
#if CONFIG_SYSTEMVIEW_EN
|
#if CONFIG_SYSTEMVIEW_EN
|
||||||
traceISR_ENTER();
|
traceISR_ENTER();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
uint64_t now = *mtime;
|
uint64_t now = *mtime;
|
||||||
now += (configRTC_CLOCK_HZ / configTICK_RATE_HZ);
|
now += (configRTC_CLOCK_HZ / configTICK_RATE_HZ);
|
||||||
*mtimecmp = now;
|
*mtimecmp = now;
|
||||||
|
|
||||||
/* 调用freertos的tick增加接口 */
|
/* 调用freertos的tick增加接口 */
|
||||||
if (xTaskIncrementTick() != pdFALSE)
|
if( xTaskIncrementTick() != pdFALSE )
|
||||||
{
|
{
|
||||||
#if CONFIG_SYSTEMVIEW_EN
|
#if CONFIG_SYSTEMVIEW_EN
|
||||||
traceISR_EXIT_TO_SCHEDULER();
|
traceISR_EXIT_TO_SCHEDULER();
|
||||||
#endif
|
#endif
|
||||||
portYIELD();
|
portYIELD();
|
||||||
}
|
}
|
||||||
#if CONFIG_SYSTEMVIEW_EN
|
#if CONFIG_SYSTEMVIEW_EN
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
traceISR_EXIT();
|
traceISR_EXIT();
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
portCLEAR_INTERRUPT_MASK_FROM_ISR(uxSavedInterruptStatus);
|
portCLEAR_INTERRUPT_MASK_FROM_ISR( uxSavedInterruptStatus );
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 初始化tick
|
* @brief 初始化tick
|
||||||
*
|
*
|
||||||
@@ -307,20 +321,21 @@ void vPortSysTickHandler(void)
|
|||||||
void vPortSetupTimer(void)
|
void vPortSetupTimer(void)
|
||||||
{
|
{
|
||||||
/* 内核timer定时器使用64位的计数器来实现 */
|
/* 内核timer定时器使用64位的计数器来实现 */
|
||||||
volatile uint64_t *mtime = (uint64_t *)(TIMER_CTRL_ADDR + TIMER_MTIME);
|
volatile uint64_t * mtime = (uint64_t*) (TIMER_CTRL_ADDR + TIMER_MTIME);
|
||||||
volatile uint64_t *mtimecmp = (uint64_t *)(TIMER_CTRL_ADDR + TIMER_MTIMECMP);
|
volatile uint64_t * mtimecmp = (uint64_t*) (TIMER_CTRL_ADDR + TIMER_MTIMECMP);
|
||||||
|
|
||||||
portENTER_CRITICAL();
|
portENTER_CRITICAL();
|
||||||
uint64_t now = *mtime;
|
uint64_t now = *mtime;
|
||||||
now += (configRTC_CLOCK_HZ / configTICK_RATE_HZ);
|
now += (configRTC_CLOCK_HZ / configTICK_RATE_HZ);
|
||||||
*mtimecmp = now;
|
*mtimecmp = now;
|
||||||
portEXIT_CRITICAL();
|
portEXIT_CRITICAL();
|
||||||
|
|
||||||
eclic_set_vmode(CLIC_INT_TMR);
|
eclic_set_vmode(CLIC_INT_TMR);
|
||||||
eclic_irq_enable(CLIC_INT_TMR, configKERNEL_INTERRUPT_PRIORITY >> configPRIO_BITS, 0);
|
eclic_irq_enable(CLIC_INT_TMR,configKERNEL_INTERRUPT_PRIORITY>>configPRIO_BITS,0);
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 初始化软中断
|
* @brief 初始化软中断
|
||||||
*
|
*
|
||||||
@@ -328,10 +343,11 @@ void vPortSetupTimer(void)
|
|||||||
void vPortSetupMSIP(void)
|
void vPortSetupMSIP(void)
|
||||||
{
|
{
|
||||||
eclic_set_vmode(CLIC_INT_SFT);
|
eclic_set_vmode(CLIC_INT_SFT);
|
||||||
eclic_irq_enable(CLIC_INT_SFT, configKERNEL_INTERRUPT_PRIORITY >> configPRIO_BITS, 0);
|
eclic_irq_enable(CLIC_INT_SFT,configKERNEL_INTERRUPT_PRIORITY>>configPRIO_BITS,0);
|
||||||
}
|
}
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 调度启动前的初始化准备
|
* @brief 调度启动前的初始化准备
|
||||||
*
|
*
|
||||||
|
|||||||
@@ -1,13 +1,14 @@
|
|||||||
#ifndef PINE_PORTMACRO_H
|
#ifndef PORTMACRO_H
|
||||||
#define PINE_PORTMACRO_H
|
#define PORTMACRO_H
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
extern "C"
|
extern "C" {
|
||||||
{
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
#include "riscv_encoding.h"
|
#include "riscv_encoding.h"
|
||||||
|
|
||||||
|
|
||||||
/*-----------------------------------------------------------
|
/*-----------------------------------------------------------
|
||||||
* Port specific definitions.
|
* Port specific definitions.
|
||||||
*
|
*
|
||||||
@@ -19,128 +20,123 @@ extern "C"
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
/* Type definitions. */
|
/* Type definitions. */
|
||||||
#define portCHAR char
|
#define portCHAR char
|
||||||
#define portFLOAT float
|
#define portFLOAT float
|
||||||
#define portDOUBLE double
|
#define portDOUBLE double
|
||||||
#define portLONG long
|
#define portLONG long
|
||||||
#define portSHORT short
|
#define portSHORT short
|
||||||
#define portSTACK_TYPE uint32_t
|
#define portSTACK_TYPE uint32_t
|
||||||
#define portBASE_TYPE long
|
#define portBASE_TYPE long
|
||||||
|
|
||||||
typedef portSTACK_TYPE StackType_t;
|
typedef portSTACK_TYPE StackType_t;
|
||||||
typedef long BaseType_t;
|
typedef long BaseType_t;
|
||||||
typedef unsigned long UBaseType_t;
|
typedef unsigned long UBaseType_t;
|
||||||
|
|
||||||
#if (configUSE_16_BIT_TICKS == 1)
|
#if( configUSE_16_BIT_TICKS == 1 )
|
||||||
typedef uint16_t TickType_t;
|
typedef uint16_t TickType_t;
|
||||||
#define portMAX_DELAY (TickType_t)0xffff
|
#define portMAX_DELAY ( TickType_t ) 0xffff
|
||||||
#else
|
#else
|
||||||
typedef uint32_t TickType_t;
|
typedef uint32_t TickType_t;
|
||||||
#define portMAX_DELAY (TickType_t)0xffffffffUL
|
#define portMAX_DELAY ( TickType_t ) 0xffffffffUL
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
/* Architecture specifics. */
|
/* Architecture specifics. */
|
||||||
#define portSTACK_GROWTH (-1)
|
#define portSTACK_GROWTH ( -1 )
|
||||||
#define portTICK_PERIOD_MS ((TickType_t)1000 / configTICK_RATE_HZ)
|
#define portTICK_PERIOD_MS ( ( TickType_t ) 1000 / configTICK_RATE_HZ )
|
||||||
#define portBYTE_ALIGNMENT 8
|
#define portBYTE_ALIGNMENT 8
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
/* Architecture specifics. */
|
||||||
|
extern void vPortYield(unsigned long,unsigned long);
|
||||||
|
extern void vPortYield_from_ulSynchTrap(unsigned long,unsigned long);
|
||||||
|
extern int xPortSetInterruptMask(void);
|
||||||
|
extern void vPortClearInterruptMask( int uxSavedStatusValue );
|
||||||
|
|
||||||
/* Architecture specifics. */
|
|
||||||
extern void vPortYield(unsigned long, unsigned long);
|
|
||||||
extern void vPortYield_from_ulSynchTrap(unsigned long, unsigned long);
|
|
||||||
extern int xPortSetInterruptMask(void);
|
|
||||||
extern void vPortClearInterruptMask(int uxSavedStatusValue);
|
|
||||||
|
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
/*System Calls */
|
/*System Calls */
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
//ecall macro used to store argument in a3
|
//ecall macro used to store argument in a3
|
||||||
#define ECALL(arg) ({ \
|
#define ECALL(arg) ({ \
|
||||||
register uintptr_t a2 asm("a2") = (uintptr_t)(arg); \
|
register uintptr_t a2 asm ("a2") = (uintptr_t)(arg); \
|
||||||
asm volatile("ecall" \
|
asm volatile ("ecall" \
|
||||||
: "+r"(a2) \
|
: "+r" (a2) \
|
||||||
: \
|
: \
|
||||||
: "memory"); \
|
: "memory"); \
|
||||||
a2; \
|
a2; \
|
||||||
})
|
})
|
||||||
|
|
||||||
extern void vPortSetMSIPInt(void);
|
|
||||||
|
extern void vPortSetMSIPInt(void);
|
||||||
#define port_MSIPSET_BIT vPortSetMSIPInt()
|
#define port_MSIPSET_BIT vPortSetMSIPInt()
|
||||||
|
|
||||||
#define IRQ_DISABLE 20
|
#define IRQ_DISABLE 20
|
||||||
#define IRQ_ENABLE 30
|
#define IRQ_ENABLE 30
|
||||||
#define PORT_YIELD 40
|
#define PORT_YIELD 40
|
||||||
#define PORT_YIELD_TO_RA 50
|
#define PORT_YIELD_TO_RA 50
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
/* Scheduler utilities. */
|
/* Scheduler utilities. */
|
||||||
/* the return after the ECALL is VERY important */
|
/* the return after the ECALL is VERY important */
|
||||||
|
|
||||||
//#define portYIELD() ECALL(PORT_YIELD);
|
//#define portYIELD() ECALL(PORT_YIELD);
|
||||||
#define portYIELD() port_MSIPSET_BIT;
|
#define portYIELD() port_MSIPSET_BIT;
|
||||||
|
|
||||||
#ifdef CONFIG_SYSTEMVIEW_EN
|
#if CONFIG_SYSTEMVIEW_EN
|
||||||
#define portEND_SWITCHING_ISR(xSwitchRequired) \
|
#define portEND_SWITCHING_ISR(xSwitchRequired) { if( xSwitchRequired != pdFALSE) { traceISR_EXIT_TO_SCHEDULER(); portYIELD(); } else {traceISR_EXIT(); } }
|
||||||
{ \
|
|
||||||
if (xSwitchRequired != pdFALSE) \
|
|
||||||
{ \
|
|
||||||
traceISR_EXIT_TO_SCHEDULER(); \
|
|
||||||
portYIELD(); \
|
|
||||||
} \
|
|
||||||
else \
|
|
||||||
{ \
|
|
||||||
traceISR_EXIT(); \
|
|
||||||
} \
|
|
||||||
}
|
|
||||||
#else
|
#else
|
||||||
#define portEND_SWITCHING_ISR(xSwitchRequired) \
|
#define portEND_SWITCHING_ISR(xSwitchRequired) if( xSwitchRequired != pdFALSE) portYIELD()
|
||||||
if (xSwitchRequired != pdFALSE) \
|
|
||||||
portYIELD()
|
|
||||||
#endif
|
#endif
|
||||||
#define portYIELD_FROM_ISR(x) portEND_SWITCHING_ISR(x)
|
#define portYIELD_FROM_ISR(x) portEND_SWITCHING_ISR(x)
|
||||||
|
|
||||||
/* Critical section management. */
|
/* Critical section management. */
|
||||||
extern void vPortEnterCritical(void);
|
extern void vPortEnterCritical( void );
|
||||||
extern void vPortExitCritical(void);
|
extern void vPortExitCritical( void );
|
||||||
extern void eclic_set_mth(uint8_t mth);
|
extern void eclic_set_mth (uint8_t mth);
|
||||||
#define portDISABLE_INTERRUPTS() \
|
#define portDISABLE_INTERRUPTS() \
|
||||||
{ \
|
{ \
|
||||||
eclic_set_mth((configMAX_SYSCALL_INTERRUPT_PRIORITY) | 0x1f); \
|
eclic_set_mth((configMAX_SYSCALL_INTERRUPT_PRIORITY)|0x1f); \
|
||||||
__asm volatile("fence"); \
|
__asm volatile("fence"); \
|
||||||
__asm volatile("fence.i"); \
|
__asm volatile("fence.i"); \
|
||||||
}
|
}
|
||||||
#define portENABLE_INTERRUPTS() eclic_set_mth(0)
|
#define portENABLE_INTERRUPTS() eclic_set_mth(0)
|
||||||
#define portSET_INTERRUPT_MASK_FROM_ISR() xPortSetInterruptMask()
|
#define portSET_INTERRUPT_MASK_FROM_ISR() xPortSetInterruptMask()
|
||||||
#define portCLEAR_INTERRUPT_MASK_FROM_ISR(uxSavedStatusValue) vPortClearInterruptMask(uxSavedStatusValue)
|
#define portCLEAR_INTERRUPT_MASK_FROM_ISR( uxSavedStatusValue ) vPortClearInterruptMask( uxSavedStatusValue )
|
||||||
#define portENTER_CRITICAL() vPortEnterCritical()
|
#define portENTER_CRITICAL() vPortEnterCritical()
|
||||||
#define portEXIT_CRITICAL() vPortExitCritical()
|
#define portEXIT_CRITICAL() vPortExitCritical()
|
||||||
|
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
/* Task function macros as described on the FreeRTOS.org WEB site. These are
|
/* Task function macros as described on the FreeRTOS.org WEB site. These are
|
||||||
not necessary for to use this port. They are defined so the common demo files
|
not necessary for to use this port. They are defined so the common demo files
|
||||||
(which build with all the ports) will build. */
|
(which build with all the ports) will build. */
|
||||||
#define portTASK_FUNCTION_PROTO(vFunction, pvParameters) void vFunction(void *pvParameters)
|
#define portTASK_FUNCTION_PROTO( vFunction, pvParameters ) void vFunction( void *pvParameters )
|
||||||
#define portTASK_FUNCTION(vFunction, pvParameters) void vFunction(void *pvParameters)
|
#define portTASK_FUNCTION( vFunction, pvParameters ) void vFunction( void *pvParameters )
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
/* Tickless idle/low power functionality. */
|
/* Tickless idle/low power functionality. */
|
||||||
#ifndef portSUPPRESS_TICKS_AND_SLEEP
|
#ifndef portSUPPRESS_TICKS_AND_SLEEP
|
||||||
extern void vPortSuppressTicksAndSleep(TickType_t xExpectedIdleTime);
|
extern void vPortSuppressTicksAndSleep( TickType_t xExpectedIdleTime );
|
||||||
#define portSUPPRESS_TICKS_AND_SLEEP(xExpectedIdleTime) vPortSuppressTicksAndSleep(xExpectedIdleTime)
|
#define portSUPPRESS_TICKS_AND_SLEEP( xExpectedIdleTime ) vPortSuppressTicksAndSleep( xExpectedIdleTime )
|
||||||
#endif
|
#endif
|
||||||
/*-----------------------------------------------------------*/
|
/*-----------------------------------------------------------*/
|
||||||
|
|
||||||
#define portINLINE __inline
|
|
||||||
|
#define portINLINE __inline
|
||||||
|
|
||||||
#ifndef portFORCE_INLINE
|
#ifndef portFORCE_INLINE
|
||||||
#define portFORCE_INLINE inline __attribute__((always_inline))
|
#define portFORCE_INLINE inline __attribute__(( always_inline))
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#endif /* PORTMACRO_H */
|
#endif /* PORTMACRO_H */
|
||||||
|
|
||||||
|
|||||||
@@ -7,17 +7,17 @@
|
|||||||
| 17 | PB2 | BOOT2 | Pulldown |
|
| 17 | PB2 | BOOT2 | Pulldown |
|
||||||
| 32 | | IMU INT 1 | N/A |
|
| 32 | | IMU INT 1 | N/A |
|
||||||
| 30 | | IMU INT 2 | N/A |
|
| 30 | | IMU INT 2 | N/A |
|
||||||
| 14 | PA7 | Handle Temp | ADC Input 7 |
|
| | PA4 | Handle Temp | ADC Input ? |
|
||||||
| 15 | PB0 | Tip Temp | ADC Input 8 |
|
| | PA1 | Tip Temp | ADC Input ? |
|
||||||
| 13 | PA6 | B Button | Active Low |
|
| | PB1 | B Button | Active High |
|
||||||
| 21 | PA9 | A Button | Active Low |
|
| | PB0 | A Button | Active High |
|
||||||
| 23 | PA11 | USB D- | - |
|
| | PA11 | USB D- | - |
|
||||||
| 24 | PA12 | USB D+ | - |
|
| | PA12 | USB D+ | - |
|
||||||
| 31 | PB4 | Tip PWM Out | TIMER2_CH0 |
|
| | PA6 | Tip PWM Out | - |
|
||||||
| 16 | PB1 | Input DC V Sense | ADC Input 9 |
|
| | PA0 | Input DC V Sense | ADC Input ? |
|
||||||
| 20 | PA8 | OLED Reset | |
|
| | PA9 | OLED Reset | |
|
||||||
| 34 | PB7 | SDA | I2C0_SDA |
|
| | PB7 | SDA | I2C0_SDA |
|
||||||
| 33 | PB6 | SCL | I2C0_SCL |
|
| | PB6 | SCL | I2C0_SCL |
|
||||||
|
|
||||||
## ADC Configuration
|
## ADC Configuration
|
||||||
|
|
||||||
|
|||||||
@@ -9,27 +9,27 @@
|
|||||||
#define BSP_MINIWARE_PINS_H_
|
#define BSP_MINIWARE_PINS_H_
|
||||||
#include "Vendor/Lib/gd32vf103_gpio.h"
|
#include "Vendor/Lib/gd32vf103_gpio.h"
|
||||||
//TODO
|
//TODO
|
||||||
#define KEY_B_Pin BIT(6)
|
#define KEY_B_Pin BIT(1)
|
||||||
#define KEY_B_GPIO_Port GPIOA
|
#define KEY_B_GPIO_Port GPIOB
|
||||||
#define TMP36_INPUT_Pin BIT(7)
|
#define TMP36_INPUT_Pin BIT(4)
|
||||||
#define TMP36_INPUT_GPIO_Port GPIOA
|
#define TMP36_INPUT_GPIO_Port GPIOA
|
||||||
#define TMP36_ADC1_CHANNEL ADC_CHANNEL_7
|
#define TMP36_ADC1_CHANNEL ADC_CHANNEL_4
|
||||||
#define TMP36_ADC2_CHANNEL ADC_CHANNEL_7
|
#define TMP36_ADC2_CHANNEL ADC_CHANNEL_4
|
||||||
#define TIP_TEMP_Pin BIT(0)
|
#define TIP_TEMP_Pin BIT(1)
|
||||||
#define TIP_TEMP_GPIO_Port GPIOB
|
#define TIP_TEMP_GPIO_Port GPIOA
|
||||||
#define TIP_TEMP_ADC1_CHANNEL ADC_CHANNEL_8
|
#define TIP_TEMP_ADC1_CHANNEL ADC_CHANNEL_1
|
||||||
#define TIP_TEMP_ADC2_CHANNEL ADC_CHANNEL_8
|
#define TIP_TEMP_ADC2_CHANNEL ADC_CHANNEL_1
|
||||||
|
|
||||||
#define VIN_Pin BIT(1)
|
#define VIN_Pin BIT(0)
|
||||||
#define VIN_GPIO_Port GPIOB
|
#define VIN_GPIO_Port GPIOA
|
||||||
#define VIN_ADC1_CHANNEL ADC_CHANNEL_9
|
#define VIN_ADC1_CHANNEL ADC_CHANNEL_0
|
||||||
#define VIN_ADC2_CHANNEL ADC_CHANNEL_9
|
#define VIN_ADC2_CHANNEL ADC_CHANNEL_0
|
||||||
#define OLED_RESET_Pin BIT(8)
|
#define OLED_RESET_Pin BIT(9)
|
||||||
#define OLED_RESET_GPIO_Port GPIOA
|
#define OLED_RESET_GPIO_Port GPIOA
|
||||||
#define KEY_A_Pin BIT(9)
|
#define KEY_A_Pin BIT(0)
|
||||||
#define KEY_A_GPIO_Port GPIOA
|
#define KEY_A_GPIO_Port GPIOB
|
||||||
#define PWM_Out_Pin BIT(4)
|
#define PWM_Out_Pin BIT(6)
|
||||||
#define PWM_Out_GPIO_Port GPIOB
|
#define PWM_Out_GPIO_Port GPIOA
|
||||||
#define SCL_Pin BIT(6)
|
#define SCL_Pin BIT(6)
|
||||||
#define SCL_GPIO_Port GPIOB
|
#define SCL_GPIO_Port GPIOB
|
||||||
#define SDA_Pin BIT(7)
|
#define SDA_Pin BIT(7)
|
||||||
|
|||||||
@@ -9,32 +9,28 @@
|
|||||||
#include "int_n.h"
|
#include "int_n.h"
|
||||||
bool FUSB302_present = false;
|
bool FUSB302_present = false;
|
||||||
|
|
||||||
void power_check()
|
void power_check() {
|
||||||
{
|
|
||||||
#ifdef POW_PD
|
#ifdef POW_PD
|
||||||
if (FUSB302_present)
|
if (FUSB302_present) {
|
||||||
{
|
//Cant start QC until either PD works or fails
|
||||||
//Cant start QC until either PD works or fails
|
if (PolicyEngine::setupCompleteOrTimedOut() == false) {
|
||||||
if (PolicyEngine::setupCompleteOrTimedOut() == false)
|
return;
|
||||||
{
|
}
|
||||||
return;
|
if (PolicyEngine::pdHasNegotiated()) {
|
||||||
}
|
return;
|
||||||
if (PolicyEngine::pdHasNegotiated())
|
}
|
||||||
{
|
}
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
#ifdef POW_QC
|
#ifdef POW_QC
|
||||||
QC_resync();
|
QC_resync();
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
uint8_t usb_pd_detect()
|
uint8_t usb_pd_detect() {
|
||||||
{
|
|
||||||
#ifdef POW_PD
|
#ifdef POW_PD
|
||||||
FUSB302_present = fusb302_detect();
|
FUSB302_present = fusb302_detect();
|
||||||
|
|
||||||
return FUSB302_present;
|
return FUSB302_present;
|
||||||
#endif
|
#endif
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -55,8 +55,8 @@ void setup_gpio() {
|
|||||||
//Alternate function clock enable
|
//Alternate function clock enable
|
||||||
rcu_periph_clock_enable(RCU_AF);
|
rcu_periph_clock_enable(RCU_AF);
|
||||||
//Buttons as input
|
//Buttons as input
|
||||||
gpio_init(KEY_A_GPIO_Port, GPIO_MODE_IPU, GPIO_OSPEED_2MHZ, KEY_A_Pin);
|
gpio_init(KEY_A_GPIO_Port, GPIO_MODE_IPD, GPIO_OSPEED_2MHZ, KEY_A_Pin);
|
||||||
gpio_init(KEY_B_GPIO_Port, GPIO_MODE_IPU, GPIO_OSPEED_2MHZ, KEY_B_Pin);
|
gpio_init(KEY_B_GPIO_Port, GPIO_MODE_IPD, GPIO_OSPEED_2MHZ, KEY_B_Pin);
|
||||||
//OLED reset as output
|
//OLED reset as output
|
||||||
gpio_init(OLED_RESET_GPIO_Port, GPIO_MODE_OUT_PP, GPIO_OSPEED_2MHZ,
|
gpio_init(OLED_RESET_GPIO_Port, GPIO_MODE_OUT_PP, GPIO_OSPEED_2MHZ,
|
||||||
OLED_RESET_Pin);
|
OLED_RESET_Pin);
|
||||||
@@ -73,7 +73,7 @@ void setup_gpio() {
|
|||||||
TIP_TEMP_Pin);
|
TIP_TEMP_Pin);
|
||||||
gpio_init(VIN_GPIO_Port, GPIO_MODE_AIN, GPIO_OSPEED_2MHZ, VIN_Pin);
|
gpio_init(VIN_GPIO_Port, GPIO_MODE_AIN, GPIO_OSPEED_2MHZ, VIN_Pin);
|
||||||
//Timer 2 remap to move timer 2 ch0 to pin PB4
|
//Timer 2 remap to move timer 2 ch0 to pin PB4
|
||||||
gpio_pin_remap_config(GPIO_TIMER2_PARTIAL_REMAP, ENABLE);
|
// gpio_pin_remap_config(GPIO_TIMER2_PARTIAL_REMAP, ENABLE);
|
||||||
//Remap PB4 away from JTAG NJRST
|
//Remap PB4 away from JTAG NJRST
|
||||||
gpio_pin_remap_config(GPIO_SWJ_NONJTRST_REMAP, ENABLE);
|
gpio_pin_remap_config(GPIO_SWJ_NONJTRST_REMAP, ENABLE);
|
||||||
//TODO - rest of pins as floating
|
//TODO - rest of pins as floating
|
||||||
@@ -112,7 +112,7 @@ void setup_i2c() {
|
|||||||
/* enable I2C0 clock */
|
/* enable I2C0 clock */
|
||||||
rcu_periph_clock_enable(RCU_I2C0);
|
rcu_periph_clock_enable(RCU_I2C0);
|
||||||
//Setup I20 at 100kHz with DMA?
|
//Setup I20 at 100kHz with DMA?
|
||||||
i2c_clock_config(I2C0, 400 * 1000, I2C_DTCY_16_9);
|
i2c_clock_config(I2C0, 100 * 1000, I2C_DTCY_16_9);
|
||||||
i2c_mode_addr_config(I2C0, I2C_I2CMODE_ENABLE, I2C_ADDFORMAT_7BITS, 0x00);
|
i2c_mode_addr_config(I2C0, I2C_I2CMODE_ENABLE, I2C_ADDFORMAT_7BITS, 0x00);
|
||||||
i2c_enable(I2C0);
|
i2c_enable(I2C0);
|
||||||
/* enable acknowledge */
|
/* enable acknowledge */
|
||||||
|
|||||||
176
workspace/TS100/Core/BSP/Pine64/Vendor/Lib/GD32VF103xB.lds
vendored
Normal file
176
workspace/TS100/Core/BSP/Pine64/Vendor/Lib/GD32VF103xB.lds
vendored
Normal file
@@ -0,0 +1,176 @@
|
|||||||
|
OUTPUT_ARCH( "riscv" )
|
||||||
|
|
||||||
|
ENTRY( _start )
|
||||||
|
|
||||||
|
MEMORY
|
||||||
|
{
|
||||||
|
/* Run in FLASH */
|
||||||
|
flash (rxai!w) : ORIGIN = 0x08000000, LENGTH = 128k
|
||||||
|
ram (wxa!ri) : ORIGIN = 0x20000000, LENGTH = 32K
|
||||||
|
|
||||||
|
/* Run in RAM */
|
||||||
|
/* flash (rxai!w) : ORIGIN = 0x20000000, LENGTH = 24k
|
||||||
|
ram (wxa!ri) : ORIGIN = 0x20006000, LENGTH = 8K
|
||||||
|
*/
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
SECTIONS
|
||||||
|
{
|
||||||
|
__stack_size = DEFINED(__stack_size) ? __stack_size : 2K;
|
||||||
|
|
||||||
|
|
||||||
|
.init :
|
||||||
|
{
|
||||||
|
KEEP (*(SORT_NONE(.init)))
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.ilalign :
|
||||||
|
{
|
||||||
|
. = ALIGN(4);
|
||||||
|
PROVIDE( _ilm_lma = . );
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.ialign :
|
||||||
|
{
|
||||||
|
PROVIDE( _ilm = . );
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.text :
|
||||||
|
{
|
||||||
|
*(.rodata .rodata.*)
|
||||||
|
*(.text.unlikely .text.unlikely.*)
|
||||||
|
*(.text.startup .text.startup.*)
|
||||||
|
*(.text .text.*)
|
||||||
|
*(.gnu.linkonce.t.*)
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.fini :
|
||||||
|
{
|
||||||
|
KEEP (*(SORT_NONE(.fini)))
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
. = ALIGN(4);
|
||||||
|
|
||||||
|
PROVIDE (__etext = .);
|
||||||
|
PROVIDE (_etext = .);/*0x80022c8*/
|
||||||
|
PROVIDE (etext = .);/*0x80022c8*/
|
||||||
|
PROVIDE( _eilm = . );
|
||||||
|
|
||||||
|
.preinit_array :
|
||||||
|
{
|
||||||
|
PROVIDE_HIDDEN (__preinit_array_start = .);
|
||||||
|
KEEP (*(.preinit_array))
|
||||||
|
PROVIDE_HIDDEN (__preinit_array_end = .);
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.init_array :
|
||||||
|
{
|
||||||
|
PROVIDE_HIDDEN (__init_array_start = .);
|
||||||
|
KEEP (*(SORT_BY_INIT_PRIORITY(.init_array.*) SORT_BY_INIT_PRIORITY(.ctors.*)))
|
||||||
|
KEEP (*(.init_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .ctors))
|
||||||
|
PROVIDE_HIDDEN (__init_array_end = .);
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.fini_array :
|
||||||
|
{
|
||||||
|
PROVIDE_HIDDEN (__fini_array_start = .);
|
||||||
|
KEEP (*(SORT_BY_INIT_PRIORITY(.fini_array.*) SORT_BY_INIT_PRIORITY(.dtors.*)))
|
||||||
|
KEEP (*(.fini_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .dtors))
|
||||||
|
PROVIDE_HIDDEN (__fini_array_end = .);
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.ctors :
|
||||||
|
{
|
||||||
|
/* gcc uses crtbegin.o to find the start of
|
||||||
|
the constructors, so we make sure it is
|
||||||
|
first. Because this is a wildcard, it
|
||||||
|
doesn't matter if the user does not
|
||||||
|
actually link against crtbegin.o; the
|
||||||
|
linker won't look for a file to match a
|
||||||
|
wildcard. The wildcard also means that it
|
||||||
|
doesn't matter which directory crtbegin.o
|
||||||
|
is in. */
|
||||||
|
KEEP (*crtbegin.o(.ctors))
|
||||||
|
KEEP (*crtbegin?.o(.ctors))
|
||||||
|
/* We don't want to include the .ctor section from
|
||||||
|
the crtend.o file until after the sorted ctors.
|
||||||
|
The .ctor section from the crtend file contains the
|
||||||
|
end of ctors marker and it must be last */
|
||||||
|
KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .ctors))
|
||||||
|
KEEP (*(SORT(.ctors.*)))
|
||||||
|
KEEP (*(.ctors))
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.dtors :
|
||||||
|
{
|
||||||
|
KEEP (*crtbegin.o(.dtors))
|
||||||
|
KEEP (*crtbegin?.o(.dtors))
|
||||||
|
KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .dtors))
|
||||||
|
KEEP (*(SORT(.dtors.*)))
|
||||||
|
KEEP (*(.dtors))
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
. = ALIGN(4);
|
||||||
|
PROVIDE( _eilm = . );
|
||||||
|
|
||||||
|
.lalign :
|
||||||
|
{
|
||||||
|
. = ALIGN(4);
|
||||||
|
PROVIDE( _data_lma = . );
|
||||||
|
} >flash AT>flash
|
||||||
|
|
||||||
|
.dalign :
|
||||||
|
{
|
||||||
|
. = ALIGN(4);
|
||||||
|
PROVIDE( _data = . );
|
||||||
|
} >ram AT>flash
|
||||||
|
|
||||||
|
|
||||||
|
.data :
|
||||||
|
{
|
||||||
|
*(.rdata)
|
||||||
|
|
||||||
|
*(.gnu.linkonce.r.*)
|
||||||
|
*(.data .data.*)
|
||||||
|
*(.gnu.linkonce.d.*)
|
||||||
|
. = ALIGN(8);
|
||||||
|
PROVIDE( __global_pointer$ = . + 0x800);
|
||||||
|
*(.sdata .sdata.*)
|
||||||
|
*(.gnu.linkonce.s.*)
|
||||||
|
. = ALIGN(8);
|
||||||
|
*(.srodata.cst16)
|
||||||
|
*(.srodata.cst8)
|
||||||
|
*(.srodata.cst4)
|
||||||
|
*(.srodata.cst2)
|
||||||
|
*(.srodata .srodata.*)
|
||||||
|
} >ram AT>flash
|
||||||
|
|
||||||
|
. = ALIGN(4);
|
||||||
|
PROVIDE( _edata = . );
|
||||||
|
PROVIDE( edata = . );
|
||||||
|
|
||||||
|
PROVIDE( _fbss = . ); /*0X200052A0 0X200002A0*/
|
||||||
|
PROVIDE( __bss_start = . );
|
||||||
|
.bss :
|
||||||
|
{
|
||||||
|
*(.sbss*)
|
||||||
|
*(.gnu.linkonce.sb.*)
|
||||||
|
*(.bss .bss.*)
|
||||||
|
*(.gnu.linkonce.b.*)
|
||||||
|
*(COMMON)
|
||||||
|
. = ALIGN(4);
|
||||||
|
} >ram AT>ram
|
||||||
|
|
||||||
|
. = ALIGN(8);
|
||||||
|
PROVIDE( _end = . ); /*0X2000,0340*/
|
||||||
|
PROVIDE( end = . );
|
||||||
|
PROVIDE( heap_start = . );
|
||||||
|
|
||||||
|
.stack ORIGIN(ram) + LENGTH(ram) - __stack_size :
|
||||||
|
{
|
||||||
|
PROVIDE( heap_end = . );
|
||||||
|
. = __stack_size;
|
||||||
|
PROVIDE( _sp = . );
|
||||||
|
} >ram AT>ram
|
||||||
|
}
|
||||||
@@ -29,11 +29,9 @@
|
|||||||
*
|
*
|
||||||
* Returns the value read from addr.
|
* Returns the value read from addr.
|
||||||
*/
|
*/
|
||||||
static uint8_t fusb_read_byte(uint8_t addr)
|
static uint8_t fusb_read_byte(uint8_t addr) {
|
||||||
{
|
|
||||||
uint8_t data[1];
|
uint8_t data[1];
|
||||||
if (!FRToSI2C::Mem_Read(FUSB302B_ADDR, addr, (uint8_t *)data, 1))
|
if (!FRToSI2C::Mem_Read(FUSB302B_ADDR, addr, (uint8_t*) data, 1)) {
|
||||||
{
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
return data[0];
|
return data[0];
|
||||||
@@ -47,8 +45,7 @@ static uint8_t fusb_read_byte(uint8_t addr)
|
|||||||
* size: The number of bytes to read
|
* size: The number of bytes to read
|
||||||
* buf: The buffer into which data will be read
|
* buf: The buffer into which data will be read
|
||||||
*/
|
*/
|
||||||
static bool fusb_read_buf(uint8_t addr, uint8_t size, uint8_t *buf)
|
static bool fusb_read_buf(uint8_t addr, uint8_t size, uint8_t *buf) {
|
||||||
{
|
|
||||||
return FRToSI2C::Mem_Read(FUSB302B_ADDR, addr, buf, size);
|
return FRToSI2C::Mem_Read(FUSB302B_ADDR, addr, buf, size);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -59,9 +56,9 @@ static bool fusb_read_buf(uint8_t addr, uint8_t size, uint8_t *buf)
|
|||||||
* addr: The memory address to which we will write
|
* addr: The memory address to which we will write
|
||||||
* byte: The value to write
|
* byte: The value to write
|
||||||
*/
|
*/
|
||||||
static bool fusb_write_byte(uint8_t addr, uint8_t byte)
|
static bool fusb_write_byte(uint8_t addr, uint8_t byte) {
|
||||||
{
|
FRToSI2C::Mem_Write(FUSB302B_ADDR, addr, (uint8_t*) &byte, 1);
|
||||||
return FRToSI2C::Mem_Write(FUSB302B_ADDR, addr, (uint8_t *)&byte, 1);
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -72,29 +69,27 @@ static bool fusb_write_byte(uint8_t addr, uint8_t byte)
|
|||||||
* size: The number of bytes to write
|
* size: The number of bytes to write
|
||||||
* buf: The buffer to write
|
* buf: The buffer to write
|
||||||
*/
|
*/
|
||||||
static bool fusb_write_buf(uint8_t addr, uint8_t size, const uint8_t *buf)
|
static bool fusb_write_buf(uint8_t addr, uint8_t size, const uint8_t *buf) {
|
||||||
{
|
FRToSI2C::Mem_Write(FUSB302B_ADDR, addr, (uint8_t*)buf, size);
|
||||||
return FRToSI2C::Mem_Write(FUSB302B_ADDR, addr, buf, size);
|
return true; //TODO
|
||||||
}
|
}
|
||||||
|
|
||||||
void fusb_send_message(const union pd_msg *msg)
|
void fusb_send_message(const union pd_msg *msg) {
|
||||||
{
|
if (!FRToSI2C::lock2()) {
|
||||||
if (!FRToSI2C::lock2())
|
|
||||||
{
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
/* Token sequences for the FUSB302B */
|
/* Token sequences for the FUSB302B */
|
||||||
static uint8_t sop_seq[5] = {
|
static uint8_t sop_seq[5] = {
|
||||||
FUSB_FIFO_TX_SOP1,
|
FUSB_FIFO_TX_SOP1,
|
||||||
FUSB_FIFO_TX_SOP1,
|
FUSB_FIFO_TX_SOP1,
|
||||||
FUSB_FIFO_TX_SOP1,
|
FUSB_FIFO_TX_SOP1,
|
||||||
FUSB_FIFO_TX_SOP2,
|
FUSB_FIFO_TX_SOP2,
|
||||||
FUSB_FIFO_TX_PACKSYM};
|
FUSB_FIFO_TX_PACKSYM };
|
||||||
static const uint8_t eop_seq[4] = {
|
static const uint8_t eop_seq[4] = {
|
||||||
FUSB_FIFO_TX_JAM_CRC,
|
FUSB_FIFO_TX_JAM_CRC,
|
||||||
FUSB_FIFO_TX_EOP,
|
FUSB_FIFO_TX_EOP,
|
||||||
FUSB_FIFO_TX_TXOFF,
|
FUSB_FIFO_TX_TXOFF,
|
||||||
FUSB_FIFO_TX_TXON};
|
FUSB_FIFO_TX_TXON };
|
||||||
|
|
||||||
/* Take the I2C2 mutex now so there can't be a race condition on sop_seq */
|
/* Take the I2C2 mutex now so there can't be a race condition on sop_seq */
|
||||||
/* Get the length of the message: a two-octet header plus NUMOBJ four-octet
|
/* Get the length of the message: a two-octet header plus NUMOBJ four-octet
|
||||||
@@ -105,188 +100,155 @@ void fusb_send_message(const union pd_msg *msg)
|
|||||||
sop_seq[4] = FUSB_FIFO_TX_PACKSYM | msg_len;
|
sop_seq[4] = FUSB_FIFO_TX_PACKSYM | msg_len;
|
||||||
|
|
||||||
/* Write all three parts of the message to the TX FIFO */
|
/* Write all three parts of the message to the TX FIFO */
|
||||||
fusb_write_buf(FUSB_FIFOS, 5, sop_seq);
|
fusb_write_buf( FUSB_FIFOS, 5, sop_seq);
|
||||||
fusb_write_buf(FUSB_FIFOS, msg_len, msg->bytes);
|
fusb_write_buf( FUSB_FIFOS, msg_len, msg->bytes);
|
||||||
fusb_write_buf(FUSB_FIFOS, 4, eop_seq);
|
fusb_write_buf( FUSB_FIFOS, 4, eop_seq);
|
||||||
|
|
||||||
FRToSI2C::unlock2();
|
FRToSI2C::unlock2();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t fusb_read_message(union pd_msg *msg)
|
uint8_t fusb_read_message(union pd_msg *msg) {
|
||||||
{
|
if (!FRToSI2C::lock2()) {
|
||||||
if (!FRToSI2C::lock2())
|
return 1;
|
||||||
{
|
|
||||||
asm("bkpt");
|
|
||||||
}
|
}
|
||||||
static uint8_t garbage[4];
|
static uint8_t garbage[4];
|
||||||
uint8_t numobj;
|
uint8_t numobj;
|
||||||
|
|
||||||
// Read the header. If its not a SOP we dont actually want it at all
|
// Read the header. If its not a SOP we dont actually want it at all
|
||||||
// But on some revisions of the fusb if you dont both pick them up and read them out of the fifo, it gets stuck
|
// But on some revisions of the fusb if you dont both pick them up and read them out of the fifo, it gets stuck
|
||||||
fusb_read_byte(FUSB_FIFOS);
|
fusb_read_byte( FUSB_FIFOS);
|
||||||
/* Read the message header into msg */
|
/* Read the message header into msg */
|
||||||
fusb_read_buf(FUSB_FIFOS, 2, msg->bytes);
|
fusb_read_buf( FUSB_FIFOS, 2, msg->bytes);
|
||||||
/* Get the number of data objects */
|
/* Get the number of data objects */
|
||||||
numobj = PD_NUMOBJ_GET(msg);
|
numobj = PD_NUMOBJ_GET(msg);
|
||||||
/* If there is at least one data object, read the data objects */
|
/* If there is at least one data object, read the data objects */
|
||||||
if (numobj > 0)
|
if (numobj > 0) {
|
||||||
{
|
fusb_read_buf( FUSB_FIFOS, numobj * 4, msg->bytes + 2);
|
||||||
fusb_read_buf(FUSB_FIFOS, numobj * 4, msg->bytes + 2);
|
|
||||||
}
|
}
|
||||||
/* Throw the CRC32 in the garbage, since the PHY already checked it. */
|
/* Throw the CRC32 in the garbage, since the PHY already checked it. */
|
||||||
fusb_read_buf(FUSB_FIFOS, 4, garbage);
|
fusb_read_buf( FUSB_FIFOS, 4, garbage);
|
||||||
|
|
||||||
FRToSI2C::unlock2();
|
FRToSI2C::unlock2();
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void fusb_send_hardrst()
|
void fusb_send_hardrst() {
|
||||||
{
|
|
||||||
|
|
||||||
if (!FRToSI2C::lock2())
|
if (!FRToSI2C::lock2()) {
|
||||||
{
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
/* Send a hard reset */
|
/* Send a hard reset */
|
||||||
fusb_write_byte(FUSB_CONTROL3, 0x07 | FUSB_CONTROL3_SEND_HARD_RESET);
|
fusb_write_byte( FUSB_CONTROL3, 0x07 | FUSB_CONTROL3_SEND_HARD_RESET);
|
||||||
|
|
||||||
FRToSI2C::unlock2();
|
FRToSI2C::unlock2();
|
||||||
}
|
}
|
||||||
|
|
||||||
void fusb_setup()
|
void fusb_setup() {
|
||||||
{
|
|
||||||
GPIO_InitTypeDef GPIO_InitStruct;
|
|
||||||
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_MEDIUM;
|
|
||||||
GPIO_InitStruct.Pin = GPIO_PIN_9;
|
|
||||||
GPIO_InitStruct.Mode = GPIO_MODE_IT_FALLING;
|
|
||||||
GPIO_InitStruct.Pull = GPIO_PULLUP;
|
|
||||||
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
|
|
||||||
HAL_NVIC_SetPriority(EXTI9_5_IRQn, 12, 0);
|
|
||||||
HAL_NVIC_EnableIRQ(EXTI9_5_IRQn);
|
|
||||||
|
|
||||||
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED)
|
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) {
|
||||||
{
|
if (!FRToSI2C::lock2()) {
|
||||||
if (!FRToSI2C::lock2())
|
|
||||||
{
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/* Fully reset the FUSB302B */
|
/* Fully reset the FUSB302B */
|
||||||
fusb_write_byte(FUSB_RESET, FUSB_RESET_SW_RES);
|
fusb_write_byte( FUSB_RESET, FUSB_RESET_SW_RES);
|
||||||
osDelay(2);
|
osDelay(2);
|
||||||
if (!fusb_read_id())
|
if (!fusb_read_id()) {
|
||||||
{
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Turn on all power */
|
/* Turn on all power */
|
||||||
fusb_write_byte(FUSB_POWER, 0x0F);
|
fusb_write_byte( FUSB_POWER, 0x0F);
|
||||||
|
|
||||||
/* Set interrupt masks */
|
/* Set interrupt masks */
|
||||||
//Setting to 0 so interrupts are allowed
|
//Setting to 0 so interrupts are allowed
|
||||||
fusb_write_byte(FUSB_MASK1, 0x00);
|
fusb_write_byte( FUSB_MASK1, 0x00);
|
||||||
fusb_write_byte(FUSB_MASKA, 0x00);
|
fusb_write_byte( FUSB_MASKA, 0x00);
|
||||||
fusb_write_byte(FUSB_MASKB, 0x00);
|
fusb_write_byte( FUSB_MASKB, 0x00);
|
||||||
fusb_write_byte(FUSB_CONTROL0, 0b11 << 2);
|
fusb_write_byte( FUSB_CONTROL0, 0b11 << 2);
|
||||||
|
|
||||||
/* Enable automatic retransmission */
|
/* Enable automatic retransmission */
|
||||||
fusb_write_byte(FUSB_CONTROL3, 0x07);
|
fusb_write_byte( FUSB_CONTROL3, 0x07);
|
||||||
//set defaults
|
//set defaults
|
||||||
fusb_write_byte(FUSB_CONTROL2, 0x00);
|
fusb_write_byte( FUSB_CONTROL2, 0x00);
|
||||||
/* Flush the RX buffer */
|
/* Flush the RX buffer */
|
||||||
fusb_write_byte(FUSB_CONTROL1,
|
fusb_write_byte( FUSB_CONTROL1,
|
||||||
FUSB_CONTROL1_RX_FLUSH);
|
FUSB_CONTROL1_RX_FLUSH);
|
||||||
|
|
||||||
/* Measure CC1 */
|
/* Measure CC1 */
|
||||||
fusb_write_byte(FUSB_SWITCHES0, 0x07);
|
fusb_write_byte( FUSB_SWITCHES0, 0x07);
|
||||||
osDelay(10);
|
osDelay(10);
|
||||||
uint8_t cc1 = fusb_read_byte(FUSB_STATUS0) & FUSB_STATUS0_BC_LVL;
|
uint8_t cc1 = fusb_read_byte( FUSB_STATUS0) & FUSB_STATUS0_BC_LVL;
|
||||||
|
|
||||||
/* Measure CC2 */
|
/* Measure CC2 */
|
||||||
fusb_write_byte(FUSB_SWITCHES0, 0x0B);
|
fusb_write_byte( FUSB_SWITCHES0, 0x0B);
|
||||||
osDelay(10);
|
osDelay(10);
|
||||||
uint8_t cc2 = fusb_read_byte(FUSB_STATUS0) & FUSB_STATUS0_BC_LVL;
|
uint8_t cc2 = fusb_read_byte( FUSB_STATUS0) & FUSB_STATUS0_BC_LVL;
|
||||||
|
|
||||||
/* Select the correct CC line for BMC signaling; also enable AUTO_CRC */
|
/* Select the correct CC line for BMC signaling; also enable AUTO_CRC */
|
||||||
if (cc1 > cc2)
|
if (cc1 > cc2) {
|
||||||
{
|
fusb_write_byte( FUSB_SWITCHES1, 0x25);
|
||||||
fusb_write_byte(FUSB_SWITCHES1, 0x25);
|
fusb_write_byte( FUSB_SWITCHES0, 0x07);
|
||||||
fusb_write_byte(FUSB_SWITCHES0, 0x07);
|
} else {
|
||||||
|
fusb_write_byte( FUSB_SWITCHES1, 0x26);
|
||||||
|
fusb_write_byte( FUSB_SWITCHES0, 0x0B);
|
||||||
}
|
}
|
||||||
else
|
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) {
|
||||||
{
|
|
||||||
fusb_write_byte(FUSB_SWITCHES1, 0x26);
|
|
||||||
fusb_write_byte(FUSB_SWITCHES0, 0x0B);
|
|
||||||
}
|
|
||||||
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED)
|
|
||||||
{
|
|
||||||
FRToSI2C::unlock2();
|
FRToSI2C::unlock2();
|
||||||
}
|
}
|
||||||
fusb_reset();
|
fusb_reset();
|
||||||
}
|
}
|
||||||
|
|
||||||
void fusb_get_status(union fusb_status *status)
|
void fusb_get_status(union fusb_status *status) {
|
||||||
{
|
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) {
|
||||||
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED)
|
if (!FRToSI2C::lock2()) {
|
||||||
{
|
|
||||||
if (!FRToSI2C::lock2())
|
|
||||||
{
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Read the interrupt and status flags into status */
|
/* Read the interrupt and status flags into status */
|
||||||
fusb_read_buf(FUSB_STATUS0A, 7, status->bytes);
|
fusb_read_buf( FUSB_STATUS0A, 7, status->bytes);
|
||||||
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED)
|
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) {
|
||||||
{
|
|
||||||
FRToSI2C::unlock2();
|
FRToSI2C::unlock2();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
enum fusb_typec_current fusb_get_typec_current()
|
enum fusb_typec_current fusb_get_typec_current() {
|
||||||
{
|
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) {
|
||||||
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED)
|
if (!FRToSI2C::lock2()) {
|
||||||
{
|
|
||||||
if (!FRToSI2C::lock2())
|
|
||||||
{
|
|
||||||
return fusb_tcc_none;
|
return fusb_tcc_none;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/* Read the BC_LVL into a variable */
|
/* Read the BC_LVL into a variable */
|
||||||
enum fusb_typec_current bc_lvl = (enum fusb_typec_current)(fusb_read_byte(
|
enum fusb_typec_current bc_lvl = (enum fusb_typec_current) (fusb_read_byte(
|
||||||
FUSB_STATUS0) &
|
FUSB_STATUS0) & FUSB_STATUS0_BC_LVL);
|
||||||
FUSB_STATUS0_BC_LVL);
|
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) {
|
||||||
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED)
|
|
||||||
{
|
|
||||||
FRToSI2C::unlock2();
|
FRToSI2C::unlock2();
|
||||||
}
|
}
|
||||||
return bc_lvl;
|
return bc_lvl;
|
||||||
}
|
}
|
||||||
|
|
||||||
void fusb_reset()
|
void fusb_reset() {
|
||||||
{
|
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) {
|
||||||
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED)
|
if (!FRToSI2C::lock2()) {
|
||||||
{
|
|
||||||
if (!FRToSI2C::lock2())
|
|
||||||
{
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Flush the TX buffer */
|
/* Flush the TX buffer */
|
||||||
fusb_write_byte(FUSB_CONTROL0, 0x44);
|
fusb_write_byte( FUSB_CONTROL0, 0x44);
|
||||||
/* Flush the RX buffer */
|
/* Flush the RX buffer */
|
||||||
fusb_write_byte(FUSB_CONTROL1, FUSB_CONTROL1_RX_FLUSH);
|
fusb_write_byte( FUSB_CONTROL1, FUSB_CONTROL1_RX_FLUSH);
|
||||||
/* Reset the PD logic */
|
/* Reset the PD logic */
|
||||||
// fusb_write_byte( FUSB_RESET, FUSB_RESET_PD_RESET);
|
// fusb_write_byte( FUSB_RESET, FUSB_RESET_PD_RESET);
|
||||||
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED)
|
if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) {
|
||||||
{
|
|
||||||
FRToSI2C::unlock2();
|
FRToSI2C::unlock2();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool fusb_read_id()
|
bool fusb_read_id() {
|
||||||
{
|
|
||||||
//Return true if read of the revision ID is sane
|
//Return true if read of the revision ID is sane
|
||||||
uint8_t version = 0;
|
uint8_t version = 0;
|
||||||
fusb_read_buf(FUSB_DEVICE_ID, 1, &version);
|
fusb_read_buf(FUSB_DEVICE_ID, 1, &version);
|
||||||
@@ -294,8 +256,7 @@ bool fusb_read_id()
|
|||||||
return false;
|
return false;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
uint8_t fusb302_detect()
|
uint8_t fusb302_detect() {
|
||||||
{
|
|
||||||
//Probe the I2C bus for its address
|
//Probe the I2C bus for its address
|
||||||
return FRToSI2C::probe(FUSB302B_ADDR);
|
return FRToSI2C::probe(FUSB302B_ADDR);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -8,7 +8,12 @@
|
|||||||
#include "stdlib.h"
|
#include "stdlib.h"
|
||||||
#include "task.h"
|
#include "task.h"
|
||||||
#include "I2C_Wrapper.hpp"
|
#include "I2C_Wrapper.hpp"
|
||||||
|
#include "fusbpd.h"
|
||||||
void postRToSInit() {
|
void postRToSInit() {
|
||||||
// Any after RTos setup
|
// Any after RTos setup
|
||||||
FRToSI2C::FRToSInit();
|
FRToSI2C::FRToSInit();
|
||||||
|
#ifdef POW_PD
|
||||||
|
//Spawn all of the USB-C processors
|
||||||
|
fusb302_start_processing();
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ void preRToSInit() {
|
|||||||
eclic_priority_group_set(ECLIC_PRIGROUP_LEVEL4_PRIO0);
|
eclic_priority_group_set(ECLIC_PRIGROUP_LEVEL4_PRIO0);
|
||||||
eclic_global_interrupt_enable();
|
eclic_global_interrupt_enable();
|
||||||
hardware_init();
|
hardware_init();
|
||||||
FRToSI2C::init();
|
FRToSI2C::FRToSInit();
|
||||||
gpio_bit_reset(OLED_RESET_GPIO_Port, OLED_RESET_Pin);
|
gpio_bit_reset(OLED_RESET_GPIO_Port, OLED_RESET_Pin);
|
||||||
delay_ms(50);
|
delay_ms(50);
|
||||||
gpio_bit_set(OLED_RESET_GPIO_Port, OLED_RESET_Pin);
|
gpio_bit_set(OLED_RESET_GPIO_Port, OLED_RESET_Pin);
|
||||||
|
|||||||
Reference in New Issue
Block a user