broadcom Power Management

Power States
博通定义了4个Power States(S0,S1,S2,S3)
On(S0):(都被激活状态,全功耗)
Display, decode, and record are all active
Full Power
Active Standby(S1): (未解码或显示,可以录制,数据处理可能会被破)
       No display or decode, but the box must listen for network messages or capture EPG data. Programs can be recorded.Momentary disruption of data processing is allowed in order to achieve minimum power
       Minimal power for the functionality
Passive Standby(S2):(只支持唤醒设备的AON和ON-OFF)
No display, decode, DVR, front end, or transport. No data processing. The system configures the supported wake-up devices that exist in AON and ON-OFF block  
Deep Sleep Standby(S3):(只支持唤醒设备的AON)
No display, decode, DVR, front end, or transport. The entire chip is power-gated except for the AON block. The system configures the supported wake-up devices that exist only in AON block.
各个状态可以相互转换,博通的40nm芯片在AON(Always ON)模块中有一个功率管理状态机监控所有的唤醒设备(如ir,CEC,Timer,KeyPad and GPIO)。不是所有的唤醒设备都在AON模块中,WOL,UHF和XPT不在AON中,所以这些设备不支持S4(Deep Sleep mode),只能在S3(Passive Standby mode)中使用,65nm芯片中没有AON模块,S4不支持。在ON-OFF模块的唤醒设备不同芯片是不同的,可以查阅相应芯片文档。

Active Standby State (S1)
使用S1模式的步骤:
1.停止playbck和实时解码
2.关闭所有的显示输出,移出所有的视窗输入。
3.调用NEXUS_Platform_SetStandbySettings()函数,使用Active Standby settings
4.应用程序调用kernel接口关闭kernel控制的外围设备
如:
a. SATA,USB,Ethernet以及MoCA.
b. Set the CPU clock divisor
c. Set the DDR self-refresh rate
d. Perform a MEMC1 power-down (only available on certain platforms).
代码片段如下:
NEXUS_PlatformStandbySettings nexusStandbySettings;
/* Stop decoders */
NEXUS_VideoDecoder_Stop(videoDecoder);
NEXUS_AudioDecoder_Stop(audioDecoder);
/*Stop playback */
NEXUS_Playback_Stop(playback);
/* Close File. Required for umount */
NEXUS_FilePlay_Close(file);
NEXUS_VideoWindow_RemoveInput(window, input);
NEXUS_VideoInput_Shutdown(input);
NEXUS_VideoWindow_Close(window);
NEXUS_Display_Close(display);
NEXUS_Platform_GetStandbySettings(&nexusStandbySettings);
nexusStandbySettings.mode = NEXUS_PlatformStandbyMode_eActive;
NEXUS_Platform_SetStandbySettings(&nexusStandbySettings);
可以查阅相关完整代码:
BSEAV/app/standby/active_standby.c
BSEAV/app/standby/standby.c
可以从/nexus/platform/$(NEXUS_PLATFORM)/include/nexus_platform_standby.h获取相关Nexus Standby APIs的信息

Passive Standby State (S2)
同样调用Nexus_Platform_SetStandbySettings()函数,可以用AON和ON-OFF模块
一般步骤为:
1.Stop all playback/record/live decode. Remove all display output and window inputs and c lose all displays
2.Call NEXUS_Platform_SetStandbySettings(), using NEXUS_PlatformStandbyMode_ePassive mode   and correct the wake-up settings
3.3. Call pmlib to power down linux controlled peripherals and put the CPU in SUSPEND mod e.

设置唤醒设备
唤醒设备使用Nexus api编程,通过配置NEXUS_PlatformStandbySettings,传给NEXUS_Platform_SetStandbySettings函数。这只适用S2和S3,在S1模式下唤醒不需要编程,因为kernel未standby并且通过软件监控事件。编程使用的任意事件都会讲CPU唤醒,比如你将IR,UHF,键盘,GPIO,HDMI,CEC,Timer,等作为支持唤醒的设备,当这些唤醒设备发生相应变化是,达到唤醒状态。
IR和UHF可以通过制定某个键按下来唤醒CPU,NEXUS_PlatformStandbyStatus数据结构体提供了唤醒的状态,NEXUS_Platform_GetStandbyStatus()将能获取到是哪个设备唤醒了CPU。
不是所有的linux kernel版本都支持唤醒CPU,高于2.6.31的版本才支持。

通过IR和UHF唤醒S2代码片段如下:
NEXUS_PlatformStandbySettings nexusStandbySettings;
/* Stop decoders */
NEXUS_VideoDecoder_Stop(videoDecoder);
NEXUS_AudioDecoder_Stop(audioDecoder);
/*Stop playback */
NEXUS_Playback_Stop(playback);
/* Close File. Required for umount */
NEXUS_FilePlay_Close(file);
NEXUS_Platform_GetStandbySettings(&nexusStandbySettings);
nexusStandbySettings.mode = NEXUS_PlatformStandbyMode_ePassive;
nexusStandbySettings.wakeupSettings.ir=true; /* Wake-up from IR*/
nexusStandbySettings.wakeupSettings.uhf=true; /* Wake-up from UHF */
nexusStandbySettings.wakeupSettings.timeout=10; /* Timeout in seconds */
NEXUS_Platform_SetStandbySettings(&nexusStandbySettings);

通过传输包唤醒S2的模式设置
Nexus_TransportWakeup_Filter Filter[16] =
{
{ 0x47, 0xFF, 1 }, { 0x12, 0xFF, 1 }, { 0x34, 0xFF, 1 }, { 0x15, 0xFF, 1 },
{ 0x12, 0xFF, 2 }, { 0x34, 0xFF, 2 }, { 0x03, 0xFF, 2 }, { 0x46, 0xFF, 2 },
{ 0x66, 0xFF, 2 }, { 0x4F, 0xFF, 3 }, { 0x31, 0xFF, 3 }, { 0x00, 0xFF, 3 },
{ 0x88, 0xFF, 2 }, { 0x77, 0xFF, 2 }, { 0x66, 0xFF, 2 }, { 0x55, 0xFF, 2 },
};
NEXUS_PlatformStandbySettings nexusStandbySettings;
NEXUS_TransportWakeup_Settings xptWakeupSettings;
NEXUS_Platform_GetStreamerInputBand(0, &inputBand);
NEXUS_TransportWakeup_GetSettings(&xptWakeupSettings);
BKNI_Memcpy(xptWakeupSettings.filter[0].packet, Filter, sizeof(Filter));
xptWakeupSettings.inputBand = inputBand;
xptWakeupSettings.packetLength = sizeof(Filter);
xptWakeupSettings.wakeupCallback.callback = transportWakeupCallback;
xptWakeupSettings.wakeupCallback.context = NULL;
xptWakeupSettings.enabled = true;
rc = NEXUS_TransportWakeup_SetSettings(&xptWakeupSettings);
NEXUS_Platform_GetStandbySettings(&nexusStandbySettings);
nexusStandbySettings.mode = NEXUS_PlatformStandbyMode_ePassive;
nexusStandbySettings.wakeupSettings.transport = true;
rc = NEXUS_Platform_SetStandbySettings(&nexusStandbySettings);

Deep Sleep Standby State(S3)
仍然是通过Nexus_Platform_SetStandbySettings(),只有AON模块了。
进入步骤如下:
1. Stop all playback/record/live decode. Remove all display output, window inputs and clo se all displays.同S2
2. Call NEXUS_Platform_SetStandbySettings(), using NEXUS_PlatformStandbyMode_eDeepSleep m ode and correct the wake-up settings
3. Power gate the chip by writing to the kernel sysfs interface

代码片段如下:
NEXUS_PlatformStandbySettings nexusStandbySettings;
/* Stop decoders */
NEXUS_VideoDecoder_Stop(videoDecoder);
NEXUS_AudioDecoder_Stop(audioDecoder);
/*Stop playback */
NEXUS_Playback_Stop(playback);
/* Close File. Required for umount */
NEXUS_FilePlay_Close(file);
NEXUS_Platform_GetStandbySettings(&nexusStandbySettings);
nexusStandbySettings.mode = NEXUS_PlatformStandbyMode_eDeepSleep;
nexusStandbySettings.wakeupSettings.ir=true;
nexusStandbySettings.wakeupSettings.uhf=true;
nexusStandbySettings.wakeupSettings.timeout=10; /* Timeout in seconds */
NEXUS_Platform_SetStandbySettings(&nexusStandbySettings);
S4(Deep Sleep Standby state)只支持2.6.37-2.2以上,上述只限于热启动,冷启动的方式另外处理
Dynamic Power Management(动态功率管理)
DPM是Nexus/Magnum软件内部特性,自动处理。这个技术在S0和S1状态使用。当用户调用STOP,disable或者disconnect组件时,Nexus和Magnum将检查是否关闭,对用户是透明的。
There are no explicit dynamic PM functions. The user?s responsibility is to consistently stop, disable, or disconnect components that are no longer in use. For instance, if you are not decoding from a transport input band, there?s no requirement that it be disabled. If you don‘t disable it, however, there’s no way for the underlying software to know that it can be powered down. This means that if the software consistently stops,disables, and/or disconnects components when they are no longer in use, dynamic PM will minimize the power consumption of the system.

Nexus Functions That Enable Dynamic PM
Frontend 
When no tuner is active, power will be reduced.
Call NEXUS_Frontend_Untune() to make a tuner inactive.
HdmiInput 
When all HdmiInput‘s are disconnected from any video window, power will be reduced.
NEXUS_VideoWindow_RemoveInput() will power down HDMI Rx.
VideoDecoder 
When all decodes are stopped and disconnected from any video window, power will be reduced.
Stop decode, then call:
NEXUS_VideoWindow_RemoveInput()
NEXUS_VideoInput_Shutdown()
Transport
  When all inputs are disabled,power will be automatically reduced.
Stop all playbacks using NEXUS_Playpump_Stop() or NEXUS_Playback_Stop() and NEXUS_PidChannel_Close()
Disable all input bands by setting
NEXUS_InputBandSettings.enabled = false.
Display
 When all outputs are disconnected, power will be reduced.
Call NEXUS_Display_RemoveOutput() for each output handle.
Security 
When all key slots have been closed, power will be reduced.
Call NEXUS_Security_FreeKeySlot() for every keyslot that has been created.
DMA
 When all DMA jobs have been terminated, power will be reduced.
Call NEXUS_DmaJob_Destroy() for every job that was created.
Graphics2D
 No dynamic power management at this time.
可以查阅nexus/examples/power_down.c

Linux Power Management
不是所有的硬件模块都是由Nexus和Magnum控制的,
例如,许多外围设备由kernel控制:
Power up/down for SATA, Ethernet, C, and USB
CPU clock scaling and DDR self-refresh rate.
Suspending the CPU and resuming from the wake-up device and/or timer.
Powering off or suspending secondary memory controller.
Hotplugging a secondary thread processor
Kernel Power State Changes
Linux kernel识别以下的power states:
S0: Full power; It maps into the On (S0) or Active Standby (S1) states
S1: Standby; maps to the Passive Standby (S2) state.
S3: Suspend to RAM (STR); maps to Deep Sleep Standby (S3) with warm boot.
Halt: Maps to power off or S3 with cold boot.
Full Power
PMLIB(BSEAV/lib/power_standby)

void *brcm_pm_ctx;
struct brcm_pm_state pmlib_state;
brcm_pm_ctx = brcm_pm_init();
brcm_pm_get_status(brcm_pm_ctx, &pmlib_state);
/*false : power down USB, true : power up USB */
pmlib_state.usb_status =false;
/*false : power down SATA, true : power up SATA */
pmlib_state.sata_status = false;
/*false : power down MEMC1, true : power up MEMC1 */
pmlib_state.memc1_status = false;
/*false : power down TP1, true : power up TP1 */
pmlib_state.tp1_status = false;
pmlib_state.cpu_divisor = cpu_divisor; /*Scale the CPU clock */
pmlib_state.ddr_timeout = ddr_timeout; /* Set DDR self refresh timeout */
rc = brcm_pm_set_status(brcm_pm_ctx, &pmlib_state);
/*SUSPEND CPU ("Passive Standby")*/
brcm_pm_suspend(brcm_pm_ctx, BRCM_PM_STANDBY);
注意,在待机前,请先umount掉其FS及设备。

SATA
要让hdparm工作,AHCI必须开启
hdparm -y /dev/<devname> 允许standby
hdparm -S0 /dev/sda 禁用standby

USB
pmusb -m auto <devname>
pmusb -m auto usb1
允许所有USB自动挂起
pmusb -m auto -r
禁用自动挂起
pmusb -m on -r

Net
ifdown eth0
ifup eth0

唤醒事件
S2和S3支持不同的事件
Wake-up Timer
1.Enable the timer interrupt in the PM/AON L2 interrupt control.
2.Enable the wake-up timer in the WKTMR_EVENT register.
3.Set timeout in seconds in WKTMR_ALARM register.Do NOT set bit 0 of standby_flags

Ethernet Wake-on-LAN
enable Ethernet Magic packet and ACPI WOL on interface ethX, issue the following command
ethtool -s ethX wol g
To enable Ethernet ACPI WOL only on interface ethX, issue the following command:
ethtool -s ethX wol a
To disable Ethernet Magic packet and ACPI WOL on interface ethX, use the following command:
ethtool -s ethX wol d

Linux Kernel Attributes
To initiate S3 standby with warm boot, run the following:
# echo mem > /sys/power/state
To initiate S2 standby, run the following:
# echo standby > /sys/power/state
To initiate S3 standby with cold boot, run the following:
# echo 1 > /sys/devices/platform/brcmstb/halt_mode
# halt
To offline TP1, run the following:
# echo 0 > /sys/devices/system/cpu/cpu1/online
To online tp1, run the following:
# echo 1 > /sys/devices/system/cpu/cpu1/online

broadcom特有的属性
Broadcom特有的功率管理属性位于/sys/devices/platform/brcmstb目录下
memc1_power 控制MEMC1/DDR1的状态
0 powered down
1 fully powered
2 in SSPD
# echo 0 > /sys/devices/platform/brcmstb/memc1_power
# echo 1 > /sys/devices/platform/brcmstb/memc1_power
# echo 2 > /sys/devices/platform/brcmstb/memc1_power

standby_flags
默认为0
Bit #Bit Mask   Description
0   0x01   Wake the system in one second.
1 0x02   Sleep for 180 seconds immediately prior to system suspend —— useful for BBS verification of
register settings. The system is not fully suspended at that time, however.
2 0x04   Print progress characters during low-level suspend/resume; useful for debugging
3 0x08   Do not go to S2 suspend —— wait for five seconds and resume. If Bit 1 is also set, timeout is 12
seconds.
# echo 0x5 > /sys/devices/platform/brcmstb/standby_flags

ddr_timeout
控制MEMC0自刷新
0   禁用自刷新 (默认)
1 允许自刷新
# echo 1 > /sys/devices/platform/brcmstb/ddr_timeout

time_at_wakeup
A read-only file that stores WKTMR, reading at the time of wake-up in the form of:
hex(COUNTER):hex(PRESCALER_VAL)
# cat /sys/devices/platform/brcmstb/time_at_wakeup
0:0
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值