Linux has become more and more popular. At present, many people are learning Linux systems, which has many problems with Linux systems. This article describes in detail the Linux kernel's support for the S3C2410 sleep mode, it plays a certain role when you learn about Linux kernel's support for the S3C2410 sleep mode x.
I. S3C2410 supports four Power Supply Modes
1) NORMAL MODE
Maximum power consumption. you can disable the clock of a specific controller to reduce power consumption.
2) SLOW MODE
In this mode, there can be no internal PLL, and the power consumption depends on the frequency of the external clock.
3) IDLE MODE
FCLK is shut down, mainly because of CPU core power saving. Can be awakened by any external interruption
4) Power_OFF MODE
In addition to the processor wake-up logic unit, the processor does not consume any power. You can use EINT [] or RTC alarm interrupt to wake up the system.
II. Introduction to various power-saving modes of S3C2410
1) SLOW mode SLOW)
Set SLOW_BIT of CLKSLOW to 1
2) IDLE in IDLE mode)
CLKCON [2] is set to 1 and then enters
3) power-down mode Power_OFF)
CLKCON [3] is set to 1
Iii. Preparations before S3C2410 enters the power-down mode
1. Set Reasonable GPIO for power-down mode
2. Block all interrupts in the interrupt shield register.
3. properly configure the wake-up source, including the real-time clock. 4. Disable USB. Miscr [] = 11b
5. Store the sleep return address or data that is not lost in the power-down mode in GSTATUS3, 4
6. Configure miscr [1:0] to pull the data bus
7. Disable LCD
8. Read REFRESH, CLKCON, and miscr registers to populate TLB.
8th points may be a little difficult to understand. You need to explain it:
The reason is that you need to suspend the SDRAM before entering the power-down mode. After the SDRAM is suspended, you also need to operate the REFRESH, CLKCON, and miscr special function registers. The addresses of these registers may be virtual addresses, this requires corresponding entries in TLB. If not, you need to fetch the corresponding page table from the sdram. At this time, the sdram has been suspended. To prevent this problem, you can read the address to be accessed before suspending the sdram, in this way, the corresponding page table items will be retained in the TLB, and the access to REFRESH, CLKCON, and miscr will not require the support of sdram.
9. set REFRESH [22] = 1b to enable the self-REFRESH mode for the sdram.
10. Wait for the Self-refresh of sdram to be effective.
11. Set miscr [] = 111b to enable the signal (SCLK0, SCLK1 and SCKE) of the SDRAM to be protected in Power_OF mode.
12. Set CLKCON to enter the Power_OFF mode.
Iv. Wake-up process in power-down mode of S3C2410
1. Wake up the source system to generate an internal reset signal
2. After the system is reset, test whether GSTATUS2 [2] is indeed awakened from Power_OFF mode.
3. Set miscr [] = 000b to release the SDRAM signal protection
4. Configure the SDRAM Controller
5. Wait until the SDRAM is automatically refreshed and released
6. Read the values of GSTATUS3 and 4 and use them to return to the program location before sleep.
Note: To wake up the system using an external interrupt EINT [], you must keep the nBATT_FLT High.
V. Configure 2.6.26.5 kernel to support S3C2410 Power Management
Vi. Linux system's support for the power-down mode of S3C2410
1) kernel interface driver File
The/drivers/char/Linux-2.6.26.5 of the apm-emulation.c Kernel provides an entry function for the system to sleep. In earlier versions, the interface file is arch/arm/kernel/apm. c.
2) kernel files related to preparation before entering sleep
Kernel/power/console. c
This file provides functions to sleep or shut down all system processes.
Drivers/base/power/suspend. c
This file enables all devices to drive the suspend function.
3) enter the settings related file before sleep
Arch/arm/mach-s3c2410/pm. c
4) program files in the Assembly segment before sleep
Arch/arm/mach-s3c2410/sleep. s
5) The Sleeping wake-up part is in Uboot.
Cpu/arm920t/start. s
6) Assembly segment program files related to the wake-up phase in the kernel
Arch/arm/mach-s3c2410/sleep. s
VII. Implementation Method
The specific implementation principle can be obtained by reading the relevant documents above. How to achieve system sleep and Wakeup
1) kernel Modification Process
Set the sleep wake-up interrupt source based on the actual hardware situation. My system is to interrupt 0-3 as the wake-up source. So let the kernel allow external interruption of the EINT0--3 to wake it up. The kernel version is 2.6.26.5. By default, the system allows eint0.eint15 and IRQ_RTC as the wake-up source for interruption.
The numbers of initial_irqwake_intmask and initialqwake_eintmask are shielding codes. To enable external interruption of the EINT0--3 as a wake-up source,
To be modified:
Arch/arm/plat-s3c24xx/irq. c
Unsigned long initi_irqwake_intmask = 0 xffffffffL;
Is:
Unsigned long initi_irqwake_intmask = 0xfffffff0L;
2) Modify U-boot
The system will run the reset program after sleep, of course, U-boot. To enable the wake-up system to resume normal operation and enter the pre-sleep running position, you need to modify the U-boot
Add the following code to the cpu/arm920t/start. s of uboot. Note: After the sdram is initialized, refer to the fourth title of this article, "S3C2410 power-down mode wake-up process"
- /* Power Manage Check if this is a wake-up from sleep */
- Ldr r1, = 0x5620.b4
- Ldr r0, [r1]
- Tst r0, #0x02
- Beq notPowerOFF
- /***** Led test ****
- Ldr r0, = 0x56000050
- Ldr r1, = 0x55555555
- Str r1, [r0]
- Ldr r0, = 0x56000054
- Ldr r1, = 0x0
- Str r1, [r0]
- */
- WakeupStart:
- // Clear sleep reset bit
- Ldr r0, = 0x5620.b4
- Mov r1, #0x2
- Str r1, [r0]
- Ldr r0, = 0x56000080 // Release the SDRAM signal protections
- Ldr r1, = 0x00010330
- Str r1, [r0]
- Ldr r0, = 0x48000024
- Ldr r1, [r0]
- Bic r1, r1, #0x400000
- Str r1, [r0]
- Mov RR1, #0x1000
- 1: subs r1, r1, #1 // wait until the SelfRefresh is released.
- Bne 1b
- /*
- Ldr r0, = 0x56000050
- Ldr r1, = 0x55555555
- Str r1, [r0]
- Ldr r0, = 0x56000054
- Ldr r1, = 0x5555
- Str r1, [r0]
- */
- Ldr r0, = 0x5620.b8 // read a return address go to s3c2410_cpu_resume
- Ldr r1, [r0]
- Mov pc, r1 // go to resume to the position before sleep
- Nop
- Nop
- 1: B 1b
- NotPowerOFF: 3) Compile the test program
- # Include<Stdio. h>
- # Include<Sys/Types. h>
- # Include<Sys/Ioctl. h>
- # Include<Unistd. h>
- # Include<Fcntl. h>
- # Include<Linux/Ioctl. h>
- # Define APM_IOC_STANDBY _ IO ('A', 1)
- # Define APM_IOC_SUSPEND _ IO ('A', 2)
- Int main (void)
- {
- Int fd;
- Fd=Open("/Dev/apm_bios", O_RDWR );
- If (fd< 0){
- Printf ("fd open failed \ n ");
- Exit (0 );
- }
- Printf ("\ n/dev/apm_bios opened,Fd= % D \ n ", fd );
- Ioctl (fd, APM_IOC_SUSPEND );
- Close (fd );
- Printf ("/dev/apm_bios closed :) \ n ");
- Return 0;
- }
4) Test Results
- #./test
- .....
- sleep: irq wakeup masks: fffffff0,fffffff0
- GSTATUS3 0x30367140
- GSTATUS4 0x00000000
Go to sleep status. Press the K10 button, that is, stop 0 and wake up the system.
- GPIO[0] CON 007fffff => 007fffff, DAT 00000000 => 00000000
- GPIO[1] CON 00044555 => 00044555, DAT 00000540 => 00000540
- GPIO[2] CON aaaaaaaa => aaaaaaaa, DAT 00000000 => 00000000
- GPIO[3] CON aaaaaaaa => aaaaaaaa, DAT 00000000 => 00000000
- GPIO[4] CON aaaaa6aa => aaaaa6aa, DAT 0000ffc5 => 0000ffc5
- GPIO[5] CON 000055aa => 000055aa, DAT 000000fe => 000000ff
- GPIO[6] CON ffa5ff30 => ffa5ffba, DAT 0000aced => 0000aced
- GPIO[7] CON 002afaaa => 002afaaa, DAT 000001ff => 000001fb
- post sleep: IRQs 0x02000001, 0x00000200
- IRQ 16 asserted at resume
- post sleep, preparing to return
- S3C2410 PM Resume (post-restore)
- s3c2410-sdi s3c2410-sdi: powered down.
- s3c24xx-pm: check if we have anything to wake-up with
- Disabling IRQ 52 (pin 192)
- Disabling IRQ 53 (pin 193)
- Disabling IRQ 55 (pin 195)
- dma3: restoring configuration
- timer tcon=00000000, tcnt a2c1, tcfg 00000200,00000000, usec 00001eb8
- s3c2410-wdt: watchdog disabled
- s3c2410-i2c s3c2410-i2c: slave address 0x10
- s3c2410-i2c s3c2410-i2c: bus frequency set to 390 KHz
- s3c2410-nand s3c2410-nand: Tacls=3, 30ns Twrph0=7 70ns, Twrph1=3 30ns
- s3c2410-sdi s3c2410-sdi: running at 0kHz (requested: 0kHz).
- s3c2410-sdi s3c2410-sdi: running at 98kHz (requested: 97kHz).
- s3c2410-sdi s3c2410-sdi: running at 98kHz (requested: 97kHz).
- s3c2410-sdi s3c2410-sdi: running at 98kHz (requested: 97kHz).
- s3c2410-sdi s3c2410-sdi: powered down.
- usb usb1: root hub lost power or was reset
- Restarting tasks ... done.
- /dev/apm_bios closed :)
- #
At this time, the system resumes normal operation. The preceding section describes the Linux kernel's support for the S3C2410 sleep mode.
- Easy understanding of Linux shutdown commands
- Describes how to enter and exit a Linux operating system
- Describe Linux operating system deficiencies and Development Trends
- Introduction to Linux Application Scope
- This gives you a better understanding of common Linux software.