/************************************************************************************
 * @Copyright (c)    :(C)2021, Qindao ieslab Co., Ltd
 * @FileName   	     :hdsc_nb_uart_driver.c
 * @Author           :QDIES PLATFORM TEAM
 * @Version          :V1.1
 * @Date             :2021-07
 * @Description      :
 ************************************************************************************/
#include "sys_config.h"
#ifdef MODULE_BLE_USED

#ifdef	__cplusplus
extern "C"
{
#endif

#include "UWater_uart_driver.h"
#include "ble14531_uart_driver.h"
#include "ble14531_driver.h"
#include "UWater_rtcc_driver.h"
#include "sys_processor.h"
#include "UWater_DebugPrint.h"

///********************************变量定义************************************/
BLE_UART_COMM BLE_Uart_Comm;
u8 g_s_ble_rev_state;		//接收状态机的状态变量
u8 g_s_ble_revc_frame_state = BLE_S0;

volatile u8 v_g_ble_rcv_data = 0;
u8 s_ble_buf[BLE_AT_RCV_BUF_SIZE] = {0};
#if BLE_CENTRAL_SLAVE_MOD
BLE_SLAVE_INFO a_ble_scan_buf[BLE_AT_SCAN_MAC_TOTAL];
u8 g_ble_sacn_complete = FALSE;
u8 g_ble_temp_array[22];
u8 g_ble_check_index;
u8 g_ble_macindex;
u8 g_ble_scanindex;
#endif
u8 g_ble_rcvindex;
mtype16_ g_ble_uart_temp;
u8 g_ble_reset_flag = FALSE;
u8 s_g_buf[1];
///*****************************内部功能状态机***********************************/
void BLE_AT_OK_AND_ERROR_MACHINE(u8 data);
void BLE_AT_AT_MACHINE(u8 data);
void BLE_AT_QUERY_MACHINE(u8 data);
void BLE_AT_SCAN_MACHINE(u8 data);
void BLE_AT_BLE_RCV_FRAME_MACHINE(u8 data);

/***************************************************************************
 * @fun_name     static void UART_Receive_IT(Nbiot_UART_HandleTypeDef *huart)
 * @brief        串口接收中断处理程序
 * @param[in]    None
 * @param[out]   None
 * @retval       None
 * @other        None
 ***************************************************************************/
void BleUartReceiveIT(void)
{
#if(BLE_LP_COM)
	v_g_ble_rcv_data = LPUart_ReceiveData(BLE_UART_REALCOM);
#else
	v_g_ble_rcv_data = Uart_ReceiveData(BLE_UART_COM);
#endif

	switch (BLE_Uart_Comm.send_style)
	{
		case BLE_cst_AT_NOMAL_RCV:
		{
			break;
		}

		case BLE_cst_AT_OK_ERROR:
		{
			BLE_AT_OK_AND_ERROR_MACHINE(v_g_ble_rcv_data); 	//驱动状态机向前一步
			break;
		}

		case BLE_cst_AT_AT:
		{
			BLE_AT_AT_MACHINE(v_g_ble_rcv_data); 		//驱动状态机向前一步
			break;
		}

		case BLE_cst_AT_QUERY:
		{
			BLE_AT_QUERY_MACHINE(v_g_ble_rcv_data); 	//驱动状态机向前一步
			break;
		}
#if BLE_CENTRAL_SLAVE_MOD
		case BLE_cst_AT_SCAN_RCV:						//接收广播数据
		{
			BLE_AT_SCAN_MACHINE(v_g_ble_rcv_data);
		}
		break;
#endif			
		default:
		break;
	}
	BLE_AT_BLE_RCV_FRAME_MACHINE(v_g_ble_rcv_data);		//接收BLE透传数据
	s_g_buf[0] = v_g_ble_rcv_data;
    PrintNbData(s_g_buf,1);//打印源码
}


/***************************************************************************
 * @fun_name     void BleUartSend(u8 *buf, u16 len, u8 style)
 * @brief        发送数据
 * @param[in] 	 buf：发送数据的地址  len：发送长度
                  style：发送方式（其他：AT指令、短信、ble数据）
 * @param[out] 	 None
 * @retval     	 None
 * @other        None
 ***************************************************************************/
void BleUartSend(u8 *buf, u16 len, u8 style)
{
    static u8 send_msg_ble;
    if (len > 0)
    {
        UartSend(BLE_UART_COM, len, buf, &send_msg_ble);
        //状态初始化
        g_s_ble_rev_state = BLE_S0;
        BLE_Uart_Comm.rev_ack_flag = BLE_UART_ING;
        BLE_Uart_Comm.send_style = style;
    }
}

void BleUartChangeStyle(u8 style)
{
	g_s_ble_rev_state = BLE_S0;
	BLE_Uart_Comm.rev_ack_flag = BLE_UART_ING;
	BLE_Uart_Comm.send_style = style;
}

/***************************************************************************
* @fun_name		u8 BleUartChkStyle(void)
* @brief		查询BLE串口接收模式
* @param[in]	None
* @param[out]	None
* @retval		接收模式，对应相应的指令
* @other		None
***************************************************************************/
u8 BleUartChkStyle(void)
{
	return BLE_Uart_Comm.send_style;
}

/***************************************************************************
* @fun_name		s8 BleCheckAtAck()
* @brief		查询串口返回数据是否正确
* @param[in]	None
* @param[out]	None
* @retval		BLE_UART_ING:接收中 BLE_UART_OK：正确帧 BLE_UART_ERROR：错误帧
* @other		None
***************************************************************************/
s8 BleCheckAtAck(void)
{
    return BLE_Uart_Comm.rev_ack_flag;
}

/***************************************************************************
* @fun_name		u8 BleRcvAtData(u8 **p_data)
* @brief		查询串口返回数据是否正确
* @param[in]	None
* @param[out]	None
* @retval		BLE_UART_ING:接收中 BLE_UART_OK：正确帧 BLE_UART_ERROR：错误帧
* @other		None
***************************************************************************/
u8 BleRcvAtData(u8 **p_data)
{
	*p_data = s_ble_buf;
    return g_ble_rcvindex;
}

/***************************************************************************
* @fun_name		void BLE_AT_OK_AND_ERROR_MACHINE(u8 data)
* @brief		模块返回正确错误状态机
* @param[in]	None
* @param[out]	None
* @retval		None
* @other		None
***************************************************************************/
void BLE_AT_OK_AND_ERROR_MACHINE(u8 data)
{
    switch (g_s_ble_rev_state)
    {
        case BLE_S0:
        {
            if(data == 'O')
            {
                g_s_ble_rev_state = BLE_S1;
            }            
        }
		break;

        case BLE_S1:
        {
            if(data == 'K')
            {
				g_s_ble_rev_state = BLE_S2;
            }
            else if(data == 'R')
            {
                BLE_Uart_Comm.rev_ack_flag = BLE_UART_ERROR;
				g_s_ble_rev_state = BLE_S0;
            }
			else
			{
				g_s_ble_rev_state = BLE_S0;
			}
        }
		break;
		
		case BLE_S2:
		{
			if(data == '+')
			{
				g_s_ble_rev_state = BLE_S3;
			}
			else if(data == '\n' || data == '\r')
			{
				BLE_Uart_Comm.rev_ack_flag = BLE_UART_OK;
				g_s_ble_rev_state = BLE_S0;
			}
			else
			{
				g_s_ble_rev_state = BLE_S0;
			}
		}
		break;
		
		case BLE_S3:
		{
			if(data == '=')
			{
				g_s_ble_rev_state = BLE_S4;
			}
			else if(data == '\n' || data == '\r')
			{
				BLE_Uart_Comm.rev_ack_flag = BLE_UART_OK;
				g_s_ble_rev_state = BLE_S0;
			}
		}
		break;
		
		case BLE_S4:
		{
			if(data == 'O')
			{
				g_s_ble_rev_state = BLE_S5;
			}
		}
		break;
		
		case BLE_S5:
		{
			if(data == 'K')
            {
				BLE_Uart_Comm.rev_ack_flag = BLE_UART_OK;
            }
            else if(data == 'R')
            {
                BLE_Uart_Comm.rev_ack_flag = BLE_UART_ERROR;
            }
			g_s_ble_rev_state = BLE_S0;
		}
		break;

        default:
			g_s_ble_rev_state = BLE_S0;
		break;
    }
}

/***************************************************************************
* @fun_name		void BLE_AT_AT_MACHINE(u8 data)
* @brief		检查串口和模块，AT指令
* @param[in]	None
* @param[out]	None
* @retval		None
* @other		None
***************************************************************************/
void BLE_AT_AT_MACHINE(u8 data)
{
    switch (g_s_ble_rev_state)
    {
        case BLE_S0:
        {
            if (data == 'A')
            {
                g_s_ble_rev_state = BLE_S1;
            }
        }
        break;

        case BLE_S1:
        {
			g_s_ble_rev_state = (data == 'T' ? BLE_S2 : BLE_S0);
        }
        break;

        case BLE_S2:
        {
			BLE_Uart_Comm.rev_ack_flag = (data == '\n' ? BLE_UART_OK : BLE_UART_ERROR);
			g_s_ble_rev_state = BLE_S0;
        }
        break;

        default:
        {
            g_s_ble_rev_state = BLE_S0;
        }
        break;
    }
}

/***************************************************************************
* @fun_name		void BLE_AT_QUERY_MACHINE(u8 data)
* @brief		查询模块设置状态机
* @param[in]	None
* @param[out]	None
* @retval		None
* @other		None
***************************************************************************/
void BLE_AT_QUERY_MACHINE(u8 data)
{
    switch (g_s_ble_rev_state)
    {
        case BLE_S0:
        {
            if(data == 'O')
            {
                g_s_ble_rev_state = BLE_S1;
            }            
        }
		break;

        case BLE_S1:
        {
			g_s_ble_rev_state = data == 'K' ? BLE_S2 : BLE_S0;
        }
		break;
		
		case BLE_S2:
        {
			g_s_ble_rev_state = data == '+' ? BLE_S3 : BLE_S0;
        }
		break;
		
		case BLE_S3:
        {
			if(data == '=')
			{
				memset(s_ble_buf, 0, sizeof(s_ble_buf));
				g_ble_rcvindex = 0;
				g_s_ble_rev_state = BLE_S4;
			}
        }
		break;
		
		case BLE_S4:
        {
			if(data == '\n')
			{
				BLE_Uart_Comm.rev_ack_flag = BLE_UART_OK;
				g_s_ble_rev_state = BLE_S0;
			}
			else
			{
				if(g_ble_rcvindex < BLE_AT_RCV_BUF_SIZE)
				{
					s_ble_buf[g_ble_rcvindex++] = data;
				}
				else
				{
					BLE_Uart_Comm.rev_ack_flag = BLE_UART_OK;
					g_s_ble_rev_state = BLE_S0;
				}
			}
        }
		break;

        default:
			g_s_ble_rev_state = BLE_S0;
		break;
    }
}

#if BLE_CENTRAL_SLAVE_MOD
/***************************************************************************
* @fun_name		void BLE_AT_SCAN_MACHINE(u8 data)
* @brief		模块扫描状态机
* @param[in]	None
* @param[out]	None
* @retval		None
* @other		None
***************************************************************************/
const u8 scAT_SCAN_END[] = "SCAN COMPLETE";
#define AT_CHECK_LEN_SCAN_END		(sizeof(scAT_SCAN_END) - 1)
void BLE_AT_SCAN_MACHINE(u8 data)
{
	switch(g_s_ble_rev_state)
	{
		case BLE_S0:
		{
			if(data == scAT_SCAN_END[g_ble_check_index])
			{
				if(++g_ble_check_index >= AT_CHECK_LEN_SCAN_END)	//判断扫描结束关键字
				{
					g_ble_check_index = 0;
					g_ble_sacn_complete = TRUE;						//扫描结束
					BLE_Uart_Comm.rev_ack_flag = BLE_UART_OK;
				}
			}
			else
			{
				g_ble_check_index = 0;
			}
			if((data == 'M') && (0 == g_ble_check_index))
			{
				g_s_ble_rev_state = BLE_S1;
			}
			break;
		}
		case BLE_S1:
		{
			if(g_ble_scanindex >= BLE_AT_SCAN_MAC_TOTAL)
			{
				g_ble_scanindex = 0;
			}
			g_ble_macindex = 0;
			g_s_ble_rev_state = (data == 'A' ? BLE_S2 : BLE_S0);
			break;
		}
		
		case BLE_S2:
		{
			if(':' == data)
			{
				g_s_ble_rev_state = BLE_S3;
			}
		}
		break;
		
		case BLE_S3:		//获取MAC地址
		{
			g_ble_temp_array[g_ble_macindex++] = data;
			if(g_ble_macindex >= 12)
			{
				g_ble_macindex = 0;				
				format_ascii2hex(a_ble_scan_buf[g_ble_scanindex].mac,g_ble_temp_array,12);	//转换为6字节
				//可在此处根据档案配置的MAC信息进行过滤
				
				g_s_ble_rev_state = BLE_S4;
			}
			break;
		}
		case BLE_S4:
		{
			g_s_ble_rev_state = (data == ',' ? BLE_S5 : BLE_S0);	
		}
		break;
		
		case BLE_S5:
		{
			g_s_ble_rev_state = (data == 'R' ? BLE_S6 : BLE_S0);
		}
		break;
		
		case BLE_S6:
		{
			g_ble_uart_temp.to_uint16 = 0;
			g_s_ble_rev_state = (data == ':' ? BLE_S7 : BLE_S6);
		}
		break;
		
		case BLE_S7:		//获取RSSI
		{
			if((',' == data) || (0x0A == data) || (0x0D == data))	//回车或换行或","
			{
				g_ble_uart_temp.to_uint16 = (~g_ble_uart_temp.to_uint16) + 1;
				a_ble_scan_buf[g_ble_scanindex].rssi.to_uint16 = g_ble_uart_temp.to_uint16;
				g_s_ble_rev_state = BLE_S8;
			}
			else
			{
				if(data >= 0x30 && data <= 0x39)
				{
					g_ble_uart_temp.to_uint16 = g_ble_uart_temp.to_uint16 * 10;
					g_ble_uart_temp.to_uint16 += (data - 0x30);
				}
				if(g_ble_uart_temp.to_uint16 > 0xFF)	//厂家回复RSSI的范围：0~-255
				{
					g_ble_uart_temp.to_uint16 = g_ble_uart_temp.to_uint16 % 0xFF;
					g_s_ble_rev_state = BLE_S8;
				}
			}
		}
		break;
		
		case BLE_S8:
		{
			g_s_ble_rev_state = (data == 'S' ? BLE_S9 : BLE_S0);		//没有广播数据时，返回重新接收
		}
		break;
		
		case BLE_S9:
		{
			g_ble_macindex = 0;
			g_s_ble_rev_state = (data == ':' ? BLE_S10 : BLE_S9);
		}
		break;
		
		case BLE_S10:		//获取广播数据
		{
			if(g_ble_macindex >= 11)
		   {
				g_ble_macindex = 0;
				g_ble_scanindex++;
				g_s_ble_rev_state = BLE_S0;
		   }
		   else
		   {
				a_ble_scan_buf[g_ble_scanindex].adv_data[g_ble_macindex++] = data;
		   }
		}
		break;

		default:
			g_s_ble_rev_state = BLE_S0;
		break;
	}
}
#endif
///***************************************************************************
//* @fun_name		void BLE_AT_BLE_RCV_FRAME_MACHINE(u8 data)
//* @brief		模块接收透传数据
//* @param[in]	None
//* @param[out]	None
//* @retval		None
//* @other		None
//***************************************************************************/
void BLE_AT_BLE_RCV_FRAME_MACHINE(u8 data)
{
	switch(g_s_ble_revc_frame_state)
	{
		case BLE_S0:
		{
			if(0xFE == data || (0x68 == data))
			{
				BLE_Uart_Comm.ble_rcv_flag = 1;
				BLE_Uart_Comm.ble_rcv_len = 0;
				BLE_Uart_Comm.ble_rev_buf[BLE_Uart_Comm.ble_rcv_len++] = data;
				g_s_ble_revc_frame_state = BLE_S1;
			}
			else 
			{
				switch(data)
				{
					case 'R':
					{
						g_s_ble_revc_frame_state = BLE_S2;
						break;
					}
					case 'E':
					{
						g_s_ble_revc_frame_state = BLE_S3;
						break;
					}
				}
			}
		}
		break;
		
		case BLE_S1:
		{
			if(BLE_Uart_Comm.ble_rcv_len < BLE_UP_BUF_SIZE)
			{
				BLE_Uart_Comm.ble_rcv_flag = 1;
				BLE_Uart_Comm.ble_rev_buf[BLE_Uart_Comm.ble_rcv_len++] = data;
			}
			else
			{
				BLE_Uart_Comm.ble_rcv_len = 0;
				g_s_ble_revc_frame_state = BLE_S0;
			}
		}
		break;
		
		//接收BLERESET，至少需接收到ESET四个字符
		case BLE_S2:	
		{
			g_s_ble_revc_frame_state = (data == 'E' ? BLE_S3 : BLE_S0);
		}
		break;
		
		case BLE_S3:	
		{
			g_s_ble_revc_frame_state = (data == 'S' ? BLE_S4 : BLE_S0);
		}
		break;
		
		case BLE_S4:	
		{
			g_s_ble_revc_frame_state = (data == 'E' ? BLE_S5 : BLE_S0);
		}
		break;
		
		case BLE_S5:	
		{
			g_s_ble_revc_frame_state = (data == 'T' ? BLE_S6 : BLE_S0);
		}
		break;
		
		case BLE_S6:
		{
			if('\n' == data)	
			{
				g_ble_reset_flag = TRUE;
			}
			g_s_ble_revc_frame_state = BLE_S0;
		}
		break;
	}
}


#if BLE_CENTRAL_SLAVE_MOD
/***************************************************************************
* @fun_name		void BleClrMacBuf(void)
* @brief		清除扫描数据存放缓冲区
* @param[in]	None
* @param[out]	None
* @retval		None
* @other		None
***************************************************************************/
void BleClrMacBuf(void)
{
	memset(a_ble_scan_buf, 0, sizeof(a_ble_scan_buf));
	g_ble_scanindex = 0;
}

/***************************************************************************
* @fun_name		u8 BleGetScanDevInfo(BLE_SLAVE_INFO (*p_data)[])
* @brief		获取扫描到的设备信息
* @param[in]	None
* @param[out]	扫描到的设备MAC和信号信息
* @retval		设备数量，最大20个，在头文件中定义
* @other		None
***************************************************************************/
u8 BleGetScanDevInfo(BLE_SLAVE_INFO **p_data)
{
	*p_data = a_ble_scan_buf;
    return g_ble_scanindex;
}
/***************************************************************************
* @fun_name		u8 BleGetScanCompleteFlag(void)
* @brief		获取扫描完成标志
* @param[in]	None
* @param[out]	None
* @retval		扫描完成标志，TRUE完成，FALSE未完成
* @other		None
***************************************************************************/
u8 BleGetScanCompleteFlag(void)
{
	return g_ble_sacn_complete;
}
/***************************************************************************
* @fun_name		void BleClrScanCompleteFlag(void)
* @brief		清扫描完成标志及扫描数据存放缓冲区的index
* @param[in]	None
* @param[out]	None
* @retval		NONE
* @other		None
***************************************************************************/
void BleClrScanCompleteFlag(void)
{
	g_ble_sacn_complete = FALSE;
	g_ble_scanindex = 0;			//将缓冲区的index同时清零
}
#endif

/***************************************************************************
* @fun_name		u8 BleRcvFrameDataFlag(void)
* @brief		蓝牙收到有效规约数据的消息
* @param[in]	None
* @param[out]	None
* @retval		NONE
* @other		None
***************************************************************************/
u8 BleRcvFrameDataFlag(void)
{
	return BLE_Uart_Comm.ble_rcv_flag;
}

/***************************************************************************
* @fun_name		void BleClrRcvFrameDataFlag(void)
* @brief		清蓝牙收到有效规约数据的消息
* @param[in]	None
* @param[out]	None
* @retval		NONE
* @other		None
***************************************************************************/
void BleClrRcvFrameDataFlag(void)
{
	BLE_Uart_Comm.ble_rcv_flag = 0;
}

/******************************************************************************************
 * @fun_name    void BleGetUartRcvData(u8 **rev_data,u16 *data_len)
 * @brief       获取BLE串口接收到数据内容
 * @param[out] 	rev_data: 数据缓冲区
                data_len：数据长度
 *****************************************************************************************/
void BleGetUartRcvData(u8 **rev_data,u16 *data_len)
{
    *rev_data = BLE_Uart_Comm.ble_rev_buf;
    *data_len = BLE_Uart_Comm.ble_rcv_len;
	
	BLE_Uart_Comm.ble_rcv_len = 0;
	g_s_ble_revc_frame_state = BLE_S0;
}

//查询BLE是否发生了复位
u8 BleCheckIfResetFlag(void)
{
	return g_ble_reset_flag;
}
//清BLE发生复位标志
void BleClrIfResetFlag(void)
{
	g_ble_reset_flag = FALSE;
}
#endif
