203 lines
5.3 KiB
C
203 lines
5.3 KiB
C
#include "asm/power_interface.h"
|
|
#include "system/includes.h"
|
|
#include "asm/mcpwm.h"
|
|
#include "app_config.h"
|
|
|
|
|
|
static int lcdpg_pwm_id = -1;
|
|
static int mtpg_pwm_id = -1;
|
|
|
|
|
|
/*
|
|
*@brief 初始化pg_io送出高阻+低电平的pwm
|
|
*@param pg_io : 可选IO_LCD_PG, IO_MT_PG
|
|
*@param freq : pwm的频率
|
|
*@param duty : pwm的低电平的占空比,0~10000对应0%~100%
|
|
*@return 0:成功 非0:失败
|
|
*/
|
|
int power_gate_pwm_init(u32 pg_io, u32 freq, u32 duty)
|
|
{
|
|
struct mcpwm_config pg_mcpwm_cfg;
|
|
memset(&pg_mcpwm_cfg, 0, sizeof(struct mcpwm_config));
|
|
|
|
pg_mcpwm_cfg.aligned_mode = MCPWM_EDGE_ALIGNED; //边沿对齐
|
|
pg_mcpwm_cfg.frequency = freq;
|
|
pg_mcpwm_cfg.duty = duty; //占空比
|
|
pg_mcpwm_cfg.h_pin = pg_io; //任意引脚
|
|
pg_mcpwm_cfg.l_pin = -1; //任意引脚,不需要就填-1
|
|
pg_mcpwm_cfg.complementary_en = 0; //两个引脚的波形, 0: 同步, 1: 互补
|
|
pg_mcpwm_cfg.detect_port = -1; //任意引脚,不需要就填-1
|
|
if (pg_io == IO_LCD_PG) {
|
|
pg_mcpwm_cfg.ch = MCPWM_CH0; //通道号
|
|
lcdpg_pwm_id = mcpwm_init(&pg_mcpwm_cfg);
|
|
if (lcdpg_pwm_id < 0) {
|
|
return 1;
|
|
}
|
|
mcpwm_start(lcdpg_pwm_id);
|
|
} else {
|
|
pg_mcpwm_cfg.ch = MCPWM_CH1; //通道号
|
|
mtpg_pwm_id = mcpwm_init(&pg_mcpwm_cfg);
|
|
if (mtpg_pwm_id < 0) {
|
|
return 1;
|
|
}
|
|
mcpwm_start(mtpg_pwm_id);
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
/*
|
|
*@brief 设置pg_io的pwm的低电平占空比
|
|
*@param pg_io : 可选IO_LCD_PG, IO_MT_PG
|
|
*@param duty : pwm的低电平的占空比,0~10000对应0%~100%
|
|
*/
|
|
void power_gate_pwm_set_duty(u32 pg_io, u32 duty)
|
|
{
|
|
if ((pg_io == IO_LCD_PG) && (lcdpg_pwm_id >= 0)) {
|
|
mcpwm_set_duty(lcdpg_pwm_id, duty);
|
|
}
|
|
if ((pg_io == IO_MT_PG) && (mtpg_pwm_id >= 0)) {
|
|
mcpwm_set_duty(mtpg_pwm_id, duty);
|
|
}
|
|
}
|
|
|
|
/*
|
|
*@brief 关闭pwm, pg_io为高阻
|
|
*@param pg_io : 可选IO_LCD_PG, IO_MT_PG
|
|
*/
|
|
void power_gate_pwm_close(u32 pg_io)
|
|
{
|
|
if ((pg_io == IO_LCD_PG) && (lcdpg_pwm_id >= 0)) {
|
|
mcpwm_deinit(lcdpg_pwm_id);
|
|
}
|
|
if ((pg_io == IO_MT_PG) && (mtpg_pwm_id >= 0)) {
|
|
mcpwm_deinit(mtpg_pwm_id);
|
|
}
|
|
}
|
|
|
|
/*
|
|
*@brief 设置pg_io的开漏输出
|
|
*@param pg_io : 可选IO_LCD_PG, IO_MT_PG
|
|
*@param value : 0,输出低电平 1,则高阻
|
|
*/
|
|
void power_gate_open_drain_output(u32 pg_io, u32 value)
|
|
{
|
|
if (pg_io == IO_LCD_PG) {
|
|
SFR(JL_IOMC->LCDPG_CON, 1, 1, !value);
|
|
JL_IOMC->LCDPG_CON &= ~BIT(0);
|
|
}
|
|
if (pg_io == IO_MT_PG) {
|
|
SFR(JL_IOMC->MTPG_CON, 1, 1, !value);
|
|
JL_IOMC->MTPG_CON &= ~BIT(0);
|
|
}
|
|
}
|
|
|
|
static void power_fspg2_step_1(void)
|
|
{
|
|
//out0 slowly
|
|
JL_IOMC->STPG_CON |= BIT(STPG_HD0);
|
|
JL_IOMC->STPG_CON &= ~BIT(STPG_HD1);
|
|
JL_IOMC->STPG_CON &= ~BIT(STPG_A);
|
|
JL_IOMC->STPG_CON |= BIT(STPG_OE);
|
|
}
|
|
|
|
static void power_fspg2_step_2()
|
|
{
|
|
//STPG highz
|
|
JL_IOMC->STPG_CON &= ~(BIT(STPG_PD) | BIT(STPG_PD1));
|
|
JL_IOMC->STPG_CON &= ~BIT(STPG_OE);
|
|
|
|
//STPG out1 slowly
|
|
JL_IOMC->STPG_CON |= BIT(STPG_A);
|
|
JL_IOMC->STPG_CON &= ~BIT(STPG_HD1);
|
|
JL_IOMC->STPG_CON |= BIT(STPG_HD0);
|
|
JL_IOMC->STPG_CON |= BIT(STPG_OE);
|
|
}
|
|
|
|
static void power_fspg2_step_3()
|
|
{
|
|
//out1 driving max
|
|
u32 STPG_CON = JL_IOMC->STPG_CON;
|
|
STPG_CON |= BIT(STPG_HD1);
|
|
STPG_CON &= ~BIT(STPG_HD0);
|
|
JL_IOMC->STPG_CON = STPG_CON;
|
|
|
|
}
|
|
|
|
/*
|
|
*@brief 开启stpg供电
|
|
*@param udly_time : us延时
|
|
*@param mdly_time : ms延时
|
|
*@param *custom_udelay :us延时回调函数
|
|
*@param *custom_mdelay :ms延时回调函数
|
|
*/
|
|
static void power_gate_fspg2_base(u32 udly_time, u32 mdly_time, void (*custom_udelay)(u32), void (*custom_mdelay)(u32))
|
|
{
|
|
//if stpg power have been 1, don't need poweron again
|
|
if (JL_IOMC->STPG_CON & BIT(STPG_A)) {
|
|
return;
|
|
}
|
|
|
|
//FIXME:输出0延时100us后,io是否需要设置为高阻
|
|
power_fspg2_step_1();
|
|
if (custom_udelay) {
|
|
custom_udelay(udly_time);
|
|
}
|
|
|
|
power_fspg2_step_2();
|
|
|
|
if (custom_udelay) {
|
|
custom_udelay(udly_time);
|
|
}
|
|
|
|
power_fspg2_step_3();
|
|
|
|
if (custom_mdelay) {
|
|
custom_mdelay(mdly_time);
|
|
}
|
|
}
|
|
|
|
void fspg2_poweron(u32 ms)
|
|
{
|
|
power_gate_fspg2_base(100, ms, udelay, mdelay);
|
|
}
|
|
|
|
/*
|
|
*@brief 关闭stpg供电
|
|
*@param udly_time : us延时
|
|
*@param mdly_time : ms延时
|
|
*@param *custom_udelay :us延时回调函数
|
|
*@param *custom_mdelay :ms延时回调函数
|
|
*/
|
|
static void poweroff_gate_fspg2_base(u32 udly_time, u32 mdly_time, void (*custom_udelay)(u32), void (*custom_mdelay)(u32))
|
|
{
|
|
|
|
//out0 slowly
|
|
u32 stpg_con = JL_IOMC->STPG_CON;
|
|
stpg_con |= BIT(STPG_HD0);
|
|
stpg_con &= ~BIT(STPG_HD1);
|
|
JL_IOMC->STPG_CON = stpg_con;
|
|
JL_IOMC->STPG_CON &= ~BIT(STPG_A);
|
|
JL_IOMC->STPG_CON |= BIT(STPG_OE);
|
|
|
|
if (custom_udelay) {
|
|
custom_udelay(udly_time);
|
|
}
|
|
|
|
//pulldown 200k
|
|
JL_IOMC->STPG_CON |= BIT(STPG_PD);
|
|
JL_IOMC->STPG_CON &= ~BIT(STPG_PD1);
|
|
JL_IOMC->STPG_CON &= ~BIT(STPG_OE);
|
|
JL_IOMC->STPG_CON &= ~BIT(STPG_HD0);
|
|
|
|
/* log_i("Delay 100ms after fspg2_poweroff !\n"); */
|
|
if (custom_mdelay) {
|
|
custom_mdelay(mdly_time);
|
|
}
|
|
}
|
|
|
|
void fspg2_poweroff(u32 ms)
|
|
{
|
|
poweroff_gate_fspg2_base(100, ms, udelay, mdelay);
|
|
}
|
|
|