/*
 * rs485.c
 *
 *  Created on: 2024年6月20日
 *      Author: psx
 */

#include "rs485.h"
#include "uart_dev.h"
#include "ring_queue.h"


void USART3_IRQHandler(void) __attribute__((interrupt("WCH-Interrupt-fast")));
void USART4_IRQHandler(void) __attribute__((interrupt("WCH-Interrupt-fast")));

//#define USART3_buffer_len 128
//#define USART4_buffer_len 128

//uint8_t USART3_Rbuffer_Num = 0;
//uint8_t USART4_Rbuffer_Num = 0;

/* 接收缓冲区数组 */
uint8_t USART3_Rbuffer[1] = {0x00};
uint8_t USART4_Rbuffer[1] = {0x00};
///* 发送 */
//uint8_t USART3_Tbuffer_Num = 0;
//uint8_t USART3_Tbuffer_Len = 0;
//uint8_t *USART3_Tbuffer;


/*
 * @brief 初始化GW485
 * @param
 * @retval
 */
void GW_485_Init(int baud)
{
    /* 初始化GW485控制引脚 */
    GPIO_InitTypeDef   GPIO_InitStructure;
    GPIO_InitStructure.GPIO_Pin = Pin_GW_485_RDE;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;              //设置PB4为复用推挽输出
    GPIO_Init(GPIO_GW_485_RDE, &GPIO_InitStructure);
    GPIO_WriteBit(GPIO_GW_485_RDE, Pin_GW_485_RDE, read);

    USART_InitTypeDef  USART_InitStructure;
    NVIC_InitTypeDef   NVIC_InitStructure;

    /* USART4  TX --> PB0   RX --> PB1  */
    RCC_PB2PeriphClockCmd(RCC_PB2Periph_GPIOB, ENABLE);
    RCC_PB1PeriphClockCmd(RCC_PB1Periph_USART4, ENABLE);

    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;              //设置PB0为复用推挽输出
    GPIO_Init(GPIOB, &GPIO_InitStructure);

    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;        //设置PB1为浮空输入
    GPIO_Init(GPIOB, &GPIO_InitStructure);

    USART_InitStructure.USART_BaudRate = baud;
    USART_InitStructure.USART_WordLength = USART_WordLength_8b;
    USART_InitStructure.USART_StopBits = USART_StopBits_1;
    USART_InitStructure.USART_Parity = USART_Parity_No;
    USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
    USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
    USART_Init(USART4, &USART_InitStructure);

    NVIC_InitStructure.NVIC_IRQChannel = USART4_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=1;      //抢占优先级为1
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;           //子优先级为2
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;              //IRQ通道使能
    NVIC_Init(&NVIC_InitStructure);                              //中断优先级初始化

    USART_ITConfig(USART4, USART_IT_RXNE, ENABLE);
//    USART_ITConfig(USART4, USART_IT_IDLE, ENABLE);

    USART_Cmd(USART4,ENABLE);
}

/*
 * @brief 初始化BAT_485
 * @param
 * @retval
 */
void BAT_485_Init(int baud)
{
    /* 初始化GW485控制引脚 */
    GPIO_InitTypeDef   GPIO_InitStructure;
    GPIO_InitStructure.GPIO_Pin = Pin_BAT_485_RDE;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;              //设置PB5为复用推挽输出
    GPIO_Init(GPIO_BAT_485_RDE, &GPIO_InitStructure);
    GPIO_WriteBit(GPIO_BAT_485_RDE, Pin_BAT_485_RDE, read);

    USART_InitTypeDef  USART_InitStructure;
    NVIC_InitTypeDef   NVIC_InitStructure;

    /* USART3  TX --> PB10   RX --> PB11  */
    RCC_PB2PeriphClockCmd(RCC_PB2Periph_GPIOB, ENABLE);
    RCC_PB1PeriphClockCmd(RCC_PB1Periph_USART3, ENABLE);

    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;              //设置PB10为复用推挽输出
    GPIO_Init(GPIOB, &GPIO_InitStructure);

    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;        //设置PB11为浮空输入
    GPIO_Init(GPIOB, &GPIO_InitStructure);

    USART_InitStructure.USART_BaudRate = baud;
    USART_InitStructure.USART_WordLength = USART_WordLength_8b;
    USART_InitStructure.USART_StopBits = USART_StopBits_1;
    USART_InitStructure.USART_Parity = USART_Parity_No;
    USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
    USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
    USART_Init(USART3, &USART_InitStructure);

    NVIC_InitStructure.NVIC_IRQChannel = USART3_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=1;      //抢占优先级为1
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;           //子优先级为1
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;              //IRQ通道使能
    NVIC_Init(&NVIC_InitStructure);                              //中断优先级初始化

    USART_ITConfig(USART3, USART_IT_RXNE, ENABLE);
//    USART_ITConfig(USART3, USART_IT_IDLE, ENABLE);

    USART_Cmd(USART3,ENABLE);
}

/*
 * @brief 通过485发送一个字节
 * @param pUSARTx 对应的串口设备
 * @param data 字符
 * @retval
 */
void USARTx_SendByte(USART_TypeDef* pUSARTx, uint8_t data)
{
//    if (pUSARTx == GW_485) {
//        GPIO_WriteBit(GPIO_GW_485_RDE, Pin_GW_485_RDE, write);
//    }
//    else if (pUSARTx == BAT_485) {
//        GPIO_WriteBit(GPIO_BAT_485_RDE, Pin_BAT_485_RDE, write);
//    }
//    else {
//        return;
//    }

    USART_SendData(pUSARTx, data);
    while(USART_GetFlagStatus(pUSARTx, USART_FLAG_TXE) == RESET);
//
//    if (pUSARTx == GW_485) {
//        GPIO_WriteBit(GPIO_GW_485_RDE, Pin_GW_485_RDE, read);
//    }
//    else if (pUSARTx == BAT_485) {
//        GPIO_WriteBit(GPIO_BAT_485_RDE, Pin_BAT_485_RDE, read);
//    }
//    else {
//        return;
//    }
}

///*
// * @brief 通过串口发送一个字节
// * @param pUSARTx 对应的串口设备
// * @param data 字符
// * @retval
// */
//void USARTx_SendByte_str(USART_TypeDef* pUSARTx, uint8_t data)
//{
//    USART_SendData(pUSARTx, data);
//    while(USART_GetFlagStatus(pUSARTx, USART_FLAG_TXE) == RESET);
//}
//
///*
// * @brief 通过485发送一个字符串
// * @param pUSARTx 对应的串口设备
// * @param data 字符串
// * @retval
// */
//void USARTx_SendStr(USART_TypeDef* pUSARTx, char *str)
//{
//    if (pUSARTx == GW_485) {
//        GPIO_WriteBit(GPIO_GW_485_RDE, Pin_GW_485_RDE, write);
//    }
//    else if (pUSARTx == BAT_485) {
//        GPIO_WriteBit(GPIO_BAT_485_RDE, Pin_BAT_485_RDE, write);
//    }
//    else {
//        return;
//    }
//
//    uint8_t i = 0;
//    do
//    {
//        USARTx_SendByte_str(pUSARTx, *(str+i));
//       i++;
//    }while(*(str+i) != '\0');
//    while(USART_GetFlagStatus(pUSARTx, USART_FLAG_TC) == RESET);
//
//    if (pUSARTx == GW_485) {
//        GPIO_WriteBit(GPIO_GW_485_RDE, Pin_GW_485_RDE, read);
//    }
//    else if (pUSARTx == BAT_485) {
//        GPIO_WriteBit(GPIO_BAT_485_RDE, Pin_BAT_485_RDE, read);
//    }
//    else {
//        return;
//    }
//}
//
///*
// * @brief 通过485发送一个字符串的指定长度
// * @param pUSARTx 对应的串口设备
// * @param data 字符串
// * @retval
// */
//void USARTx_SendStr_Len(USART_TypeDef* pUSARTx, char *str, int len)
//{
//    if (pUSARTx == GW_485) {
//        GPIO_WriteBit(GPIO_GW_485_RDE, Pin_GW_485_RDE, write);
//    }
//    else if (pUSARTx == BAT_485) {
//        GPIO_WriteBit(GPIO_BAT_485_RDE, Pin_BAT_485_RDE, write);
//    }
//    else {
//        return;
//    }
//
//    uint8_t i = 0;
//    do
//    {
//        USARTx_SendByte_str(pUSARTx, *(str+i));
//       i++;
//    }while(--len);
//    while(USART_GetFlagStatus(pUSARTx, USART_FLAG_TC) == RESET);
//
//    if (pUSARTx == GW_485) {
//        GPIO_WriteBit(GPIO_GW_485_RDE, Pin_GW_485_RDE, read);
//    }
//    else if (pUSARTx == BAT_485) {
//        GPIO_WriteBit(GPIO_BAT_485_RDE, Pin_BAT_485_RDE, read);
//    }
//    else {
//        return;
//    }
//}

void USARTx_ITSendstr(USART_TypeDef* pUSARTx, char *str, int len)
{
    USART_ITConfig(USART3, USART_IT_RXNE, ENABLE);
}

/*
 * @brief USART3的串口中断处理函数
 * @param
 * @retval
 */
void USART3_IRQHandler(void)
{
    if(USART_GetITStatus(USART3, USART_IT_RXNE) != RESET) //中断产生
    {
//        printf(" in usart3 \n");
//        USART_ClearITPendingBit(USART3,USART_IT_RXNE);                //清除中断标志
        USART3_Rbuffer[0] = USART_ReceiveData(USART3); //接收数据
        uint8_t c = 0;
        uart_device_info *dev = (uart_device_info *)g_bat485_uart3_handle;
        c = USART3_Rbuffer[0];
        if(!RingQueueFull(&dev->uart_ring_queue))
           InRingQueue(&dev->uart_ring_queue, c);
    }

//    if(USART_GetFlagStatus(USART3,USART_FLAG_TC) == SET) //中断发送
//    {
//        USART_SendData(USART3, USART3_Tbuffer[USART3_Tbuffer_Num++]);
//        if (USART3_Tbuffer_Len == USART3_Tbuffer_Num) {
//            USART3_Tbuffer_Num = 0;
//            USART_ITConfig(USART3, USART_IT_TC, DISABLE);
////            USART_ClearFlag(USART3,USART_FLAG_ORE);  //清标志
////            USART_ReceiveData(USART3);               //读DR
//        }
//    }
}

/*
 * @brief USART4的串口中断处理函数
 * @param
 * @retval
 */
void USART4_IRQHandler(void)
{
    if(USART_GetITStatus(USART4, USART_IT_RXNE) != RESET) //中断产生
    {
//        printf(" in usart4 \n");
//        USART_ClearITPendingBit(USART4, USART_IT_RXNE);                //清除中断标志
        USART4_Rbuffer[0] = USART_ReceiveData(USART4); //接收数据
        uint8_t c = 0;
        uart_device_info *dev = (uart_device_info *)g_gw485_uart4_handle;
        c = USART4_Rbuffer[0];
        if(!RingQueueFull(&dev->uart_ring_queue))
           InRingQueue(&dev->uart_ring_queue, c);
    }

//    if(USART_GetFlagStatus(USART4,USART_FLAG_TC) == SET) //中断发送
//    {
//        USART_SendData(USART4, USART4_Tbuffer[USART3_Tbuffer_Num++]);
//        if (USART4_Tbuffer_Len == USART4_Tbuffer_Num) {
//            USART4_Tbuffer_Num = 0;
//            USART_ITConfig(USART4, USART_IT_TC, DISABLE);
////            USART_ClearFlag(USART3,USART_FLAG_ORE);  //清标志
////            USART_ReceiveData(USART3);               //读DR
//        }
//    }
}



