244 lines
7.1 KiB
C
244 lines
7.1 KiB
C
/*
|
||
*********************************************************************************************************
|
||
* IAR Development Kits
|
||
* on the
|
||
*
|
||
* Nano130
|
||
*
|
||
* Filename : spi_flash.c
|
||
* Version : V1.00
|
||
* Programmer(s) : Qian Xianghong
|
||
*********************************************************************************************************
|
||
*/
|
||
|
||
#include "includes.h"
|
||
|
||
// 片选
|
||
#define LIS2DH12_CS_LOW() LL_GPIO_ResetOutputPin(GPIOB, LL_GPIO_PIN_12)
|
||
#define LIS2DH12_CS_HIGH() LL_GPIO_SetOutputPin(GPIOB, LL_GPIO_PIN_12)
|
||
|
||
// 加速度计ID
|
||
uint8_t Accelero_ID = 0;
|
||
// 运动状态(默认为1,万一加速度计有问题)
|
||
volatile uint8_t Motion_Status = 1;
|
||
// 运动检测:第一次需要定位
|
||
volatile uint8_t Motion_Detected = 1;
|
||
|
||
typedef unsigned char uchar;
|
||
typedef unsigned short ushort;
|
||
typedef unsigned int uint;
|
||
|
||
//****************************************
|
||
// 定义LIS2DH12内部地址
|
||
//****************************************
|
||
#define CTRL_REG1 0x20
|
||
#define CTRL_REG2 0x21
|
||
#define CTRL_REG3 0x22
|
||
#define CTRL_REG4 0x23
|
||
#define CTRL_REG5 0x24
|
||
#define CTRL_REG6 0x25
|
||
#define ACT_THS 0x3E
|
||
#define ACT_DUR 0x3F
|
||
#define WHO_AM_I 0x0F //地址寄存器(默认数值0x33,只读)
|
||
|
||
uchar Single_WriteSPI(uchar REG_Address,uchar REG_data)
|
||
{
|
||
LIS2DH12_CS_LOW();
|
||
|
||
// Write Address
|
||
*(__IO uint8_t *)&SPI2->DR = (REG_Address & 0x3F);
|
||
while(!(SPI2->SR & SPI_SR_RXNE));
|
||
*(__IO uint8_t *)&SPI2->DR;
|
||
|
||
// Write data
|
||
*(__IO uint8_t *)&SPI2->DR = REG_data;
|
||
while(!(SPI2->SR & SPI_SR_RXNE));
|
||
*(__IO uint8_t *)&SPI2->DR;
|
||
|
||
LIS2DH12_CS_HIGH();
|
||
|
||
return 1;
|
||
}
|
||
|
||
uchar Single_ReadSPI(uchar REG_Address, uchar *REG_data)
|
||
{
|
||
LIS2DH12_CS_LOW();
|
||
|
||
// Read Address
|
||
*(__IO uint8_t *)&SPI2->DR = ((REG_Address & 0x3F) | 0x80);
|
||
while(!(SPI2->SR & SPI_SR_RXNE));
|
||
*(__IO uint8_t *)&SPI2->DR;
|
||
|
||
// 提供Clock
|
||
*(__IO uint8_t *)&SPI2->DR = 0;
|
||
while(!(SPI2->SR & SPI_SR_RXNE));
|
||
*REG_data = *(__IO uint8_t *)&SPI2->DR;
|
||
|
||
LIS2DH12_CS_HIGH();
|
||
|
||
return 1;
|
||
}
|
||
|
||
// 读取运动状态
|
||
void Accelero_ReadStatus(uint8_t int2_pin)
|
||
{
|
||
// 当前运动状态
|
||
Motion_Status = !int2_pin; // Active low
|
||
PRINTF("\r\nHard Motion status = %d\r\n", Motion_Status);
|
||
// 检测到了运动(需要重新定位)
|
||
if(Motion_Status)
|
||
Motion_Detected = 1;
|
||
}
|
||
|
||
/**
|
||
* @brief EXTI line detection callback.
|
||
* @param GPIO_Pin: Specifies the port pin connected to corresponding EXTI line.
|
||
* @retval None
|
||
*/
|
||
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
|
||
{
|
||
if(GPIO_Pin == LL_EXTI_LINE_10)
|
||
{
|
||
if(Wakeup_Sleeping)
|
||
{
|
||
SysTick->CTRL |= (SysTick_CTRL_ENABLE_Msk | SysTick_CTRL_TICKINT_Msk);
|
||
delay_ms(10);
|
||
|
||
Vcc_Enable();
|
||
delay_ms(40);
|
||
Wakeup_Sleeping = 0;
|
||
|
||
printf("\nWakeup by Accelero ...\n");
|
||
}
|
||
|
||
// 读取运动状态
|
||
Accelero_ReadStatus(LL_GPIO_IsInputPinSet(GPIOD, LL_GPIO_PIN_10));
|
||
}
|
||
}
|
||
|
||
// 加速度中断处理,本函数被【key.c】模块中【GPDEF_IRQHandler】函数调用
|
||
void Accelero_Init()
|
||
{
|
||
LL_EXTI_InitTypeDef EXTI_InitStruct = {0};
|
||
LL_GPIO_InitTypeDef GPIO_InitStruct = {0};
|
||
|
||
LL_AHB2_GRP1_EnableClock(LL_AHB2_GRP1_PERIPH_GPIOB);
|
||
/**SPI2 GPIO Configuration
|
||
PB13 ------> SPI2_SCK
|
||
PB14 ------> SPI2_MISO
|
||
PB15 ------> SPI2_MOSI
|
||
*/
|
||
GPIO_InitStruct.Pin = LL_GPIO_PIN_13|LL_GPIO_PIN_14|LL_GPIO_PIN_15;
|
||
GPIO_InitStruct.Mode = LL_GPIO_MODE_ALTERNATE;
|
||
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_MEDIUM;
|
||
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
|
||
GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
|
||
GPIO_InitStruct.Alternate = LL_GPIO_AF_5;
|
||
LL_GPIO_Init(GPIOB, &GPIO_InitStruct);
|
||
|
||
/**/
|
||
LL_GPIO_SetOutputPin(GPIOB, LL_GPIO_PIN_12);
|
||
|
||
/**/
|
||
GPIO_InitStruct.Pin = LL_GPIO_PIN_12;
|
||
GPIO_InitStruct.Mode = LL_GPIO_MODE_OUTPUT;
|
||
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_LOW;
|
||
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL;
|
||
GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
|
||
LL_GPIO_Init(GPIOB, &GPIO_InitStruct);
|
||
|
||
LL_AHB2_GRP1_EnableClock(LL_AHB2_GRP1_PERIPH_GPIOD);
|
||
|
||
/**/
|
||
LL_SYSCFG_SetEXTISource(LL_SYSCFG_EXTI_PORTD, LL_SYSCFG_EXTI_LINE10);
|
||
|
||
/**/
|
||
EXTI_InitStruct.Line_0_31 = LL_EXTI_LINE_10;
|
||
EXTI_InitStruct.Line_32_63 = LL_EXTI_LINE_NONE;
|
||
EXTI_InitStruct.LineCommand = ENABLE;
|
||
EXTI_InitStruct.Mode = LL_EXTI_MODE_IT;
|
||
EXTI_InitStruct.Trigger = LL_EXTI_TRIGGER_RISING_FALLING;
|
||
LL_EXTI_Init(&EXTI_InitStruct);
|
||
|
||
/**/
|
||
LL_GPIO_SetPinPull(GPIOD, LL_GPIO_PIN_10, LL_GPIO_PULL_UP);
|
||
|
||
/**/
|
||
LL_GPIO_SetPinMode(GPIOD, LL_GPIO_PIN_10, LL_GPIO_MODE_INPUT);
|
||
}
|
||
|
||
// 初始化LIS2DH12
|
||
void Accelero_Open()
|
||
{
|
||
LL_SPI_InitTypeDef SPI_InitStruct = {0};
|
||
LL_EXTI_InitTypeDef EXTI_InitStruct = {0};
|
||
|
||
/* Peripheral clock enable */
|
||
LL_APB1_GRP1_EnableClock(LL_APB1_GRP1_PERIPH_SPI2);
|
||
|
||
/* SPI2 parameter configuration*/
|
||
SPI_InitStruct.TransferDirection = LL_SPI_FULL_DUPLEX;
|
||
SPI_InitStruct.Mode = LL_SPI_MODE_MASTER;
|
||
SPI_InitStruct.DataWidth = LL_SPI_DATAWIDTH_8BIT;
|
||
SPI_InitStruct.ClockPolarity = LL_SPI_POLARITY_LOW;
|
||
SPI_InitStruct.ClockPhase = LL_SPI_PHASE_1EDGE;
|
||
SPI_InitStruct.NSS = LL_SPI_NSS_SOFT;
|
||
SPI_InitStruct.BaudRate = LL_SPI_BAUDRATEPRESCALER_DIV2;
|
||
SPI_InitStruct.BitOrder = LL_SPI_MSB_FIRST;
|
||
SPI_InitStruct.CRCCalculation = LL_SPI_CRCCALCULATION_DISABLE;
|
||
SPI_InitStruct.CRCPoly = 7;
|
||
LL_SPI_Init(SPI2, &SPI_InitStruct);
|
||
LL_SPI_SetStandard(SPI2, LL_SPI_PROTOCOL_MOTOROLA);
|
||
LL_SPI_DisableNSSPulseMgt(SPI2);
|
||
|
||
LL_SPI_SetRxFIFOThreshold(SPI2, LL_SPI_RX_FIFO_TH_QUARTER);
|
||
LL_SPI_Enable(SPI2);
|
||
|
||
Single_WriteSPI(CTRL_REG1, 0x5F); //控制寄存器,(100Hz, Low-power mode,Enable XYZ)
|
||
Single_WriteSPI(CTRL_REG2, 0x00); //控制寄存器,(High-pass filter disabled)
|
||
Single_WriteSPI(CTRL_REG3, 0x00); //控制寄存器
|
||
Single_WriteSPI(CTRL_REG4, 0x00); //控制寄存器,(4-wire SPI,Self-test disabled, HR=0, FS= ±2g)
|
||
Single_WriteSPI(CTRL_REG5, 0x00); //控制寄存器,(FIFO disabled)
|
||
Single_WriteSPI(CTRL_REG6, 0x08); //控制寄存器,(Enable activity interrupt on INT2 pin)
|
||
|
||
// Activate/Inactivate: 门限寄存器,(x 4g/250 mg)
|
||
if(dcBuff.configDisplay.op_SEND_GPS_DATA) // 槽车最灵敏,只在行驶过程中判断
|
||
Single_WriteSPI(ACT_THS, 4);
|
||
else if(dcBuff.configDisplay.op_USE_CAPACITY_SENSOR) // 杜瓦瓶最不灵敏(电池容量低)
|
||
Single_WriteSPI(ACT_THS, 40);
|
||
else // 罐箱
|
||
Single_WriteSPI(ACT_THS, 20);
|
||
// Activate/Inactivate: 持续时间寄存器
|
||
Single_WriteSPI(ACT_DUR, 40);
|
||
|
||
// 读出ID:测试通信是否正常
|
||
Accelero_CheckID();
|
||
// 非罐箱或槽车版,禁止加速度中断
|
||
if(!(dcBuff.configDisplay.op_BOX_VER || dcBuff.configDisplay.op_SEND_GPS_DATA))
|
||
{
|
||
EXTI_InitStruct.Line_0_31 = LL_EXTI_LINE_10;
|
||
EXTI_InitStruct.Line_32_63 = LL_EXTI_LINE_NONE;
|
||
EXTI_InitStruct.LineCommand = DISABLE;
|
||
EXTI_InitStruct.Mode = LL_EXTI_MODE_IT;
|
||
EXTI_InitStruct.Trigger = LL_EXTI_TRIGGER_RISING_FALLING;
|
||
LL_EXTI_Init(&EXTI_InitStruct);
|
||
}
|
||
|
||
NVIC_SetPriority(EXTI15_10_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),5, 0));
|
||
NVIC_EnableIRQ(EXTI15_10_IRQn);
|
||
}
|
||
|
||
// 读出ID放在Accelero_ID(检查加速度计是否正常)
|
||
void Accelero_CheckID()
|
||
{
|
||
// 读出ID:测试通信是否正常
|
||
Single_ReadSPI(WHO_AM_I, &Accelero_ID);
|
||
PRINTF("\r\nAccelero ID = 0x%02X\r\n", Accelero_ID);
|
||
|
||
if(Accelero_ID == ACCELERO_ID)
|
||
{
|
||
Motion_Status = !LL_GPIO_IsInputPinSet(GPIOD, LL_GPIO_PIN_10);
|
||
PRINTF("\r\nInit Motion status = %d\r\n", Motion_Status);
|
||
}
|
||
}
|