linux/drivers/gpu/drm/amd/display/dc/bios/command_table_helper.c
<<
>>
Prefs
   1/*
   2 * Copyright 2012-15 Advanced Micro Devices, Inc.
   3 *
   4 * Permission is hereby granted, free of charge, to any person obtaining a
   5 * copy of this software and associated documentation files (the "Software"),
   6 * to deal in the Software without restriction, including without limitation
   7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
   8 * and/or sell copies of the Software, and to permit persons to whom the
   9 * Software is furnished to do so, subject to the following conditions:
  10 *
  11 * The above copyright notice and this permission notice shall be included in
  12 * all copies or substantial portions of the Software.
  13 *
  14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
  17 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
  18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
  19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
  20 * OTHER DEALINGS IN THE SOFTWARE.
  21 *
  22 * Authors: AMD
  23 *
  24 */
  25
  26#include "dm_services.h"
  27
  28#include "atom.h"
  29
  30#include "include/bios_parser_types.h"
  31
  32#include "command_table_helper.h"
  33
  34bool dal_bios_parser_init_cmd_tbl_helper(
  35        const struct command_table_helper **h,
  36        enum dce_version dce)
  37{
  38        switch (dce) {
  39#if defined(CONFIG_DRM_AMD_DC_SI)
  40        case DCE_VERSION_6_0:
  41        case DCE_VERSION_6_1:
  42        case DCE_VERSION_6_4:
  43                *h = dal_cmd_tbl_helper_dce60_get_table();
  44                return true;
  45#endif
  46
  47        case DCE_VERSION_8_0:
  48        case DCE_VERSION_8_1:
  49        case DCE_VERSION_8_3:
  50                *h = dal_cmd_tbl_helper_dce80_get_table();
  51                return true;
  52
  53        case DCE_VERSION_10_0:
  54                *h = dal_cmd_tbl_helper_dce110_get_table();
  55                return true;
  56
  57        case DCE_VERSION_11_0:
  58                *h = dal_cmd_tbl_helper_dce110_get_table();
  59                return true;
  60
  61        case DCE_VERSION_11_2:
  62        case DCE_VERSION_11_22:
  63                *h = dal_cmd_tbl_helper_dce112_get_table();
  64                return true;
  65
  66        default:
  67                /* Unsupported DCE */
  68                BREAK_TO_DEBUGGER();
  69                return false;
  70        }
  71}
  72
  73/* real implementations */
  74
  75bool dal_cmd_table_helper_controller_id_to_atom(
  76        enum controller_id id,
  77        uint8_t *atom_id)
  78{
  79        if (atom_id == NULL) {
  80                BREAK_TO_DEBUGGER();
  81                return false;
  82        }
  83
  84        switch (id) {
  85        case CONTROLLER_ID_D0:
  86                *atom_id = ATOM_CRTC1;
  87                return true;
  88        case CONTROLLER_ID_D1:
  89                *atom_id = ATOM_CRTC2;
  90                return true;
  91        case CONTROLLER_ID_D2:
  92                *atom_id = ATOM_CRTC3;
  93                return true;
  94        case CONTROLLER_ID_D3:
  95                *atom_id = ATOM_CRTC4;
  96                return true;
  97        case CONTROLLER_ID_D4:
  98                *atom_id = ATOM_CRTC5;
  99                return true;
 100        case CONTROLLER_ID_D5:
 101                *atom_id = ATOM_CRTC6;
 102                return true;
 103        case CONTROLLER_ID_UNDERLAY0:
 104                *atom_id = ATOM_UNDERLAY_PIPE0;
 105                return true;
 106        case CONTROLLER_ID_UNDEFINED:
 107                *atom_id = ATOM_CRTC_INVALID;
 108                return true;
 109        default:
 110                /* Wrong controller id */
 111                BREAK_TO_DEBUGGER();
 112                return false;
 113        }
 114}
 115
 116/**
 117 * dal_cmd_table_helper_transmitter_bp_to_atom - Translate the Transmitter to the
 118 *                                    corresponding ATOM BIOS value
 119 * @t: transmitter
 120 * returns: output digitalTransmitter
 121 *    // =00: Digital Transmitter1 ( UNIPHY linkAB )
 122 *    // =01: Digital Transmitter2 ( UNIPHY linkCD )
 123 *    // =02: Digital Transmitter3 ( UNIPHY linkEF )
 124 */
 125uint8_t dal_cmd_table_helper_transmitter_bp_to_atom(
 126        enum transmitter t)
 127{
 128        switch (t) {
 129        case TRANSMITTER_UNIPHY_A:
 130        case TRANSMITTER_UNIPHY_B:
 131        case TRANSMITTER_TRAVIS_LCD:
 132                return 0;
 133        case TRANSMITTER_UNIPHY_C:
 134        case TRANSMITTER_UNIPHY_D:
 135                return 1;
 136        case TRANSMITTER_UNIPHY_E:
 137        case TRANSMITTER_UNIPHY_F:
 138                return 2;
 139        default:
 140                /* Invalid Transmitter Type! */
 141                BREAK_TO_DEBUGGER();
 142                return 0;
 143        }
 144}
 145
 146uint32_t dal_cmd_table_helper_encoder_mode_bp_to_atom(
 147        enum signal_type s,
 148        bool enable_dp_audio)
 149{
 150        switch (s) {
 151        case SIGNAL_TYPE_DVI_SINGLE_LINK:
 152        case SIGNAL_TYPE_DVI_DUAL_LINK:
 153                return ATOM_ENCODER_MODE_DVI;
 154        case SIGNAL_TYPE_HDMI_TYPE_A:
 155                return ATOM_ENCODER_MODE_HDMI;
 156        case SIGNAL_TYPE_LVDS:
 157                return ATOM_ENCODER_MODE_LVDS;
 158        case SIGNAL_TYPE_EDP:
 159        case SIGNAL_TYPE_DISPLAY_PORT_MST:
 160        case SIGNAL_TYPE_DISPLAY_PORT:
 161        case SIGNAL_TYPE_VIRTUAL:
 162                if (enable_dp_audio)
 163                        return ATOM_ENCODER_MODE_DP_AUDIO;
 164                else
 165                        return ATOM_ENCODER_MODE_DP;
 166        case SIGNAL_TYPE_RGB:
 167                return ATOM_ENCODER_MODE_CRT;
 168        default:
 169                return ATOM_ENCODER_MODE_CRT;
 170        }
 171}
 172
 173void dal_cmd_table_helper_assign_control_parameter(
 174        const struct command_table_helper *h,
 175        struct bp_encoder_control *control,
 176        DIG_ENCODER_CONTROL_PARAMETERS_V2 *ctrl_param)
 177{
 178        /* there are three transmitter blocks, each one has two links 4-lanes
 179         * each, A+B, C+D, E+F, Uniphy A, C and E are enumerated as link 0 in
 180         * each transmitter block B, D and F as link 1, third transmitter block
 181         * has non splitable links (UniphyE and UniphyF can not be configured
 182         * separately to drive two different streams)
 183         */
 184        if ((control->transmitter == TRANSMITTER_UNIPHY_B) ||
 185                (control->transmitter == TRANSMITTER_UNIPHY_D) ||
 186                (control->transmitter == TRANSMITTER_UNIPHY_F)) {
 187                /* Bit2: Link Select
 188                 * =0: PHY linkA/C/E
 189                 * =1: PHY linkB/D/F
 190                 */
 191                ctrl_param->acConfig.ucLinkSel = 1;
 192        }
 193
 194        /* Bit[4:3]: Transmitter Selection
 195         * =00: Digital Transmitter1 ( UNIPHY linkAB )
 196         * =01: Digital Transmitter2 ( UNIPHY linkCD )
 197         * =02: Digital Transmitter3 ( UNIPHY linkEF )
 198         * =03: Reserved
 199         */
 200        ctrl_param->acConfig.ucTransmitterSel =
 201                (uint8_t)(h->transmitter_bp_to_atom(control->transmitter));
 202
 203        /* We need to convert from KHz units into 10KHz units */
 204        ctrl_param->ucAction = h->encoder_action_to_atom(control->action);
 205        ctrl_param->usPixelClock = cpu_to_le16((uint16_t)(control->pixel_clock / 10));
 206        ctrl_param->ucEncoderMode =
 207                (uint8_t)(h->encoder_mode_bp_to_atom(
 208                        control->signal, control->enable_dp_audio));
 209        ctrl_param->ucLaneNum = (uint8_t)(control->lanes_number);
 210}
 211
 212bool dal_cmd_table_helper_clock_source_id_to_ref_clk_src(
 213        enum clock_source_id id,
 214        uint32_t *ref_clk_src_id)
 215{
 216        if (ref_clk_src_id == NULL) {
 217                BREAK_TO_DEBUGGER();
 218                return false;
 219        }
 220
 221        switch (id) {
 222        case CLOCK_SOURCE_ID_PLL1:
 223                *ref_clk_src_id = ENCODER_REFCLK_SRC_P1PLL;
 224                return true;
 225        case CLOCK_SOURCE_ID_PLL2:
 226                *ref_clk_src_id = ENCODER_REFCLK_SRC_P2PLL;
 227                return true;
 228        case CLOCK_SOURCE_ID_DCPLL:
 229                *ref_clk_src_id = ENCODER_REFCLK_SRC_DCPLL;
 230                return true;
 231        case CLOCK_SOURCE_ID_EXTERNAL:
 232                *ref_clk_src_id = ENCODER_REFCLK_SRC_EXTCLK;
 233                return true;
 234        case CLOCK_SOURCE_ID_UNDEFINED:
 235                *ref_clk_src_id = ENCODER_REFCLK_SRC_INVALID;
 236                return true;
 237        default:
 238                /* Unsupported clock source id */
 239                BREAK_TO_DEBUGGER();
 240                return false;
 241        }
 242}
 243
 244uint8_t dal_cmd_table_helper_encoder_id_to_atom(
 245        enum encoder_id id)
 246{
 247        switch (id) {
 248        case ENCODER_ID_INTERNAL_LVDS:
 249                return ENCODER_OBJECT_ID_INTERNAL_LVDS;
 250        case ENCODER_ID_INTERNAL_TMDS1:
 251                return ENCODER_OBJECT_ID_INTERNAL_TMDS1;
 252        case ENCODER_ID_INTERNAL_TMDS2:
 253                return ENCODER_OBJECT_ID_INTERNAL_TMDS2;
 254        case ENCODER_ID_INTERNAL_DAC1:
 255                return ENCODER_OBJECT_ID_INTERNAL_DAC1;
 256        case ENCODER_ID_INTERNAL_DAC2:
 257                return ENCODER_OBJECT_ID_INTERNAL_DAC2;
 258        case ENCODER_ID_INTERNAL_LVTM1:
 259                return ENCODER_OBJECT_ID_INTERNAL_LVTM1;
 260        case ENCODER_ID_INTERNAL_HDMI:
 261                return ENCODER_OBJECT_ID_HDMI_INTERNAL;
 262        case ENCODER_ID_EXTERNAL_TRAVIS:
 263                return ENCODER_OBJECT_ID_TRAVIS;
 264        case ENCODER_ID_EXTERNAL_NUTMEG:
 265                return ENCODER_OBJECT_ID_NUTMEG;
 266        case ENCODER_ID_INTERNAL_KLDSCP_TMDS1:
 267                return ENCODER_OBJECT_ID_INTERNAL_KLDSCP_TMDS1;
 268        case ENCODER_ID_INTERNAL_KLDSCP_DAC1:
 269                return ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DAC1;
 270        case ENCODER_ID_INTERNAL_KLDSCP_DAC2:
 271                return ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DAC2;
 272        case ENCODER_ID_EXTERNAL_MVPU_FPGA:
 273                return ENCODER_OBJECT_ID_MVPU_FPGA;
 274        case ENCODER_ID_INTERNAL_DDI:
 275                return ENCODER_OBJECT_ID_INTERNAL_DDI;
 276        case ENCODER_ID_INTERNAL_UNIPHY:
 277                return ENCODER_OBJECT_ID_INTERNAL_UNIPHY;
 278        case ENCODER_ID_INTERNAL_KLDSCP_LVTMA:
 279                return ENCODER_OBJECT_ID_INTERNAL_KLDSCP_LVTMA;
 280        case ENCODER_ID_INTERNAL_UNIPHY1:
 281                return ENCODER_OBJECT_ID_INTERNAL_UNIPHY1;
 282        case ENCODER_ID_INTERNAL_UNIPHY2:
 283                return ENCODER_OBJECT_ID_INTERNAL_UNIPHY2;
 284        case ENCODER_ID_INTERNAL_UNIPHY3:
 285                return ENCODER_OBJECT_ID_INTERNAL_UNIPHY3;
 286        case ENCODER_ID_INTERNAL_WIRELESS:
 287                return ENCODER_OBJECT_ID_INTERNAL_VCE;
 288        case ENCODER_ID_UNKNOWN:
 289                return ENCODER_OBJECT_ID_NONE;
 290        default:
 291                /* Invalid encoder id */
 292                BREAK_TO_DEBUGGER();
 293                return ENCODER_OBJECT_ID_NONE;
 294        }
 295}
 296