@ -14,6 +14,13 @@
# include "mxs_init.h"
/**
* mxs_power_clock2xtal ( ) - Switch CPU core clock source to 24 MHz XTAL
*
* This function switches the CPU core clock from PLL to 24 MHz XTAL
* oscilator . This is necessary if the PLL is being reconfigured to
* prevent crash of the CPU core .
*/
static void mxs_power_clock2xtal ( void )
{
struct mxs_clkctrl_regs * clkctrl_regs =
@ -24,6 +31,13 @@ static void mxs_power_clock2xtal(void)
& clkctrl_regs - > hw_clkctrl_clkseq_set ) ;
}
/**
* mxs_power_clock2pll ( ) - Switch CPU core clock source to PLL
*
* This function switches the CPU core clock from 24 MHz XTAL oscilator
* to PLL . This can only be called once the PLL has re - locked and once
* the PLL is stable after reconfiguration .
*/
static void mxs_power_clock2pll ( void )
{
struct mxs_clkctrl_regs * clkctrl_regs =
@ -36,6 +50,13 @@ static void mxs_power_clock2pll(void)
CLKCTRL_CLKSEQ_BYPASS_CPU ) ;
}
/**
* mxs_power_set_auto_restart ( ) - Set the auto - restart bit
*
* This function ungates the RTC block and sets the AUTO_RESTART
* bit to work around a design bug on MX28EVK Rev . A .
*/
static void mxs_power_set_auto_restart ( void )
{
struct mxs_rtc_regs * rtc_regs =
@ -66,6 +87,14 @@ static void mxs_power_set_auto_restart(void)
;
}
/**
* mxs_power_set_linreg ( ) - Set linear regulators 25 mV below DC - DC converter
*
* This function configures the VDDIO , VDDA and VDDD linear regulators output
* to be 25 mV below the VDDIO , VDDA and VDDD output from the DC - DC switching
* converter . This is the recommended setting for the case where we use both
* linear regulators and DC - DC converter to power the VDDIO rail .
*/
static void mxs_power_set_linreg ( void )
{
struct mxs_power_regs * power_regs =
@ -85,6 +114,11 @@ static void mxs_power_set_linreg(void)
POWER_VDDIOCTRL_LINREG_OFFSET_1STEPS_BELOW ) ;
}
/**
* mxs_get_batt_volt ( ) - Measure battery input voltage
*
* This function retrieves the battery input voltage and returns it .
*/
static int mxs_get_batt_volt ( void )
{
struct mxs_power_regs * power_regs =
@ -96,11 +130,24 @@ static int mxs_get_batt_volt(void)
return volt ;
}
/**
* mxs_is_batt_ready ( ) - Test if the battery provides enough voltage to boot
*
* This function checks if the battery input voltage is higher than 3.6 V and
* therefore allows the system to successfully boot using this power source .
*/
static int mxs_is_batt_ready ( void )
{
return ( mxs_get_batt_volt ( ) > = 3600 ) ;
}
/**
* mxs_is_batt_good ( ) - Test if battery is operational at all
*
* This function starts recharging the battery and tests if the input current
* provided by the 5 V input recharging the battery is also sufficient to power
* the DC - DC converter .
*/
static int mxs_is_batt_good ( void )
{
struct mxs_power_regs * power_regs =
@ -141,6 +188,15 @@ static int mxs_is_batt_good(void)
return 0 ;
}
/**
* mxs_power_setup_5v_detect ( ) - Start the 5 V input detection comparator
*
* This function enables the 5 V detection comparator and sets the 5 V valid
* threshold to 4.4 V . We use 4.4 V threshold here to make sure that even
* under high load , the voltage drop on the 5 V input won ' t be so critical
* to cause undervolt on the 4 P2 linear regulator supplying the DC - DC
* converter and thus making the system crash .
*/
static void mxs_power_setup_5v_detect ( void )
{
struct mxs_power_regs * power_regs =
@ -153,6 +209,12 @@ static void mxs_power_setup_5v_detect(void)
POWER_5VCTRL_PWRUP_VBUS_CMPS ) ;
}
/**
* mxs_src_power_init ( ) - Preconfigure the power block
*
* This function configures reasonable values for the DC - DC control loop
* and battery monitor .
*/
static void mxs_src_power_init ( void )
{
struct mxs_power_regs * power_regs =
@ -184,6 +246,12 @@ static void mxs_src_power_init(void)
clrbits_le32 ( & power_regs - > hw_power_5vctrl , POWER_5VCTRL_DCDC_XFER ) ;
}
/**
* mxs_power_init_4p2_params ( ) - Configure the parameters of the 4 P2 regulator
*
* This function configures the necessary parameters for the 4 P2 linear
* regulator to supply the DC - DC converter from 5 V input .
*/
static void mxs_power_init_4p2_params ( void )
{
struct mxs_power_regs * power_regs =
@ -208,6 +276,12 @@ static void mxs_power_init_4p2_params(void)
0x3f < < POWER_5VCTRL_CHARGE_4P2_ILIMIT_OFFSET ) ;
}
/**
* mxs_enable_4p2_dcdc_input ( ) - Enable or disable the DCDC input from 4 P2
* @ xfer : Select if the input shall be enabled or disabled
*
* This function enables or disables the 4 P2 input into the DC - DC converter .
*/
static void mxs_enable_4p2_dcdc_input ( int xfer )
{
struct mxs_power_regs * power_regs =
@ -304,6 +378,12 @@ static void mxs_enable_4p2_dcdc_input(int xfer)
POWER_CTRL_ENIRQ_VDD5V_DROOP ) ;
}
/**
* mxs_power_init_4p2_regulator ( ) - Start the 4 P2 regulator
*
* This function enables the 4 P2 regulator and switches the DC - DC converter
* to use the 4 P2 input .
*/
static void mxs_power_init_4p2_regulator ( void )
{
struct mxs_power_regs * power_regs =
@ -388,6 +468,12 @@ static void mxs_power_init_4p2_regulator(void)
writel ( POWER_CTRL_DCDC4P2_BO_IRQ , & power_regs - > hw_power_ctrl_clr ) ;
}
/**
* mxs_power_init_dcdc_4p2_source ( ) - Switch DC - DC converter to 4 P2 source
*
* This function configures the DC - DC converter to be supplied from the 4 P2
* linear regulator .
*/
static void mxs_power_init_dcdc_4p2_source ( void )
{
struct mxs_power_regs * power_regs =
@ -410,6 +496,12 @@ static void mxs_power_init_dcdc_4p2_source(void)
}
}
/**
* mxs_power_enable_4p2 ( ) - Power up the 4 P2 regulator
*
* This function drives the process of powering up the 4 P2 linear regulator
* and switching the DC - DC converter input over to the 4 P2 linear regulator .
*/
static void mxs_power_enable_4p2 ( void )
{
struct mxs_power_regs * power_regs =
@ -469,6 +561,14 @@ static void mxs_power_enable_4p2(void)
& power_regs - > hw_power_charge_clr ) ;
}
/**
* mxs_boot_valid_5v ( ) - Boot from 5 V supply
*
* This function configures the power block to boot from valid 5 V input .
* This is called only if the 5 V is reliable and can properly supply the
* CPU . This function proceeds to configure the 4 P2 converter to be supplied
* from the 5 V input .
*/
static void mxs_boot_valid_5v ( void )
{
struct mxs_power_regs * power_regs =
@ -492,6 +592,11 @@ static void mxs_boot_valid_5v(void)
mxs_power_enable_4p2 ( ) ;
}
/**
* mxs_powerdown ( ) - Shut down the system
*
* This function powers down the CPU completely .
*/
static void mxs_powerdown ( void )
{
struct mxs_power_regs * power_regs =
@ -501,6 +606,12 @@ static void mxs_powerdown(void)
& power_regs - > hw_power_reset ) ;
}
/**
* mxs_batt_boot ( ) - Configure the power block to boot from battery input
*
* This function configures the power block to boot from the battery voltage
* supply .
*/
static void mxs_batt_boot ( void )
{
struct mxs_power_regs * power_regs =
@ -545,6 +656,14 @@ static void mxs_batt_boot(void)
0x8 < < POWER_5VCTRL_CHARGE_4P2_ILIMIT_OFFSET ) ;
}
/**
* mxs_handle_5v_conflict ( ) - Test if the 5 V input is reliable
*
* This function tests if the 5 V input can reliably supply the system . If it
* can , then proceed to configuring the system to boot from 5 V source , otherwise
* try booting from battery supply . If we can not boot from battery supply
* either , shut down the system .
*/
static void mxs_handle_5v_conflict ( void )
{
struct mxs_power_regs * power_regs =
@ -581,6 +700,12 @@ static void mxs_handle_5v_conflict(void)
}
}
/**
* mxs_5v_boot ( ) - Configure the power block to boot from 5 V input
*
* This function handles configuration of the power block when supplied by
* a 5 V input .
*/
static void mxs_5v_boot ( void )
{
struct mxs_power_regs * power_regs =
@ -604,6 +729,12 @@ static void mxs_5v_boot(void)
mxs_handle_5v_conflict ( ) ;
}
/**
* mxs_init_batt_bo ( ) - Configure battery brownout threshold
*
* This function configures the battery input brownout threshold . The value
* at which the battery brownout happens is configured to 3.0 V in the code .
*/
static void mxs_init_batt_bo ( void )
{
struct mxs_power_regs * power_regs =
@ -618,6 +749,12 @@ static void mxs_init_batt_bo(void)
writel ( POWER_CTRL_ENIRQ_BATT_BO , & power_regs - > hw_power_ctrl_clr ) ;
}
/**
* mxs_switch_vddd_to_dcdc_source ( ) - Switch VDDD rail to DC - DC converter
*
* This function turns off the VDDD linear regulator and therefore makes
* the VDDD rail be supplied only by the DC - DC converter .
*/
static void mxs_switch_vddd_to_dcdc_source ( void )
{
struct mxs_power_regs * power_regs =
@ -632,6 +769,15 @@ static void mxs_switch_vddd_to_dcdc_source(void)
POWER_VDDDCTRL_DISABLE_STEPPING ) ;
}
/**
* mxs_power_configure_power_source ( ) - Configure power block source
*
* This function is the core of the power configuration logic . The function
* selects the power block input source and configures the whole power block
* accordingly . After the configuration is complete and the system is stable
* again , the function switches the CPU clock source back to PLL . Finally ,
* the function switches the voltage rails to DC - DC converter .
*/
static void mxs_power_configure_power_source ( void )
{
int batt_ready , batt_good ;
@ -676,6 +822,15 @@ static void mxs_power_configure_power_source(void)
# endif
}
/**
* mxs_enable_output_rail_protection ( ) - Enable power rail protection
*
* This function enables overload protection on the power rails . This is
* triggered if the power rails ' voltage drops rapidly due to overload and
* in such case , the supply to the powerrail is cut - off , protecting the
* CPU from damage . Note that under such condition , the system will likely
* crash or misbehave .
*/
static void mxs_enable_output_rail_protection ( void )
{
struct mxs_power_regs * power_regs =
@ -694,6 +849,13 @@ static void mxs_enable_output_rail_protection(void)
POWER_VDDIOCTRL_PWDN_BRNOUT ) ;
}
/**
* mxs_get_vddio_power_source_off ( ) - Get VDDIO rail power source
*
* This function tests if the VDDIO rail is supplied by linear regulator
* or by the DC - DC converter . Returns 1 if powered by linear regulator ,
* returns 0 if powered by the DC - DC converter .
*/
static int mxs_get_vddio_power_source_off ( void )
{
struct mxs_power_regs * power_regs =
@ -722,6 +884,13 @@ static int mxs_get_vddio_power_source_off(void)
}
/**
* mxs_get_vddd_power_source_off ( ) - Get VDDD rail power source
*
* This function tests if the VDDD rail is supplied by linear regulator
* or by the DC - DC converter . Returns 1 if powered by linear regulator ,
* returns 0 if powered by the DC - DC converter .
*/
static int mxs_get_vddd_power_source_off ( void )
{
struct mxs_power_regs * power_regs =
@ -810,6 +979,18 @@ static const struct mxs_vddx_cfg mxs_vddmem_cfg = {
} ;
# endif
/**
* mxs_power_set_vddx ( ) - Configure voltage on DC - DC converter rail
* @ cfg : Configuration data of the DC - DC converter rail
* @ new_target : New target voltage of the DC - DC converter rail
* @ new_brownout : New brownout trigger voltage
*
* This function configures the output voltage on the DC - DC converter rail .
* The rail is selected by the @ cfg argument . The new voltage target is
* selected by the @ new_target and the voltage is specified in mV . The
* new brownout value is selected by the @ new_brownout argument and the
* value is also in mV .
*/
static void mxs_power_set_vddx ( const struct mxs_vddx_cfg * cfg ,
uint32_t new_target , uint32_t new_brownout )
{
@ -883,6 +1064,14 @@ static void mxs_power_set_vddx(const struct mxs_vddx_cfg *cfg,
}
}
/**
* mxs_setup_batt_detect ( ) - Start the battery voltage measurement logic
*
* This function starts and configures the LRADC block . This allows the
* power initialization code to measure battery voltage and based on this
* knowledge , decide whether to boot at all , boot from battery or boot
* from 5 V input .
*/
static void mxs_setup_batt_detect ( void )
{
mxs_lradc_init ( ) ;
@ -890,6 +1079,14 @@ static void mxs_setup_batt_detect(void)
early_delay ( 10 ) ;
}
/**
* mxs_ungate_power ( ) - Ungate the POWER block
*
* This function ungates clock to the power block . In case the power block
* was still gated at this point , it will not be possible to configure the
* block and therefore the power initialization would fail . This function
* is only needed on i . MX233 , on i . MX28 the power block is always ungated .
*/
static void mxs_ungate_power ( void )
{
# ifdef CONFIG_MX23
@ -900,6 +1097,12 @@ static void mxs_ungate_power(void)
# endif
}
/**
* mxs_power_init ( ) - The power block init main function
*
* This function calls all the power block initialization functions in
* proper sequence to start the power block .
*/
void mxs_power_init ( void )
{
struct mxs_power_regs * power_regs =
@ -933,6 +1136,12 @@ void mxs_power_init(void)
}
# ifdef CONFIG_SPL_MXS_PSWITCH_WAIT
/**
* mxs_power_wait_pswitch ( ) - Wait for power switch to be pressed
*
* This function waits until the power - switch was pressed to start booting
* the board .
*/
void mxs_power_wait_pswitch ( void )
{
struct mxs_power_regs * power_regs =