valveboard/examples/stm32f103/HARDWARE/valve/valve.c
2021-11-22 00:34:34 +08:00

90 lines
2.8 KiB
C

#include "valve.h"
uint8_t waiting_send = 0;
uint8_t sending = 0;
uint8_t period = 0;
uint8_t *valve_data = 0;
void VALVE_Init()
{
VALVE_TIM_PERIPHERAL_FUNC(VALVE_TIM_PERIPHERAL, ENABLE);
VALVE_GPIO_PERIPHERAL_FUNC(VALVE_SCLK_PERIPHERAL | VALVE_SEN_PERIPHERAL | VALVE_SDATA_PERIPHERAL, ENABLE);
NVIC_InitTypeDef NVIC_InitStructure;
GPIO_InitTypeDef GPIO_InitStructure;
TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Pin = VALVE_SCLK_PIN;
GPIO_Init(VALVE_SCLK_PORT, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = VALVE_SEN_PIN;
GPIO_ResetBits(VALVE_SEN_PORT, VALVE_SEN_PIN);
GPIO_Init(VALVE_SEN_PORT, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = VALVE_SDATA_PIN;
GPIO_Init(VALVE_SDATA_PORT, &GPIO_InitStructure);
TIM_TimeBaseInitStructure.TIM_ClockDivision = TIM_CKD_DIV1;
TIM_TimeBaseInitStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseInitStructure.TIM_Period = 18000 - 1;
TIM_TimeBaseInitStructure.TIM_Prescaler = 1 - 1;
NVIC_InitStructure.NVIC_IRQChannel = VALVE_TIME_IRQN;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
NVIC_Init(&NVIC_InitStructure);
TIM_TimeBaseInit(VALVE_TIM, &TIM_TimeBaseInitStructure);
TIM_ClearFlag(VALVE_TIM, TIM_IT_Update);
TIM_ITConfig(VALVE_TIM, TIM_IT_Update, ENABLE);
TIM_Cmd(VALVE_TIM, ENABLE);
}
ErrorStatus VALVE_Send(uint8_t *valveData)
{
int timeout = VALVE_COMMUNICATION_TIMEOUT;
while (sending && --timeout)
;
if (timeout == 0)
return ERROR;
waiting_send = 1;
valve_data = valveData;
return SUCCESS;
}
void VALVE_TIM_IRQHANDLER()
{
static uint8_t current_channel = 0;
if (VALVE_TIM->SR & TIM_IT_Update)
{
if (period == 0)
VALVE_SCLK_PORT->BSRR = VALVE_SCLK_PIN;
else if (period == 2)
{
VALVE_SCLK_PORT->BRR = VALVE_SCLK_PIN;
if (waiting_send)
{
current_channel = 0;
VALVE_SEN_PORT->BSRR = VALVE_SEN_PIN;
waiting_send = 0;
sending = 1;
}
if (current_channel == VALVE_CHANNEL_NUM)
{
sending = 0;
VALVE_SEN_PORT->BRR = VALVE_SEN_PIN;
}
}
else if (period == 3 && sending == 1)
{
uint32_t tmpreg = VALVE_SDATA_PORT->ODR & ~VALVE_SDATA_PIN;
VALVE_SDATA_PORT->ODR = tmpreg | (uint16_t)(!valve_data[current_channel] * VALVE_SDATA_PIN);
current_channel += 1;
}
period++;
period %= 4;
VALVE_TIM->SR &= ~TIM_IT_Update;
}
}