diff options
Diffstat (limited to 'Documentation/gpu/amdgpu/display/programming-model-dcn.rst')
-rw-r--r-- | Documentation/gpu/amdgpu/display/programming-model-dcn.rst | 162 |
1 files changed, 162 insertions, 0 deletions
diff --git a/Documentation/gpu/amdgpu/display/programming-model-dcn.rst b/Documentation/gpu/amdgpu/display/programming-model-dcn.rst new file mode 100644 index 000000000000..c1b48d49fb0b --- /dev/null +++ b/Documentation/gpu/amdgpu/display/programming-model-dcn.rst @@ -0,0 +1,162 @@ +==================== +DC Programming Model +==================== + +In the :ref:`Display Core Next (DCN) <dcn_overview>` and :ref:`DCN Block +<dcn_blocks>` pages, you learned about the hardware components and how they +interact with each other. On this page, the focus is shifted to the display +code architecture. Hence, it is reasonable to remind the reader that the code +in DC is shared with other OSes; for this reason, DC provides a set of +abstractions and operations to connect different APIs with the hardware +configuration. See DC as a service available for a Display Manager (amdgpu_dm) +to access and configure DCN/DCE hardware (DCE is also part of DC, but for +simplicity's sake, this documentation only examines DCN). + +.. note:: + For this page, we will use the term GPU to refers to dGPU and APU. + +Overview +======== + +From the display hardware perspective, it is plausible to expect that if a +problem is well-defined, it will probably be implemented at the hardware level. +On the other hand, when there are multiple ways of achieving something without +a very well-defined scope, the solution is usually implemented as a policy at +the DC level. In other words, some policies are defined in the DC core +(resource management, power optimization, image quality, etc.), and the others +implemented in hardware are enabled via DC configuration. + +In terms of hardware management, DCN has multiple instances of the same block +(e.g., HUBP, DPP, MPC, etc), and during the driver execution, it might be +necessary to use some of these instances. The core has policies in place for +handling those instances. Regarding resource management, the DC objective is +quite simple: minimize the hardware shuffle when the driver performs some +actions. When the state changes from A to B, the transition is considered +easier to maneuver if the hardware resource is still used for the same set of +driver objects. Usually, adding and removing a resource to a `pipe_ctx` (more +details below) is not a problem; however, moving a resource from one `pipe_ctx` +to another should be avoided. + +Another area of influence for DC is power optimization, which has a myriad of +arrangement possibilities. In some way, just displaying an image via DCN should +be relatively straightforward; however, showing it with the best power +footprint is more desirable, but it has many associated challenges. +Unfortunately, there is no straight-forward analytic way to determine if a +configuration is the best one for the context due to the enormous variety of +variables related to this problem (e.g., many different DCN/DCE hardware +versions, different displays configurations, etc.) for this reason DC +implements a dedicated library for trying some configuration and verify if it +is possible to support it or not. This type of policy is extremely complex to +create and maintain, and amdgpu driver relies on Display Mode Library (DML) to +generate the best decisions. + +In summary, DC must deal with the complexity of handling multiple scenarios and +determine policies to manage them. All of the above information is conveyed to +give the reader some idea about the complexity of driving a display from the +driver's perspective. This page hopes to allow the reader to better navigate +over the amdgpu display code. + +Display Driver Architecture Overview +==================================== + +The diagram below provides an overview of the display driver architecture; +notice it illustrates the software layers adopted by DC: + +.. kernel-figure:: dc-components.svg + +The first layer of the diagram is the high-level DC API represented by the +`dc.h` file; below it are two big blocks represented by Core and Link. Next is +the hardware configuration block; the main file describing it is +the`hw_sequencer.h`, where the implementation of the callbacks can be found in +the hardware sequencer folder. Almost at the end, you can see the block level +API (`dc/inc/hw`), which represents each DCN low-level block, such as HUBP, +DPP, MPC, OPTC, etc. Notice on the left side of the diagram that we have a +different set of layers representing the interaction with the DMUB +microcontroller. + +Basic Objects +------------- + +The below diagram outlines the basic display objects. In particular, pay +attention to the names in the boxes since they represent a data structure in +the driver: + +.. kernel-figure:: dc-arch-overview.svg + +Let's start with the central block in the image, `dc`. The `dc` struct is +initialized per GPU; for example, one GPU has one `dc` instance, two GPUs have +two `dc` instances, and so forth. In other words we have one 'dc' per 'amdgpu' +instance. In some ways, this object behaves like the `Singleton` pattern. + +After the `dc` block in the diagram, you can see the `dc_link` component, which +is a low-level abstraction for the connector. One interesting aspect of the +image is that connectors are not part of the DCN block; they are defined by the +platform/board and not by the SoC. The `dc_link` struct is the high-level data +container with information such as connected sinks, connection status, signal +types, etc. After `dc_link`, there is the `dc_sink`, which is the object that +represents the connected display. + +.. note:: + For historical reasons, we used the name `dc_link`, which gives the + wrong impression that this abstraction only deals with physical connections + that the developer can easily manipulate. However, this also covers + conections like eDP or cases where the output is connected to other devices. + +There are two structs that are not represented in the diagram since they were +elaborated in the DCN overview page (check the DCN block diagram :ref:`Display +Core Next (DCN) <dcn_overview>`); still, it is worth bringing back for this +overview which is `dc_stream` and `dc_state`. The `dc_stream` stores many +properties associated with the data transmission, but most importantly, it +represents the data flow from the connector to the display. Next we have +`dc_state`, which represents the logic state within the hardware at the moment; +`dc_state` is composed of `dc_stream` and `dc_plane`. The `dc_stream` is the DC +version of `drm_crtc` and represents the post-blending pipeline. + +Speaking of the `dc_plane` data structure (first part of the diagram), you can +think about it as an abstraction similar to `drm_plane` that represents the +pre-blending portion of the pipeline. This image was probably processed by GFX +and is ready to be composited under a `dc_stream`. Normally, the driver may +have one or more `dc_plane` connected to the same `dc_stream`, which defines a +composition at the DC level. + +Basic Operations +---------------- + +Now that we have covered the basic objects, it is time to examine some of the +basic hardware/software operations. Let's start with the `dc_create()` +function, which directly works with the `dc` data struct; this function behaves +like a constructor responsible for the basic software initialization and +preparing for enabling other parts of the API. It is important to highlight +that this operation does not touch any hardware configuration; it is only a +software initialization. + +Next, we have the `dc_hardware_init()`, which also relies on the `dc` data +struct. Its main function is to put the hardware in a valid state. It is worth +highlighting that the hardware might initialize in an unknown state, and it is +a requirement to put it in a valid state; this function has multiple callbacks +for the hardware-specific initialization, whereas `dc_hardware_init` does the +hardware initialization and is the first point where we touch hardware. + +The `dc_get_link_at_index` is an operation that depends on the `dc_link` data +structure. This function retrieves and enumerates all the `dc_links` available +on the device; this is required since this information is not part of the SoC +definition but depends on the board configuration. As soon as the `dc_link` is +initialized, it is useful to figure out if any of them are already connected to +the display by using the `dc_link_detect()` function. After the driver figures +out if any display is connected to the device, the challenging phase starts: +configuring the monitor to show something. Nonetheless, dealing with the ideal +configuration is not a DC task since this is the Display Manager (`amdgpu_dm`) +responsibility which in turn is responsible for dealing with the atomic +commits. The only interface DC provides to the configuration phase is the +function `dc_validate_with_context` that receives the configuration information +and, based on that, validates whether the hardware can support it or not. It is +important to add that even if the display supports some specific configuration, +it does not mean the DCN hardware can support it. + +After the DM and DC agree upon the configuration, the stream configuration +phase starts. This task activates one or more `dc_stream` at this phase, and in +the best-case scenario, you might be able to turn the display on with a black +screen (it does not show anything yet since it does not have any plane +associated with it). The final step would be to call the +`dc_update_planes_and_stream,` which will add or remove planes. + |