3 ARM Mali DP 500/550/650 display controller driver
5 Copyright (c) 2017-2018, Arm Limited. All rights reserved.<BR>
7 SPDX-License-Identifier: BSD-2-Clause-Patent
11 #include <Library/DebugLib.h>
12 #include <Library/IoLib.h>
13 #include <Library/LcdHwLib.h>
14 #include <Library/LcdPlatformLib.h>
15 #include <Library/MemoryAllocationLib.h>
17 #include "ArmMaliDp.h"
19 // CORE_ID of the MALI DP
20 STATIC UINT32 mDpDeviceId
;
22 /** Disable the graphics layer
24 This is done by clearing the EN bit of the LG_CONTROL register.
28 LayerGraphicsDisable (VOID
)
30 MmioAnd32 (DP_BASE
+ DP_DE_LG_CONTROL
, ~DP_DE_LG_ENABLE
);
33 /** Enable the graphics layer
35 This is done by setting the EN bit of the LG_CONTROL register.
39 LayerGraphicsEnable (VOID
)
41 MmioOr32 (DP_BASE
+ DP_DE_LG_CONTROL
, DP_DE_LG_ENABLE
);
44 /** Set the frame address of the graphics layer.
46 @param[in] FrameBaseAddress Address of the data buffer to be used as
51 LayerGraphicsSetFrame (
52 IN CONST EFI_PHYSICAL_ADDRESS FrameBaseAddress
55 // Disable the graphics layer.
56 LayerGraphicsDisable ();
58 // Set up memory address of the data buffer for graphics layer.
59 // write lower bits of the address.
61 DP_BASE
+ DP_DE_LG_PTR_LOW
,
62 DP_DE_LG_PTR_LOW_MASK
& FrameBaseAddress
65 // Write higher bits of the address.
67 DP_BASE
+ DP_DE_LG_PTR_HIGH
,
68 (UINT32
)(FrameBaseAddress
>> DP_DE_LG_PTR_HIGH_SHIFT
)
71 // Enable the graphics layer.
72 LayerGraphicsEnable ();
75 /** Configures various graphics layer characteristics.
77 @param[in] UefiGfxPixelFormat This must be either
78 PixelBlueGreenRedReserved8BitPerColor
80 PixelRedGreenBlueReserved8BitPerColor
81 @param[in] HRes Horizontal resolution of the graphics layer.
82 @param[in] VRes Vertical resolution of the graphics layer.
87 IN CONST EFI_GRAPHICS_PIXEL_FORMAT UefiGfxPixelFormat
,
94 // Disable the graphics layer before configuring any settings.
95 LayerGraphicsDisable ();
97 // Setup graphics layer size.
98 MmioWrite32 (DP_BASE
+ DP_DE_LG_IN_SIZE
, FRAME_IN_SIZE (HRes
, VRes
));
100 // Setup graphics layer composition size.
101 MmioWrite32 (DP_BASE
+ DP_DE_LG_CMP_SIZE
, FRAME_CMP_SIZE (HRes
, VRes
));
103 // Setup memory stride (total visible pixels on a line * 4).
104 MmioWrite32 (DP_BASE
+ DP_DE_LG_H_STRIDE
, (HRes
* sizeof (UINT32
)));
108 // In PixelBlueGreenRedReserved8BitPerColor format, byte 0 represents blue,
109 // byte 1 represents green, byte 2 represents red, and byte 3 is reserved
110 // which is equivalent to XRGB format of the DP500/DP550/DP650. Whereas
111 // PixelRedGreenBlueReserved8BitPerColor is equivalent to XBGR of the
112 // DP500/DP550/DP650.
113 if (UefiGfxPixelFormat
== PixelBlueGreenRedReserved8BitPerColor
) {
114 PixelFormat
= (mDpDeviceId
== MALIDP_500
) ? DP_PIXEL_FORMAT_DP500_XRGB_8888
115 : DP_PIXEL_FORMAT_XRGB_8888
;
117 PixelFormat
= (mDpDeviceId
== MALIDP_500
) ? DP_PIXEL_FORMAT_DP500_XBGR_8888
118 : DP_PIXEL_FORMAT_XBGR_8888
;
121 MmioWrite32 (DP_BASE
+ DP_DE_LG_FORMAT
, PixelFormat
);
123 // Enable graphics layer.
124 LayerGraphicsEnable ();
127 /** Configure timing information of the display.
129 @param[in] Horizontal Pointer to horizontal timing parameters.
130 (Resolution, Sync, Back porch, Front porch)
131 @param[in] Vertical Pointer to vertical timing parameters.
132 (Resolution, Sync, Back porch, Front porch)
136 SetDisplayEngineTiming (
137 IN CONST SCAN_TIMINGS
* CONST Horizontal
,
138 IN CONST SCAN_TIMINGS
* CONST Vertical
143 UINTN RegSyncControl
;
144 UINTN RegHVActiveSize
;
146 if (mDpDeviceId
== MALIDP_500
) {
147 // MALI DP500 timing registers.
148 RegHIntervals
= DP_BASE
+ DP_DE_DP500_H_INTERVALS
;
149 RegVIntervals
= DP_BASE
+ DP_DE_DP500_V_INTERVALS
;
150 RegSyncControl
= DP_BASE
+ DP_DE_DP500_SYNC_CONTROL
;
151 RegHVActiveSize
= DP_BASE
+ DP_DE_DP500_HV_ACTIVESIZE
;
153 // MALI DP550/DP650 timing registers.
154 RegHIntervals
= DP_BASE
+ DP_DE_H_INTERVALS
;
155 RegVIntervals
= DP_BASE
+ DP_DE_V_INTERVALS
;
156 RegSyncControl
= DP_BASE
+ DP_DE_SYNC_CONTROL
;
157 RegHVActiveSize
= DP_BASE
+ DP_DE_HV_ACTIVESIZE
;
160 // Horizontal back porch and front porch.
163 H_INTERVALS (Horizontal
->FrontPorch
, Horizontal
->BackPorch
)
166 // Vertical back porch and front porch.
169 V_INTERVALS (Vertical
->FrontPorch
, Vertical
->BackPorch
)
172 // Sync control, Horizontal and Vertical sync.
175 SYNC_WIDTH (Horizontal
->Sync
, Vertical
->Sync
)
178 // Set up Horizontal and Vertical area size.
181 HV_ACTIVE (Horizontal
->Resolution
, Vertical
->Resolution
)
185 /** Return CORE_ID of the ARM Mali DP.
187 @retval 0xFFF No Mali DP found.
188 @retval 0x500 Mali DP core id for DP500.
189 @retval 0x550 Mali DP core id for DP550.
190 @retval 0x650 Mali DP core id for DP650.
199 // First check for DP500 as register offset for DP550/DP650 CORE_ID
200 // is beyond 3K/4K register space of the DP500.
201 DpCoreId
= MmioRead32 (DP_BASE
+ DP_DE_DP500_CORE_ID
);
202 DpCoreId
>>= DP_DE_DP500_CORE_ID_SHIFT
;
204 if (DpCoreId
== MALIDP_500
) {
208 // Check for DP550 or DP650.
209 DpCoreId
= MmioRead32 (DP_BASE
+ DP_DC_CORE_ID
);
210 DpCoreId
>>= DP_DC_CORE_ID_SHIFT
;
212 if ((DpCoreId
== MALIDP_550
) || (DpCoreId
== MALIDP_650
)) {
216 return MALIDP_NOT_PRESENT
;
219 /** Check for presence of MALI.
221 This function returns success if the platform implements
222 DP500/DP550/DP650 ARM Mali display processor.
224 @retval EFI_SUCCESS DP500/DP550/DP650 display processor found
226 @retval EFI_NOT_FOUND DP500/DP550/DP650 display processor not found
233 "Probing ARM Mali DP500/DP550/DP650 at base address 0x%p\n",
237 if (mDpDeviceId
== 0) {
238 mDpDeviceId
= ArmMaliDpGetCoreId ();
241 if (mDpDeviceId
== MALIDP_NOT_PRESENT
) {
242 DEBUG ((DEBUG_WARN
, "ARM Mali DP not found...\n"));
243 return EFI_NOT_FOUND
;
246 DEBUG ((DEBUG_WARN
, "Found ARM Mali DP %x\n", mDpDeviceId
));
250 /** Initialize platform display.
252 @param[in] FrameBaseAddress Address of the frame buffer.
254 @retval EFI_SUCCESS Display initialization successful.
255 @retval !(EFI_SUCCESS) Display initialization failure.
259 IN CONST EFI_PHYSICAL_ADDRESS FrameBaseAddress
262 DEBUG ((DEBUG_WARN
, "Framebuffer base address = %p\n", FrameBaseAddress
));
264 if (mDpDeviceId
== 0) {
265 mDpDeviceId
= ArmMaliDpGetCoreId ();
268 if (mDpDeviceId
== MALIDP_NOT_PRESENT
) {
269 DEBUG ((DEBUG_ERROR
, "ARM Mali DP initialization failed,"
270 "no ARM Mali DP present\n"));
271 return EFI_NOT_FOUND
;
274 // We are using graphics layer of the Mali DP as a main framebuffer.
275 LayerGraphicsSetFrame (FrameBaseAddress
);
280 /** Set ARM Mali DP in cofiguration mode.
282 The ARM Mali DP must be in the configuration mode for
283 configuration of the H_INTERVALS, V_INTERVALS, SYNC_CONTROL
288 SetConfigurationMode (VOID
)
290 // Request configuration Mode.
291 if (mDpDeviceId
== MALIDP_500
) {
292 MmioOr32 (DP_BASE
+ DP_DE_DP500_CONTROL
, DP_DE_DP500_CONTROL_CONFIG_REQ
);
294 MmioOr32 (DP_BASE
+ DP_DC_CONTROL
, DP_DC_CONTROL_CM_ACTIVE
);
298 /** Set ARM Mali DP in normal mode.
300 Normal mode is the main operating mode of the display processor
301 in which display layer data is fetched from framebuffer and
308 // Disable configuration Mode.
309 if (mDpDeviceId
== MALIDP_500
) {
310 MmioAnd32 (DP_BASE
+ DP_DE_DP500_CONTROL
, ~DP_DE_DP500_CONTROL_CONFIG_REQ
);
312 MmioAnd32 (DP_BASE
+ DP_DC_CONTROL
, ~DP_DC_CONTROL_CM_ACTIVE
);
316 /** Set the global configuration valid flag.
318 Any new configuration parameters written to the display engine are not
319 activated until the global configuration valid flag is set in the
320 CONFIG_VALID register.
324 SetConfigValid (VOID
)
326 if (mDpDeviceId
== MALIDP_500
) {
327 MmioOr32 (DP_BASE
+ DP_DP500_CONFIG_VALID
, DP_DC_CONFIG_VALID
);
329 MmioOr32 (DP_BASE
+ DP_DC_CONFIG_VALID
, DP_DC_CONFIG_VALID
);
333 /** Set requested mode of the display.
335 @param[in] ModeNumber Display mode number.
337 @retval EFI_SUCCESS Display mode set successful.
338 @retval EFI_DEVICE_ERROR Display mode not found/supported.
342 IN CONST UINT32 ModeNumber
346 SCAN_TIMINGS
*Horizontal
;
347 SCAN_TIMINGS
*Vertical
;
349 EFI_GRAPHICS_OUTPUT_MODE_INFORMATION ModeInfo
;
351 // Get the display mode timings and other relevant information.
352 Status
= LcdPlatformGetTimings (
357 if (EFI_ERROR (Status
)) {
358 ASSERT_EFI_ERROR (Status
);
362 ASSERT (Horizontal
!= NULL
);
363 ASSERT (Vertical
!= NULL
);
365 // Get the pixel format information.
366 Status
= LcdPlatformQueryMode (ModeNumber
, &ModeInfo
);
367 if (EFI_ERROR (Status
)) {
368 ASSERT_EFI_ERROR (Status
);
372 // Request configuration mode.
373 SetConfigurationMode ();
375 // Configure the graphics layer.
376 LayerGraphicsConfig (
377 ModeInfo
.PixelFormat
,
378 Horizontal
->Resolution
,
382 // Set the display engine timings.
383 SetDisplayEngineTiming (Horizontal
, Vertical
);
385 // After configuration, set Mali DP in normal mode.
388 // Any parameters written to the display engine are not activated until
389 // CONFIG_VALID is set.
395 /** This function de-initializes the display.
401 // Disable graphics layer.
402 LayerGraphicsDisable ();