ARM Cortex-A15 Data Abort Exception During SDRAM Size Detection
The core issue revolves around the ARM Cortex-A15 processor encountering a data abort exception when attempting to detect the size of SDRAM in a uBoot bootloader environment. The system is designed to support either 2GB or 4GB of SDRAM, and the detection mechanism involves writing to and reading from the 4GB address space. When only 2GB of SDRAM is installed, accessing the 4GB address space triggers a data abort exception, causing the processor to enter a halt state or infinite loop. The challenge is to recover from this exception gracefully and continue execution, allowing the system to determine the actual SDRAM size.
The ARM Cortex-A15 processor, part of the ARMv7 architecture, is designed to handle exceptions such as data aborts through a predefined exception vector table. When a data abort occurs, the processor saves the current state (including the program counter and CPSR) and jumps to the data abort exception handler. The handler must then determine the cause of the abort, take appropriate action, and resume normal execution. In this case, the goal is to detect whether the abort was caused by an invalid SDRAM access and, if so, adjust the SDRAM size configuration accordingly.
The uBoot bootloader initializes the External Memory Interface (EMIF) and LISA registers for a 4GB address space, regardless of the actual SDRAM size. This initialization is necessary to ensure that the memory controller is configured correctly for the maximum possible SDRAM size. However, when only 2GB of SDRAM is installed, accessing addresses beyond the 2GB boundary results in a data abort. The exception handler must be able to distinguish between this specific case and other potential causes of data aborts, such as invalid memory accesses due to software bugs or hardware faults.
Memory Access Violation and Exception Handling Mechanism
The primary cause of the issue is the memory access violation that occurs when attempting to access an address beyond the physically installed SDRAM size. The ARM Cortex-A15 processor generates a data abort exception in response to this violation, which must be handled appropriately to avoid system failure. The exception handling mechanism in ARMv7 architecture involves several key components, including the exception vector table, the Data Abort Status Register (DFSR), and the Fault Address Register (DFAR).
The exception vector table contains the addresses of the exception handlers, including the data abort handler. When a data abort occurs, the processor saves the current state and jumps to the data abort handler. The handler must then read the DFSR and DFAR to determine the cause and location of the abort. The DFSR provides information about the type of abort (e.g., translation fault, permission fault), while the DFAR contains the address that caused the abort.
In this specific case, the data abort is caused by a translation fault, as the accessed address is beyond the physically installed SDRAM size. The exception handler must recognize this specific condition and take appropriate action, such as adjusting the SDRAM size configuration and resuming execution. This requires careful implementation of the exception handler, including the use of assembly language to ensure precise control over the processor state and execution flow.
The use of C++ try/catch constructs is not suitable for this low-level exception handling, as they are designed for higher-level software exceptions and do not provide the necessary control over the processor state. Instead, the exception handler must be implemented in assembly language, with careful attention to the ARMv7 exception handling model and the specific requirements of the uBoot bootloader environment.
Implementing a Robust Data Abort Handler for SDRAM Size Detection
To address the issue, a robust data abort handler must be implemented in assembly language, with the following key steps:
-
Save the Processor State: When a data abort occurs, the processor saves the current state, including the program counter (PC) and CPSR, to the appropriate registers. The exception handler must save additional context, such as general-purpose registers, to ensure that the system state can be restored after handling the abort.
-
Determine the Cause of the Abort: The handler must read the DFSR and DFAR to determine the cause and location of the abort. If the abort was caused by an access to an address beyond the physically installed SDRAM size, the handler should proceed to adjust the SDRAM size configuration.
-
Adjust the SDRAM Size Configuration: If the abort was caused by an invalid SDRAM access, the handler should adjust the SDRAM size configuration in the uBoot global data structure (gd->ram_size) to reflect the actual installed size (2GB in this case).
-
Resume Execution: After handling the abort, the handler must restore the saved processor state and resume execution at the instruction following the one that caused the abort. This requires careful manipulation of the saved PC and CPSR to ensure that the processor continues execution correctly.
The following assembly code provides an example implementation of the data abort handler:
.global data_abort_handler
data_abort_handler:
// Save the context
STMFD sp!, {r0-r12, lr}
MRS r0, SPSR
STMFD sp!, {r0}
// Read DFSR and DFAR
MRC p15, 0, r1, c5, c0, 0 // Read DFSR
MRC p15, 0, r2, c6, c0, 0 // Read DFAR
// Check if the abort was caused by a translation fault
AND r1, r1, #0xF
CMP r1, #0x5
BNE abort_not_handled
// Check if the fault address is within the 2GB-4GB range
LDR r3, =0x80000000
CMP r2, r3
BLO abort_not_handled
LDR r3, =0x100000000
CMP r2, r3
BHS abort_not_handled
// Adjust the SDRAM size configuration
LDR r3, =gd
LDR r4, [r3, #offsetof(gd, ram_size)]
LDR r5, =0x80000000
STR r5, [r3, #offsetof(gd, ram_size)]
abort_not_handled:
// Restore the context
LDMFD sp!, {r0}
MSR SPSR_cxsf, r0
LDMFD sp!, {r0-r12, lr}
SUBS pc, lr, #4
This code saves the processor state, reads the DFSR and DFAR to determine the cause of the abort, and checks if the abort was caused by an access to the 2GB-4GB address range. If so, it adjusts the SDRAM size configuration in the uBoot global data structure. Finally, it restores the processor state and resumes execution.
In conclusion, handling data abort exceptions for SDRAM size detection in uBoot requires a deep understanding of the ARMv7 exception handling model and careful implementation of the exception handler in assembly language. By following the steps outlined above, it is possible to recover from data abort exceptions gracefully and ensure that the system correctly detects the installed SDRAM size.