/**
  ******************************************************************************
  * @file    spi_drv.h
  * @author  Product application department
  * @version V1.0
  * @date    2020.02.13
  * @brief   Header file of SPI DRV module.
  *
  ******************************************************************************
  */
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __SPI_DRV_H
#define __SPI_DRV_H

#ifdef __cplusplus
extern "C"
{
#endif

/* Includes ------------------------------------------------------------------*/
#include "drv_reg.h"
#include "drv_gpio_def.h"


#ifdef FILE_OUT
/**@defgroup DRV 3 HAL driver
  *
  *@{
  */

/** @defgroup DRV_SPI SPI
  *
  *@{
  */
#endif
/*** 宏定义 *******************************************************************/
#ifdef FILE_OUT
/** @defgroup DRV_SPI_Exported_Macros Exported Macros
  *
  * @{
  */
#endif
/**
  * @brief  SPI 常用宏常量
  *
  */
#define SPI_IT_SPIF                                   (uint8_t)(1)                                /**<  SPI中断索引:SPIF                        */
#define SPI_IT_WCOL                                   (uint8_t)(2)                                /**<  SPI中断索引:冲突                        */
#define SPI_IT_FLOST                                  (uint8_t)(3)                                /**<  SPI中断索引:模式错误                    */

#define SPI_PIN_CS                                    0X03                                        /**<  SPI管脚:SS                              */
#define SPI_PIN_CLK                                   0X02                                        /**<  SPI管脚:CLK                             */
#define SPI_PIN_MOSI                                  0X01                                        /**<  SPI管脚:MOSI                            */
#define SPI_PIN_MISO                                  0X00
#define SPI_FIFO_MAX_SIZE                             0X08

#define	SPI_IT_INDEX_SPIE                             0X80
#define	SPI_IT_INDEX_FLOSTIE                          0X20
#define	SPI_IT_INDEX_MODFIE                           0X10
#define	SPI_IT_INDEX_SSIE                             0X80

#define	SPI_IT_INDEX_RXFTOIE                          0X80
#define	SPI_IT_INDEX_RXFTOE                           0X40

#define	SPI_IT_INDEX_TXFTOIE                          0X80
#define	SPI_IT_INDEX_TXFTOE                           0X40

#define	SPI_IT_INDEX_RXFOVIE                          0X40
#define	SPI_IT_INDEX_RXFUDIE                          0X20
#define	SPI_IT_INDEX_RXFSTHIE                         0X10

#define	SPI_IT_INDEX_TXFOVIE                          0X40
#define	SPI_IT_INDEX_TXFUDIE                          0X20
#define	SPI_IT_INDEX_TXFSTHIE                         0X10

/*SPI 宏函数功能定义*/
/*frame register*/
#define _spi_en_continous_cs(spi)                  _bit_set(spi->FR,SPI_EN_CONT_CS)                          /**< SPI            */
#define _spi_dis_continous_cs(spi)                 _bit_clr(spi->FR,SPI_EN_CONT_CS)                          /**< SPI            */
#define _spi_en_guard_time(spi)                    _bit_set(spi->FR,SPI_EN_GUARD_TIME)                       /**< SPI            */
#define _spi_dis_guard_time(spi)                   _bit_clr(spi->FR,SPI_EN_GUARD_TIME)                       /**< SPI            */
#define _spi_loop_back_mode(spi)                   _bit_set(spi->FR,SPI_LOOP_BACK_MODE)                      /**< SPI            */
#define _spi_loop_normal_mode(spi)                 _bit_clr(spi->FR,SPI_LOOP_BACK_MODE)                      /**< SPI            */
#define _spi_frame_format_ti(spi)                  _bit_set(spi->FR,SPI_FRAME_FORMAT_TI)                     /**< SPI            */
#define _spi_frame_format_freescale(spi)           _bit_clr(spi->FR,SPI_FRAME_FORMAT_TI)                     /**< SPI            */
#define _spi_set_frame_size(spi,size)              _reg_modify(spi->FR,SPI_FRAME_SIZE_MASK,szie)             /**< SPI            */
/*control register 1*/
#define _spi_en_it(spi)                            _bit_set(spi->CR1,SPI_EN_IT)                              /**< SPI 中断使能         */
#define _spi_dis_it(spi)                           _bit_clr(spi->CR1,SPI_EN_IT)
#define _spi_get_it(spi)                           _bit_get(spi->CR1, SPI_EN_IT)
#define _spi_en(spi)                               _bit_set(spi->CR1,SPI_EN)                                 /**< SPI 使能             */
#define _spi_dis(spi)                              _bit_clr(spi->CR1,SPI_EN)                                 /**< SPI 禁止             */
#define _spi_get_en(spi)                           _bit_get(spi->CR1,SPI_EN)                                 /**< SPI 使能             */
#define _spi_out_mode_cmos(spi)                    _bit_set(spi->CR1,SPI_WIRED_OR_MODE_CMOS)                 /**< SPI CMOS/OPEN_DRAIN  */
#define _spi_out_mode_opendrain(spi)               _bit_clr(spi->CR1,SPI_WIRED_OR_MODE_CMOS)                 /**< SPI CMOS/OPEN_DRAIN  */
#define _spi_pin_output_cmos(spi)                  _bit_set(spi->CR1,SPI_WIRED_OR_MODE_CMOS)                 /**< SPI CMOS/OPEN_DRAIN  */
#define _spi_pin_output_opendrain(spi)             _bit_clr(spi->CR1,SPI_WIRED_OR_MODE_CMOS)                 /**< SPI CMOS/OPEN_DRAIN  */
#define _spi_master(spi)                           _bit_set(spi->CR1,SPI_MASTER)                             /**< SPI master           */
#define _spi_slave(spi)                            _bit_clr(spi->CR1,SPI_MASTER)                             /**< SPI slave            */
#define _spi_cpol_idle_high(spi)                   _bit_set(spi->CR1,SPI_CPOL_HIGH)                          /**< SPI master           */
#define _spi_cpol_idle_low(spi)                    _bit_clr(spi->CR1,SPI_CPOL_HIGH)                          /**< SPI master           */
#define _spi_cpha_edge_2(spi)                      _bit_set(spi->CR1,SPI_CPHA_2EDGE)                         /**< SPI master           */
#define _spi_cpha_edge_1(spi)                      _bit_clr(spi->CR1,SPI_CPHA_2EDGE)                         /**< SPI master           */
#define _spi_en_ssoe(spi)                          _bit_set(spi->CR1,SPI_EN_SSOE)                            /**<         */
#define _spi_dis_ssoe(spi)                         _bit_clr(spi->CR1,SPI_EN_SSOE)                            /**< SPI SSOE禁止         */
#define _spi_data_lsb(spi)                         _bit_set(spi->CR1,SPI_FIRSTBIT_LSB)                       /**< SPI master           */
#define _spi_data_msb(spi)                         _bit_clr(spi->CR1,SPI_FIRSTBIT_LSB)                       /**< SPI master           */
/*spi control register2*/
#define _spi_set_guard_time(spi,time)              _reg_modify(spi->CR2,SPI_GUARD_TIME_MASK,time)            /**< SPI master           */
#define _spi_doze_inactive(spi)                    _bit_set(spi->CR2,SPI_DOZE_INACTIVE_MODE)                 /**< SPI master           */
#define _spi_doze_active(spi)                      _bit_clr(spi->CR2,SPI_DOZE_INACTIVE_MODE)                 /**< SPI master           */
#define _spi_spc0_normal_mode(spi)                 _bit_set(spi->CR2,SPI_SPC0_BIDIR_MODE)                    /**< SPI master           */
#define _spi_spc0_bidir_mode(spi)                  _bit_clr(spi->CR2,SPI_SPC0_BIDIR_MODE)                    /**< SPI master           */
/*tx fifo timeout counter register*/
#define _spi_en_tx_fifo_timeout_it(spi)            _bit_set(spi->TXFTOCRT,SPI_EN_TX_FIFO_TINEOUT_IT)         /**<         */
#define _spi_dis_tx_fifo_timeout_it(spi)           _bit_clr(spi->TXFTOCRT,SPI_EN_TX_FIFO_TINEOUT_IT)         /**<         */
#define _spi_dis_tx_fifo_timeout_it(spi)           _bit_clr(spi->TXFTOCRT,SPI_EN_TX_FIFO_TINEOUT_IT)         /**<         */
#define _spi_get_tx_fifo_timeout_it(spi)           _bit_get(spi->TXFTOCRT,SPI_EN_TX_FIFO_TINEOUT_IT)         /**<         */
#define _spi_en_tx_fifo_timeout(spi)               _bit_set(spi->TXFTOCRT,SPI_EN_TX_FIFO_TINEOUT)            /**<         */
#define _spi_dis_tx_fifo_timeout(spi)              _bit_clr(spi->TXFTOCRT,SPI_EN_TX_FIFO_TINEOUT)            /**<         */
#define _spi_set_tx_fifo_time_cnt(spi,cnt)         _reg_modify(spi->TXFTOCTR,SPI_TX_FIFO_TIMEOUT_CNT_MASK,cnt)
/*rx fifo timeout counter register*/
#define _spi_en_rx_fifo_timeout_it(spi)            _bit_set(spi->RXFTOCRT,SPI_EN_RX_FIFO_TINEOUT_IT)         /**<         */
#define _spi_dis_rx_fifo_timeout_it(spi)           _bit_clr(spi->RXFTOCRT,SPI_EN_RX_FIFO_TINEOUT_IT)         /**<         */
#define _spi_get_rx_fifo_timeout_it(spi)           _bit_get(spi->RXFTOCRT,SPI_EN_RX_FIFO_TINEOUT_IT)         /**<         */
#define _spi_en_rx_fifo_timeout(spi)               _bit_set(spi->RXFTOCRT,SPI_EN_RX_FIFO_TINEOUT)            /**<         */
#define _spi_dis_rx_fifo_timeout(spi)              _bit_clr(spi->RXFTOCRT,SPI_EN_RX_FIFO_TINEOUT)            /**<         */
#define _spi_set_rx_fifo_time_cnt(spi,cnt)         _reg_modify(spi->RXFTOCTR,SPI_RX_FIFO_TIMEOUT_CNT_MASK,cnt)
/*spi tx fifo cotrol register*/
#define _spi_clr_tx_fifo(spi)                      _bit_set(spi->TXFCR,SPI_TX_FIFO_CLEAR)                    /**<         */
#define _spi_en_tx_fifo_overflow_it(spi)           _bit_set(spi->TXFCR,SPI_EN_TX_FIFO_OVERFLOW_IT)           /**<         */
#define _spi_get_tx_fifo_overflow_it(spi)          _bit_get(spi->TXFCR,SPI_EN_TX_FIFO_OVERFLOW_IT)           /**<         */
#define _spi_en_tx_fifo_underflow_it(spi)          _bit_set(spi->TXFCR,SPI_EN_TX_FIFO_UNDERFLOW_IT)          /**<         */
#define _spi_dis_tx_fifo_underflow_it(spi)         _bit_clr(spi->TXFCR,SPI_EN_TX_FIFO_UNDERFLOW_IT)          /**<         */
#define _spi_get_tx_fifo_underflow_it(spi)         _bit_get(spi->TXFCR,SPI_EN_TX_FIFO_UNDERFLOW_IT)          /**<         */
#define _spi_en_tx_fifo_service_th_it(spi)         _bit_set(spi->TXFCR,SPI_EN_TX_FIFO_SERVICE_THRESHOLD_IT)  /**<         */
#define _spi_dis_tx_fifo_service_th_it(spi)        _bit_clr(spi->TXFCR,0x10)  /**<         */
#define _spi_get_tx_fifo_service_th_it(spi)        _bit_get(spi->TXFCR,0x10)  /**<         */
#define _spi_set_tx_fifo_threshold(spi,threshold)  _reg_modify(spi->TXFCR,SPI_TX_FIFO_SERVICE_TRHESHOLD_MASK,threshold)
/*spi rx fifo cotrol register*/
#define _spi_clr_rx_fifo(spi)                      _bit_set(spi->RXFCR,SPI_RX_FIFO_CLEAR)                    /**<         */
#define _spi_en_rx_fifo_overflow_it(spi)           _bit_set(spi->RXFCR,SPI_EN_RX_FIFO_OVERFLOW_IT)           /**<         */
#define _spi_dis_rx_fifo_overflow_it(spi)          _bit_clr(spi->RXFCR,SPI_EN_RX_FIFO_OVERFLOW_IT)           /**<         */
#define _spi_get_rx_fifo_overflow_it(spi)          _bit_get(spi->RXFCR,SPI_EN_RX_FIFO_OVERFLOW_IT)           /**<         */
#define _spi_en_rx_fifo_underflow_it(spi)          _bit_set(spi->RXFCR,SPI_EN_RX_FIFO_UNDERFLOW_IT)          /**<         */
#define _spi_dis_rx_fifo_underflow_it(spi)         _bit_clr(spi->RXFCR,SPI_EN_RX_FIFO_UNDERFLOW_IT)          /**<         */
#define _spi_get_rx_fifo_underflow_it(spi)         _bit_get(spi->RXFCR,SPI_EN_RX_FIFO_UNDERFLOW_IT)          /**<         */
#define _spi_en_rx_fifo_service_th_it(spi)         _bit_set(spi->RXFCR,SPI_EN_RX_FIFO_SERVICE_THRESHOLD_IT)  /**<         */
#define _spi_dis_rx_fifo_service_th_it(spi)        _bit_clr(spi->RXFCR,SPI_EN_RX_FIFO_SERVICE_THRESHOLD_IT)  /**<         */
#define _spi_get_rx_fifo_service_th_it(spi)        _bit_get(spi->RXFCR,SPI_EN_RX_FIFO_SERVICE_THRESHOLD_IT)  /**<         */
#define _spi_set_rx_fifo_threshold(spi,threshold)  _reg_modify(spi->RXFCR,SPI_RX_FIFO_SERVICE_TRHESHOLD_MASK,threshold)
/*pullup and reduced driver register*/
#define _spi_en_high_speed(spi)                    _bit_set(spi->PURD,SPI_EN_HIGH_SPEED)                     /**<         */
#define _spi_dis_high_speed(spi)                   _bit_clr(spi->PURD,SPI_EN_HIGH_SPEED)                     /**<         */
#define _spi_en_mosi_miso_switch(spi)              _bit_set(spi->PURD,SPI_EN_MISO_MOSI_SWITCH)               /**<         */
#define _spi_dis_mosi_miso_switch(spi)             _bit_clr(spi->PURD,SPI_EN_MISO_MOSI_SWITCH)               /**<         */
#define _spi_en_tx_data_double_mode(spi)           _bit_set(spi->PURD,SPI_EN_DOUBLE_TX_DATA_MODE)            /**<         */
#define _spi_dis_tx_data_double_mode(spi)          _bit_clr(spi->PURD,SPI_EN_DOUBLE_TX_DATA_MODE)            /**<         */
#define _spi_set_smaple_delay(spi,tt)              _reg_modify(spi->PURD,SPI_MASTER_SAMPLE_POINT_DELAY_MASK,tt)/**<         */
#define _spi_en_pullup(spi)                        _bit_set(spi->PURD,SPI_EN_PULLUP_DEVICE)                  /**<         */
#define _spi_dis_pullup(spi)                       _bit_clr(spi->PURD,SPI_EN_PULLUP_DEVICE)                  /**<         */
#define _spi_en_pulldown(spi)                      _bit_set(spi->PURD,SPI_EN_PULLDOWN_DEVICE)                /**<         */
#define _spi_dis_pulldown(spi)                     _bit_clr(spi->PURD,SPI_EN_PULLDOWN_DEVICE)                /**<         */
/*SPI port data direction register*/
#define _spi_pin_spi(spi,pin)                      _bit_clr(spi->DDR,(1<<(pin+SPI_PPS_SHIFT_MASK)))          /**<              */
#define _spi_pin_gpio(spi,pin)                     _bit_set(spi->DDR,(1<<(pin+SPI_PPS_SHIFT_MASK)))          /**<              */
#define _spi_pin_output(spi,pin)                   _bit_set(spi->DDR,(1<<pin))                               /**< 管脚输出             */
#define _spi_pin_input(spi,pin)                    _bit_clr(spi->DDR,(1<<pin))                               /**< 管脚输入             */
#define _spi_pin_dir_output(spi,pin)               _bit_set(spi->DDR,(1<<pin))                               /**< 管脚输出             */
#define _spi_pin_dir_input(spi,pin)                _bit_clr(spi->DDR,(1<<pin))                               /**< 管脚输入             */
/*spi port data register*/
#define _spi_set_pin_bit(spi,pin)                  _bit_set(spi->PORT,(1<<pin))
#define _spi_reset_pin_bit(spi,pin)                _bit_clr(spi->PORT,(1<<pin))
#define _spi_set_cs_bit(spi)                       _bit_set(spi->PORT,1<<SPI_PIN_CS)                         /**< SPI 置位CS管脚电平   */
#define _spi_reset_cs_bit(spi)                     _bit_clr(spi->PORT,1<<SPI_PIN_CS)                         /**< SPI 复位CS管脚电平   */
#define _spi_set_mosi_bit(spi)                     _bit_set(spi->PORT,1<<SPI_PIN_MOSI)                       /**< SPI 置位MOSI管脚电平 */
#define _spi_reset_mosi_bit(spi)                   _bit_clr(spi->PORT,1<<SPI_PIN_MOSI)                       /**< SPI 复位MOSI管脚电平 */
#define _spi_set_miso_bit(spi)                     _bit_set(spi->PORT,1<<SPI_PIN_MISO)                       /**< SPI 置位MISO管脚电平 */
#define _spi_reset_miso_bit(spi)                   _bit_clr(spi->PORT,1<<SPI_PIN_MISO)                       /**< SPI 复位MISO管脚电平 */
#define _spi_set_clk_bit(spi)                      _bit_set(spi->PORT,1<<SPI_PIN_CLK)                        /**< SPI 置位CLK管脚电平  */
#define _spi_reset_clk_bit(spi)                    _bit_clr(spi->PORT,1<<SPI_PIN_CLK)                        /**< SPI 复位CLK管脚电平  */
#define _spi_get_pin_bit(spi,pin)                  _bit_get(spi->PORT,(1<<pin))
#define _spi_get_cs_bit(spi)                       ((spi->PORT & (1<<SPI_PIN_CS)) ? 1:0)                     /**< SPI 获取管脚CS电平   */
#define _spi_get_mosi_bit(spi)                     ((spi->PORT & (1<<SPI_PIN_MOSI)) ? 1:0)                   /**< SPI 获取MOSI管脚电平 */
#define _spi_get_miso_bit(spi)                     ((spi->PORT & (1<<SPI_PIN_MISO)) ? 1:0)                   /**< SPI 获取MISO管脚电平 */
#define _spi_get_clk_bit(spi)                      ((spi->PORT & (1<<SPI_PIN_CLK)) ? 1:0)                    /**< SPI 获取CLK管脚电平  */
#define _spi_bit_set(spi,pin)                      _bit_set(spi->PORT,(1<<pin))                              /**< SPI 置位管脚电平     */
#define _spi_reset_bit(spi,pin)                    _bit_clr(spi->PORT,(1<<pin))                              /**< SPI 复位管脚电平     */
#define _spi_get_pin_bit(spi,pin)                  _bit_get(spi->PORT,(1<<pin))                              /**< SPI 置位管脚电平     */
#define _spi_toggle_pin(spi,pin)                   spi->PORT ^= (1<<pin)                                     /**< SPI 翻转管脚电平     */
#define _spi_get_port_bits(spi)                    _reg_read(spi->PORT)
/*interrupt register of SS pin*/
#define _spi_en_ss_it(spi)                         _bit_set(spi->IRSP,SPI_EN_SS_IT)                          /**<         */
#define _spi_dis_ss_it(spi)                        _bit_clr(spi->IRSP,SPI_EN_SS_IT)                          /**<         */
#define _spi_get_ss_it(spi)                        _bit_get(spi->IRSP,SPI_EN_SS_IT)                          /**<         */
#define _spi_ss_pin_trigger_level_high(spi)        _bit_set(spi->IRSP,SPI_SS_LEVEL_HIGH)                     /**<         */
#define _spi_ss_pin_trigger_level_low(spi)         _bit_clr(spi->IRSP,SPI_SS_LEVEL_HIGH)                     /**<         */
#define _spi_get_ss_pin_falg(spi)                  _bit_get(spi->IRSP,SPI_SS_PIN_FLAG)
#define _spi_ss_pin_clear_flag(spi)                _bit_set(spi->IRSP,SPI_SS_PIN_FLAG)
#define _spi_get_ss_pin_bit(spi)                   _bit_get(spi->IRSP,SPI_SS_PIN_DATA_BIT)                   /**<         */
#define _spi_set_sspin_assignment(spi,a)           _reg_modify(spi->IRSP,SPI_SS_PIN_ASSIGNMENT_SEL_MASK,a)   /**<         */
/*TX FIFO status register*/
#define _spi_get_tx_fifo_next_pointer(spi)         (spi->TXFSR>>SPI_TX_FIFO_NEXT_POINTER_SHIFT_MASK)         /**<         */
#define _spi_get_tx_fifo_data_counter(spi)         (spi->TXFSR & 0x0f)                                       /**<         */
#define _spi_get_rx_fifo_next_pointer(spi)         (spi->RXFSR>>SPI_RX_FIFO_NEXT_POINTER_SHIFT_MASK)         /**<         */
#define _spi_get_rx_fifo_data_counter(spi)         (spi->RXFSR & 0x0f)                                       /**<         */
/**< SPI 获取标志         */
#define _spi_get_flag_finish(spi)                  _bit_get(spi->SR, SPI_FLAG_FINISH)                        /**< SPI 获取SPIF标志     */
#define _spi_get_flag_frame_lost(spi)              _bit_get(spi->SR, SPI_FLAG_FRAME_LOST)                    /**< SPI 获取WCOL标志     */
#define _spi_get_flag_transmission_end(spi)        _bit_get(spi->SR, SPI_FLAG_TRANSMISSION_END)              /**< SPI 获取MODF标志     */
#define _spi_get_flag_mode_fault(spi)              _bit_get(spi->SR, SPI_FLAG_MODE_FAULT)                    /**< SPI      */
#define _spi_get_flag_tx_fifo_full(spi)            _bit_get(spi->SR, SPI_FLAG_TX_FIFO_FULL)                  /**< SPI      */
#define _spi_get_flag_tx_fifo_empty(spi)           _bit_get(spi->SR, SPI_FLAG_TX_FIFO_EMPTY)                 /**< SPI      */
#define _spi_get_flag_rx_fifo_full(spi)            _bit_get(spi->SR, SPI_FLAG_RX_FIFO_FULL)                  /**< SPI      */
#define _spi_get_flag_rx_fifo_empty(spi)           _bit_get(spi->SR, SPI_FLAG_RX_FIFO_EMPTY)                 /**< SPI      */
#define _spi_get_flag_rx_fifo_service(spi)         _bit_get(spi->SR, SPI_FLAG_RX_FIFO_SERVICE)               /**< SPI      */
#define _spi_get_flag_rx_fifo_underflow(spi)       _bit_get(spi->SR, SPI_FLAG_RX_FIFO_UNDEFLOW)              /**< SPI      */
#define _spi_get_flag_rx_fifo_overflow(spi)        _bit_get(spi->SR, SPI_FLAG_RX_FIFO_OVERFLOW)              /**< SPI      */
#define _spi_get_flag_rx_fifo_timeout(spi)         _bit_get(spi->SR, SPI_FLAG_RX_FIFO_TIMEOUT)               /**< SPI      */
#define _spi_get_flag_tx_fifo_service(spi)         _bit_get(spi->SR, SPI_FLAG_TX_FIFO_SERVICE)               /**< SPI      */
#define _spi_get_flag_tx_fifo_underflow(spi)       _bit_get(spi->SR, SPI_FLAG_TX_FIFO_UNDERFLOW)             /**< SPI      */
#define _spi_get_flag_tx_fifo_overflow(spi)        _bit_get(spi->SR, SPI_FLAG_TX_FIFO_OVERFLOW)              /**< SPI      */
#define _spi_get_flag_tx_fifo_timeout(spi)         _bit_get(spi->SR, SPI_FLAG_TX_FIFO_TIMEOUT)               /**< SPI      */
#define _spi_clr_flag_frame_lost(spi)              _bit_set(spi->SR, SPI_FLAG_FRAME_LOST)                    /**< SPI      */
#define _spi_clr_flag_transmission_end(spi)        _bit_set(spi->SR, SPI_FLAG_TRANSMISSION_END)              /**< SPI      */
#define _spi_clr_flag_rx_fifo_underflow(spi)       _bit_set(spi->SR, SPI_FLAG_RX_FIFO_UNDEFLOW)              /**< SPI      */
#define _spi_clr_flag_rx_fifo_overflow(spi)        _bit_set(spi->SR, SPI_FLAG_RX_FIFO_OVERFLOW)              /**< SPI      */
#define _spi_clr_flag_rx_fifo_timeout(spi)         _bit_set(spi->SR, SPI_FLAG_RX_FIFO_TIMEOUT)               /**< SPI      */
#define _spi_clr_flag_tx_fifo_underflow(spi)       _bit_set(spi->SR, SPI_FLAG_TX_FIFO_UNDERFLOW)             /**< SPI      */
#define _spi_clr_flag_tx_fifo_overflow(spi)        _bit_set(spi->SR, SPI_FLAG_TX_FIFO_OVERFLOW)              /**< SPI      */
#define _spi_clr_flag_tx_fifo_timeout(spi)         _bit_set(spi->SR, SPI_FLAG_TX_FIFO_TIMEOUT)               /**< SPI      */
/*interrupt control register*/
#define _spi_en_mode_fault_it(spi)                 _bit_set(spi->ICR,SPI_EN_MODE_FAULT_IT)                   /**<         */
#define _spi_dis_mode_fault_it(spi)                _bit_clr(spi->ICR,SPI_EN_MODE_FAULT_IT)                   /**<         */
#define _spi_en_frame_lost_it(spi)                 _bit_set(spi->ICR,SPI_EN_FRAME_LOST_IT)                   /**< */
#define _spi_dis_frame_lost_it(spi)                _bit_clr(spi->ICR,SPI_EN_FRAME_LOST_IT)                   /**< */
/*DMA control register*/
#define _spi_en_tx_dma(spi)                        _bit_set(spi->DMACR,SPI_EN_TX_DMA)                        /**<         */
#define _spi_dis_tx_dma(spi)                       _bit_clr(spi->DMACR,SPI_EN_TX_DMA)                        /**<         */
#define _spi_get_tx_dma(spi)                       _bit_get(spi->DMACR,SPI_EN_TX_DMA)                        /**<         */
#define _spi_en_rx_dma(spi)                        _bit_set(spi->DMACR,SPI_EN_RX_DMA)                        /**<         */
#define _spi_dis_rx_dma(spi)                       _bit_clr(spi->DMACR,SPI_EN_RX_DMA)                        /**<         */
#define _spi_get_rx_dma(spi)                       _bit_get(spi->DMACR,SPI_EN_RX_DMA)

/**
  * @}
  */

/*** 结构体、枚举变量定义 *****************************************************/
#ifdef FILE_OUT
/** @defgroup DRV_SPI_Exported_Types Exported Types
  *
  * @{
  */
#endif
/**
  * @brief SPI状态
  */
//typedef enum
//{
//	DRV_SPI_IOCTRL_EN_ETFIE,    /**< 使能:SPI EOTF 中断*/
//	DRV_SPI_IOCTRL_DIS_ETFIE,   /**< 禁止:SPI EOTF 中断*/
//	DRV_SPI_IOCTRL_MODIFY_SPPR, /**< 修改:SPPR[6:4] — SPI 波特率预选择位*/
//	DRV_SPI_IOCTRL_MODIFY_SPR,  /**< 修改:SPR[2:0] — SPI 波特率选择位*/
//	DRV_SPI_IOCTRL_EN_FIRM,     /**< 使能:SPI FIRM 数据发送使能:在从模式下将 FIRM 位使能时， SPI 从 SPICFGDATA 寄存器发送数据， SPIDR 寄
//                                     存器数据无效。*/
//	DRV_SPI_IOCTRL_EN_,     /**< 禁止:SPI FIRM 数据发送:*/
//	DRV_SPI_IOCTRL_DIS,     /**< 禁止: */
//	DRV_SPI_IOCTRL_MODIFY,  /**< 修改:*/
//	DRV_SPI_IOCTRL_SET,     /**< 置位:*/
//    DRV_SPI_IOCTRL_RESET,   /**< 复位:*/
//    DRV_SPI_IOCTRL_CLR,     /**< 清除:*/
//    DRV_SPI_IOCTRL_GET,     /**< 获取:*/
//	DRV_SPI_IOCTRL_EN_,     /**< 使能:*/
//	DRV_SPI_IOCTRL_DIS, 	/**< 禁止: */
//	DRV_SPI_IOCTRL_MODIFY,	/**< 修改:*/
//	DRV_SPI_IOCTRL_SET, 	/**< 置位:*/
//	DRV_SPI_IOCTRL_RESET,	/**< 复位:*/
//	DRV_SPI_IOCTRL_CLR, 	/**< 清除:*/
//	DRV_SPI_IOCTRL_GET, 	/**< 获取:*/
//}DRV_SPI_StatusTypeDef;

/**
  * @brief SPI状态
  */
typedef enum
{
  DRV_SPI_OK       = 0x00,
  DRV_SPI_ERROR    = 0x01,
  DRV_SPI_BUSY     = 0x02,
  DRV_SPI_TIMEOUT  = 0x03,
}DRV_SPI_StatusTypeDef;
/**
  *@brief 标志索引.
  */
typedef enum
{
	SPI_FLAG_INDEX_RXFEMP,
	SPI_FLAG_INDEX_RXFFULL,
	SPI_FLAG_INDEX_XFEMP,
	SPI_FLAG_INDEX_TXFFFUL,
	SPI_FLAG_INDEX_MODE,
	SPI_FLAG_INDEX_EOTF,
	SPI_FLAG_INDEX_FLOST,
	SPI_FLAG_INDEX_SPIF,

	SPI_FLAG_INDEX_RXFSER,
	SPI_FLAG_INDEX_RXFUDF,
	SPI_FLAG_INDEX_RXFOVFM,
	SPI_FLAG_INDEX_RXFTO,
	SPI_FLAG_INDEX_TXFSER,
	SPI_FLAG_INDEX_TXFUDF,
	SPI_FLAG_INDEX_TXFOVFM,
	SPI_FLAG_INDEX_TXFTO,
}SPI_FlagIndexTypeDef;
/**
  *@brief SS中断触发方式.
  *
  */
typedef enum
{
    SPI_SS_ASSIGNMENT_SEL_LEVEL = 0,
    SPI_SS_ASSIGNMENT_SEL_RISING_EDGE,
    SPI_SS_ASSIGNMENT_SEL_FALLING_EDGE,
    SPI_SS_ASSIGNMENT_SEL_BOTH_EDGE,
}SPI_SSAssignmentSelTypeDef;

/**
  *@brief SPIFIFO控制.
  *
  */
typedef struct _SPI_FifoInitTypeDef
{
    uint8_t tx_fifo_en;
    uint8_t rx_fifo_en;
    uint8_t tx_fifo_threshold;
    uint8_t rx_fifo_threshold;
    uint8_t tx_fifo_timeout_cnt;
    uint8_t rx_fifo_timeout_cnt;
} SPI_FifoInitTypeDef;

/**
  *@brief spi初始化结构体定义.
  *
  */
typedef struct
{
	uint8_t Function;                  /**<SPI功能用于SPI主功能还是作为GPIO使能
	                                         *- MAIN_FUN
	                                         *- GPIO
	                                         */
	uint8_t OutputMode;               /**<输出模式开漏输出还是CMOS输出
                                         *- GPIO_OUTPUT_MODE_CMOS
                                         *- GPIO_OUTPUT_MODE_OPEN_DRAIN
										 */
    uint8_t Mode;                      /**<输出模式开漏输出还是CMOS输出
                                         *- SPI_MASTER
                                         *- SPI_SLAVE
										 */
    uint8_t Cpol;                      /**<空闲时电平
                                         *- SPI_CPOL_LOW
									     *- SPI_CPOL_HIGH
                                         */
    uint8_t Cpha;                      /**< 相位选择
	                                     *- SPI_CPHA_1EDGE
										 *- SPI_CPHA_2EDGE
                                        */
    uint8_t Ssoe;                      /**< SS功能设置
	                                     *- SPI_SSOE
	                                     *- SPI_SSOE_DIS
	                                     */
    uint8_t FirstBit;                  /**< 数据传输格式
	                                     *- SPI_FIRSTBIT_MSB
	                                     *- SPI_FIRSTBIT_LSB
	                                     */
    uint8_t GuardTime;                /**< 两个字节之间时间间隔*/
    uint8_t Spc0;	                    /**< 双向管脚控制
	                                     *- ENABLE
	                                     *- DISABLE
	                                     */
    uint8_t DozeMode;                 /**< SPI模块在DOZE模式工作情况:停止还是正常工作
    	                                     *- ENABLE
    	                                     *- DISABLE
    	                                     */
    uint8_t BaudratePreselectionBits;/**<波特率预分频数值*/
    uint8_t BaudrateBits;             /**<波特率位*/
    uint8_t GuradTimeEn ;              /**< 字节之间保护时间使能
                                         *- ENABLE
                                         *- DISABLE
                                         */
    uint8_t SlaveHighSpeedEn;          /**< 从模式时高速模式使能或禁止
	                                     *- ENABLE
	                                     *- DISABLE
	                                     */
	uint8_t ReducedDriveCap;         /**< 当前不可用
										 *- ENABLE
										 *- DISABLE
										 */
	uint8_t Pullup;                    /**<SPI 上拉使能或禁止
										 *- ENABLE
										 *- DISABLE
										 */
    SPI_FifoInitTypeDef FifoInit;     /**<SPI fifo控制部分*/
} SPI_InitTypeDef;

/**
  * @}
  */

/*** 全局变量声明 **************************************************************/
#ifdef FILE_OUT
/** @defgroup DRV_SPI_Exported_Variables Exported Variables
  *
  * @{
  */
#endif


/**
  * @}
  */

/*** 函数声明 ******************************************************************/
#ifdef FILE_OUT
/** @defgroup DRV_SPI_Exported_Functions Exported Functions
  * @{
  */
#endif
void DRV_SPI_DeInit(SPI_TypeDef *pspi);
DRV_SPI_StatusTypeDef DRV_SPI_Init(SPI_TypeDef *pspi, SPI_InitTypeDef *Init);
void DRV_SPI_En(SPI_TypeDef *pspi);
void DRV_SPI_Dis(SPI_TypeDef *pspi);
void DRV_SPI_Cmd(SPI_TypeDef *pspi, FunctionalStateTypeDef NewState);
void DRV_SPI_ItEn(SPI_TypeDef *pspi);
DRV_SPI_StatusTypeDef DRV_SPI_TransmitByte(SPI_TypeDef *pspi, uint8_t ToSend);
DRV_SPI_StatusTypeDef DRV_SPI_ReceiveByte(SPI_TypeDef *pspi, uint8_t *Rx);
DRV_SPI_StatusTypeDef DRV_SPI_TransmitBytes(SPI_TypeDef *pspi,
                                            uint8_t *pBuf,
                                            uint32_t Size);
DRV_SPI_StatusTypeDef DRV_SPI_ReceiveBytes(SPI_TypeDef *pspi, uint8_t *pBuf, uint32_t len);
DRV_SPI_StatusTypeDef DRV_SPI_SlaveReceiveByte(SPI_TypeDef *pspi,
                                               uint8_t *Rx,
                                               uint32_t Timeout);
DRV_SPI_StatusTypeDef DRV_SPI_SlaveTransmitByte(SPI_TypeDef *pspi, uint8_t ToSend, uint32_t Timeout);
DRV_SPI_StatusTypeDef DRV_SPI_SlaveTransmitBytes(SPI_TypeDef *pspi, uint8_t *pBuf, uint32_t len, uint32_t Timeout);
DRV_SPI_StatusTypeDef DRV_SPI_SlaveReceiveBytes(SPI_TypeDef *pspi,
                                                uint8_t *pBuf,
                                                uint32_t len,
                                                uint32_t Timeout);
void DRV_SPI_SetDR(SPI_TypeDef *pspi, uint8_t val);
void DRV_SPI_GetDR(SPI_TypeDef *pspi, uint8_t *pval);
DRV_SPI_StatusTypeDef DRV_SPI_GetFlag(SPI_TypeDef *pspi,SPI_FlagIndexTypeDef FlagIndex,uint8_t*pflag);
DRV_SPI_StatusTypeDef DRV_SPI_ClrFlag(SPI_TypeDef *pspi,SPI_FlagIndexTypeDef FlagIndex);
DRV_SPI_StatusTypeDef  DRV_SPI_WaitonFlagTimeout(SPI_TypeDef *pspi,
                                            SPI_FlagIndexTypeDef index,
                                            FlagStatusTypeDef status,
                                            uint32_t timeout);
DRV_SPI_StatusTypeDef DRV_SPI_GPIOInit(SPI_TypeDef *pspi, GPIO_InitTypeDef *Init);
void DRV_SPI_GPIODeInit(SPI_TypeDef *pspi, uint8_t pin);
void DRV_SPI_WritePin(SPI_TypeDef *pspi, uint8_t pin, GPIO_PinStateTypeDef state);
BitActionTypeDef DRV_SPI_ReadPin(SPI_TypeDef *pspi, uint8_t pin);
void DRV_SPI_TogglePin(SPI_TypeDef *pspi, uint8_t pin);

/**
  * @}
  */

/**
  *@}
  */

/**
  *@}
  */

#ifdef __cplusplus
}

#endif

#endif /* __SPI_DRV_H */
