/**
 *file    sys_gpio.c
 *brief   
 * 
 *par     Copyright (c) 2018 UWE Technologies Corp., Ltd. All Rights Reserved.
 *author  James
 *date    2018-03-20
 *version 
 * 
 *history 
 *  Date        Note
 *  2018-03-20  Original Creation
 * 
 */

#include "drivers.h"
#include "libc.h"
#include "sys_gpio.h"
#include "sys_pd_hook.h"
#include "sys_config.h"

/** GPIO definitions for function 
 *  引脚  名称              描述                                      有效电平
 *  GPIO0   CAP0            输入，无线充协议信号
 *  GPIO1   MOD             输入，无线充模式信号
 *  GPIO2   NA
 *  GPIO3   PWM0            PWM输出，无线充用    
 *  GPIO4   PWM1            PWM输出，无线充用
 *  GPIO5   CHARGE_LED      输出，充电指示LED                         0
 *  GPIO6   COMPLETE_LED    输出，连接完成LED                         0
 *  GPIO7   DM0             QC，FCP等功能管脚DM/UART0_TX   
 *  GPIO8   DP0             QC，FCP等功能管脚DP/UART0_RX   
 *  GPIO9   I2C0_SCL        连接到TP3
 *  GPIO10  I2C0_SDA        连接到TP4 
 *  GPIO12  UART1_RXD       UART1作为调试口，RXD
 *  GPIO13  UART1_TXD       UART1作为调试口，TXD
 *  GPIO14  NA
 *  GPIO15  NA
 *  GPIO16  VBUS_AD         输入/输出?
 *  GPIO17  I_DC            输出
 *  GPIO18  Protect         输出
 *  GPIO19  NA
 *  GPIO20  DP_control      输出
 *  GPIO21  DM_control2     输出
 *  GPIO22  DM_control      输出
 *  GPIO28  VBUS_EN         输出
 *  GPIO30  NA
 * 
 *  CSN/CSP                 电流检测    
 */

void sys_gpio_init()
{
    // IO init
    drv_gpio_oe_set(0,0);
    drv_gpio_en_set(0,1);

    drv_gpio_oe_set(1,0);
    drv_gpio_en_set(1,1);

    drv_gpio_oe_set(2,0);
    drv_gpio_en_set(2,1);

    drv_gpio_oe_set(3,0);
    drv_gpio_en_set(3,1);

    drv_gpio_oe_set(4,0);
    drv_gpio_en_set(4,1);

    drv_gpio_oe_set(5,0);
    drv_gpio_en_set(5,1);

    drv_gpio_oe_set(6,0);
    drv_gpio_en_set(6,1);

    // No need to configure UART0, TXD/RXD, GPIO7/8

    // No need to configure I2C, GPIO9/10

    drv_gpio_oe_set(12,0);
    drv_gpio_en_set(12,1);

    drv_gpio_oe_set(13,0);
    drv_gpio_en_set(13,1);

    drv_gpio_oe_set(14,0);
    drv_gpio_en_set(14,1);

    drv_gpio_oe_set(15,0);
    drv_gpio_en_set(15,1);

    drv_gpio_oe_set(16,0);
    drv_gpio_en_set(16,1);

    drv_gpio_oe_set(17,0);
    drv_gpio_en_set(17,1);

    drv_gpio_oe_set(18,0);
    drv_gpio_en_set(18,1);

    drv_gpio_oe_set(19,0);
    drv_gpio_en_set(19,1);

    drv_gpio_oe_set(20,0);
    drv_gpio_en_set(20,1);

    drv_gpio_oe_set(21,0);
    drv_gpio_en_set(21,1);

    drv_gpio_oe_set(22,0);
    drv_gpio_en_set(22,1);

    drv_gpio_oe_set(28,0);
    drv_gpio_en_set(28,1);

    drv_gpio_oe_set(30,0);
    drv_gpio_en_set(30,1);

    /* NO-PIN IOs, configure as GPIO input */
    drv_gpio_oe_set(11,0);
    drv_gpio_en_set(11,1);

    drv_gpio_oe_set(23,0);
    drv_gpio_en_set(23,1);

    drv_gpio_oe_set(24,0);
    drv_gpio_en_set(24,1);

    drv_gpio_oe_set(25,0);
    drv_gpio_en_set(25,1);

    drv_gpio_oe_set(26,0);
    drv_gpio_en_set(26,1);

    drv_gpio_oe_set(27,0);
    drv_gpio_en_set(27,1);

    drv_gpio_oe_set(29,0);
    drv_gpio_en_set(29,1);

    drv_gpio_oe_set(31,0);
    drv_gpio_en_set(31,1);
    /* end of NO-PIN IOs */

    drv_chip_dp0_500kohm_pull_down_set(TRUE);
    drv_chip_dp1_500kohm_pull_down_set(TRUE);
}

void sys_gpio_uart0_enable_set(bool_t en)
{
    bool_t old = drv_gpio_en_get(UART_RXD) ? FALSE : TRUE;
    if (old != en)
    {
        if (en)
        {
            drv_gpio_en_set(UART_TXD,FALSE);
            drv_gpio_pd_set(UART_TXD,FALSE);
            drv_gpio_pu_set(UART_TXD,FALSE);

            drv_gpio_en_set(UART_RXD,FALSE);
            drv_gpio_pd_set(UART_RXD,FALSE);
            drv_gpio_pu_set(UART_RXD,FALSE);

#if SYS_QUICK_CHARGE_ENABLED
            if (!usbpd_cfg_port_quick_charge_en_get())
            {
                drv_chip_dp0_dm0_short_set(FALSE);
            }
#else
            drv_chip_dp0_dm0_short_set(FALSE);
#endif /* SYS_QUICK_CHARGE_ENABLED */
        }
        else {
            drv_gpio_en_set(UART_TXD,TRUE);
            drv_gpio_oe_set(UART_TXD,FALSE);

            drv_gpio_en_set(UART_RXD,TRUE);
            drv_gpio_oe_set(UART_RXD,FALSE);

#if SYS_QUICK_CHARGE_ENABLED
            if (!usbpd_cfg_port_quick_charge_en_get())
            {
                drv_chip_dp0_dm0_short_set(TRUE);
            }
#else
            drv_chip_dp0_dm0_short_set(TRUE);
#endif /* SYS_QUICK_CHARGE_ENABLED */
        }
    }
}

void sys_gpio_uart1_enable_set(bool_t en)
{
    bool_t old = drv_gpio_en_get(SEC_UART_RXD) ? FALSE : TRUE;
    if (old != en)
    {
        if (en)
        {
            drv_gpio_en_set(SEC_UART_TXD,FALSE);
            drv_gpio_pd_set(SEC_UART_TXD,FALSE);
            drv_gpio_pu_set(SEC_UART_TXD,FALSE);

            drv_gpio_en_set(SEC_UART_RXD,FALSE);
            drv_gpio_pd_set(SEC_UART_RXD,FALSE);
            drv_gpio_pu_set(SEC_UART_RXD,FALSE);
        }
        else {
            drv_gpio_en_set(SEC_UART_TXD,TRUE);
            drv_gpio_oe_set(SEC_UART_TXD,FALSE);

            drv_gpio_en_set(SEC_UART_RXD,TRUE);
            drv_gpio_oe_set(SEC_UART_RXD,FALSE);
        }
    }
}




void sys_gpio_uart0_disable(void)
{
    if ((dpm_vbus_volt_get() > 2500U) &&
        (drv_flash_firmware_is_unbroken()))
    {
        drv_gpio_en_set(UART_TXD,TRUE);
        drv_gpio_pd_set(UART_TXD,FALSE);
        drv_gpio_oe_set(UART_TXD,FALSE);

        drv_gpio_en_set(UART_RXD,TRUE);
        drv_gpio_pd_set(UART_RXD,FALSE);
        drv_gpio_oe_set(UART_RXD,FALSE);
        drv_chip_dp0_dm0_short_set(TRUE);
    }
}

void sys_gpio_uart0_enable(void)
{
    drv_gpio_en_set(UART_TXD,FALSE);
    drv_gpio_pd_set(UART_TXD,FALSE);
    drv_gpio_pu_set(UART_TXD,FALSE);

    drv_gpio_en_set(UART_RXD,FALSE);
    drv_gpio_pd_set(UART_RXD,FALSE);
    drv_gpio_pu_set(UART_RXD,FALSE);
    drv_chip_dp0_dm0_short_set(FALSE);
}


