linux/drivers/video/exynos/exynos_dp_reg.c
<<
>>
Prefs
   1/*
   2 * Samsung DP (Display port) register interface driver.
   3 *
   4 * Copyright (C) 2012 Samsung Electronics Co., Ltd.
   5 * Author: Jingoo Han <jg1.han@samsung.com>
   6 *
   7 * This program is free software; you can redistribute it and/or modify it
   8 * under the terms of the GNU General Public License as published by the
   9 * Free Software Foundation; either version 2 of the License, or (at your
  10 * option) any later version.
  11 */
  12
  13#include <linux/device.h>
  14#include <linux/io.h>
  15#include <linux/delay.h>
  16
  17#include <video/exynos_dp.h>
  18
  19#include "exynos_dp_core.h"
  20#include "exynos_dp_reg.h"
  21
  22#define COMMON_INT_MASK_1 (0)
  23#define COMMON_INT_MASK_2 (0)
  24#define COMMON_INT_MASK_3 (0)
  25#define COMMON_INT_MASK_4 (0)
  26#define INT_STA_MASK (0)
  27
  28void exynos_dp_enable_video_mute(struct exynos_dp_device *dp, bool enable)
  29{
  30        u32 reg;
  31
  32        if (enable) {
  33                reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_1);
  34                reg |= HDCP_VIDEO_MUTE;
  35                writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_1);
  36        } else {
  37                reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_1);
  38                reg &= ~HDCP_VIDEO_MUTE;
  39                writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_1);
  40        }
  41}
  42
  43void exynos_dp_stop_video(struct exynos_dp_device *dp)
  44{
  45        u32 reg;
  46
  47        reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_1);
  48        reg &= ~VIDEO_EN;
  49        writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_1);
  50}
  51
  52void exynos_dp_lane_swap(struct exynos_dp_device *dp, bool enable)
  53{
  54        u32 reg;
  55
  56        if (enable)
  57                reg = LANE3_MAP_LOGIC_LANE_0 | LANE2_MAP_LOGIC_LANE_1 |
  58                        LANE1_MAP_LOGIC_LANE_2 | LANE0_MAP_LOGIC_LANE_3;
  59        else
  60                reg = LANE3_MAP_LOGIC_LANE_3 | LANE2_MAP_LOGIC_LANE_2 |
  61                        LANE1_MAP_LOGIC_LANE_1 | LANE0_MAP_LOGIC_LANE_0;
  62
  63        writel(reg, dp->reg_base + EXYNOS_DP_LANE_MAP);
  64}
  65
  66void exynos_dp_init_analog_param(struct exynos_dp_device *dp)
  67{
  68        u32 reg;
  69
  70        reg = TX_TERMINAL_CTRL_50_OHM;
  71        writel(reg, dp->reg_base + EXYNOS_DP_ANALOG_CTL_1);
  72
  73        reg = SEL_24M | TX_DVDD_BIT_1_0625V;
  74        writel(reg, dp->reg_base + EXYNOS_DP_ANALOG_CTL_2);
  75
  76        reg = DRIVE_DVDD_BIT_1_0625V | VCO_BIT_600_MICRO;
  77        writel(reg, dp->reg_base + EXYNOS_DP_ANALOG_CTL_3);
  78
  79        reg = PD_RING_OSC | AUX_TERMINAL_CTRL_50_OHM |
  80                TX_CUR1_2X | TX_CUR_16_MA;
  81        writel(reg, dp->reg_base + EXYNOS_DP_PLL_FILTER_CTL_1);
  82
  83        reg = CH3_AMP_400_MV | CH2_AMP_400_MV |
  84                CH1_AMP_400_MV | CH0_AMP_400_MV;
  85        writel(reg, dp->reg_base + EXYNOS_DP_TX_AMP_TUNING_CTL);
  86}
  87
  88void exynos_dp_init_interrupt(struct exynos_dp_device *dp)
  89{
  90        /* Set interrupt pin assertion polarity as high */
  91        writel(INT_POL, dp->reg_base + EXYNOS_DP_INT_CTL);
  92
  93        /* Clear pending regisers */
  94        writel(0xff, dp->reg_base + EXYNOS_DP_COMMON_INT_STA_1);
  95        writel(0x4f, dp->reg_base + EXYNOS_DP_COMMON_INT_STA_2);
  96        writel(0xe0, dp->reg_base + EXYNOS_DP_COMMON_INT_STA_3);
  97        writel(0xe7, dp->reg_base + EXYNOS_DP_COMMON_INT_STA_4);
  98        writel(0x63, dp->reg_base + EXYNOS_DP_INT_STA);
  99
 100        /* 0:mask,1: unmask */
 101        writel(0x00, dp->reg_base + EXYNOS_DP_COMMON_INT_MASK_1);
 102        writel(0x00, dp->reg_base + EXYNOS_DP_COMMON_INT_MASK_2);
 103        writel(0x00, dp->reg_base + EXYNOS_DP_COMMON_INT_MASK_3);
 104        writel(0x00, dp->reg_base + EXYNOS_DP_COMMON_INT_MASK_4);
 105        writel(0x00, dp->reg_base + EXYNOS_DP_INT_STA_MASK);
 106}
 107
 108void exynos_dp_reset(struct exynos_dp_device *dp)
 109{
 110        u32 reg;
 111
 112        exynos_dp_stop_video(dp);
 113        exynos_dp_enable_video_mute(dp, 0);
 114
 115        reg = MASTER_VID_FUNC_EN_N | SLAVE_VID_FUNC_EN_N |
 116                AUD_FIFO_FUNC_EN_N | AUD_FUNC_EN_N |
 117                HDCP_FUNC_EN_N | SW_FUNC_EN_N;
 118        writel(reg, dp->reg_base + EXYNOS_DP_FUNC_EN_1);
 119
 120        reg = SSC_FUNC_EN_N | AUX_FUNC_EN_N |
 121                SERDES_FIFO_FUNC_EN_N |
 122                LS_CLK_DOMAIN_FUNC_EN_N;
 123        writel(reg, dp->reg_base + EXYNOS_DP_FUNC_EN_2);
 124
 125        usleep_range(20, 30);
 126
 127        exynos_dp_lane_swap(dp, 0);
 128
 129        writel(0x0, dp->reg_base + EXYNOS_DP_SYS_CTL_1);
 130        writel(0x40, dp->reg_base + EXYNOS_DP_SYS_CTL_2);
 131        writel(0x0, dp->reg_base + EXYNOS_DP_SYS_CTL_3);
 132        writel(0x0, dp->reg_base + EXYNOS_DP_SYS_CTL_4);
 133
 134        writel(0x0, dp->reg_base + EXYNOS_DP_PKT_SEND_CTL);
 135        writel(0x0, dp->reg_base + EXYNOS_DP_HDCP_CTL);
 136
 137        writel(0x5e, dp->reg_base + EXYNOS_DP_HPD_DEGLITCH_L);
 138        writel(0x1a, dp->reg_base + EXYNOS_DP_HPD_DEGLITCH_H);
 139
 140        writel(0x10, dp->reg_base + EXYNOS_DP_LINK_DEBUG_CTL);
 141
 142        writel(0x0, dp->reg_base + EXYNOS_DP_PHY_TEST);
 143
 144        writel(0x0, dp->reg_base + EXYNOS_DP_VIDEO_FIFO_THRD);
 145        writel(0x20, dp->reg_base + EXYNOS_DP_AUDIO_MARGIN);
 146
 147        writel(0x4, dp->reg_base + EXYNOS_DP_M_VID_GEN_FILTER_TH);
 148        writel(0x2, dp->reg_base + EXYNOS_DP_M_AUD_GEN_FILTER_TH);
 149
 150        writel(0x00000101, dp->reg_base + EXYNOS_DP_SOC_GENERAL_CTL);
 151}
 152
 153void exynos_dp_swreset(struct exynos_dp_device *dp)
 154{
 155        writel(RESET_DP_TX, dp->reg_base + EXYNOS_DP_TX_SW_RESET);
 156}
 157
 158void exynos_dp_config_interrupt(struct exynos_dp_device *dp)
 159{
 160        u32 reg;
 161
 162        /* 0: mask, 1: unmask */
 163        reg = COMMON_INT_MASK_1;
 164        writel(reg, dp->reg_base + EXYNOS_DP_COMMON_INT_MASK_1);
 165
 166        reg = COMMON_INT_MASK_2;
 167        writel(reg, dp->reg_base + EXYNOS_DP_COMMON_INT_MASK_2);
 168
 169        reg = COMMON_INT_MASK_3;
 170        writel(reg, dp->reg_base + EXYNOS_DP_COMMON_INT_MASK_3);
 171
 172        reg = COMMON_INT_MASK_4;
 173        writel(reg, dp->reg_base + EXYNOS_DP_COMMON_INT_MASK_4);
 174
 175        reg = INT_STA_MASK;
 176        writel(reg, dp->reg_base + EXYNOS_DP_INT_STA_MASK);
 177}
 178
 179enum pll_status exynos_dp_get_pll_lock_status(struct exynos_dp_device *dp)
 180{
 181        u32 reg;
 182
 183        reg = readl(dp->reg_base + EXYNOS_DP_DEBUG_CTL);
 184        if (reg & PLL_LOCK)
 185                return PLL_LOCKED;
 186        else
 187                return PLL_UNLOCKED;
 188}
 189
 190void exynos_dp_set_pll_power_down(struct exynos_dp_device *dp, bool enable)
 191{
 192        u32 reg;
 193
 194        if (enable) {
 195                reg = readl(dp->reg_base + EXYNOS_DP_PLL_CTL);
 196                reg |= DP_PLL_PD;
 197                writel(reg, dp->reg_base + EXYNOS_DP_PLL_CTL);
 198        } else {
 199                reg = readl(dp->reg_base + EXYNOS_DP_PLL_CTL);
 200                reg &= ~DP_PLL_PD;
 201                writel(reg, dp->reg_base + EXYNOS_DP_PLL_CTL);
 202        }
 203}
 204
 205void exynos_dp_set_analog_power_down(struct exynos_dp_device *dp,
 206                                enum analog_power_block block,
 207                                bool enable)
 208{
 209        u32 reg;
 210
 211        switch (block) {
 212        case AUX_BLOCK:
 213                if (enable) {
 214                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 215                        reg |= AUX_PD;
 216                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 217                } else {
 218                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 219                        reg &= ~AUX_PD;
 220                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 221                }
 222                break;
 223        case CH0_BLOCK:
 224                if (enable) {
 225                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 226                        reg |= CH0_PD;
 227                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 228                } else {
 229                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 230                        reg &= ~CH0_PD;
 231                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 232                }
 233                break;
 234        case CH1_BLOCK:
 235                if (enable) {
 236                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 237                        reg |= CH1_PD;
 238                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 239                } else {
 240                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 241                        reg &= ~CH1_PD;
 242                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 243                }
 244                break;
 245        case CH2_BLOCK:
 246                if (enable) {
 247                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 248                        reg |= CH2_PD;
 249                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 250                } else {
 251                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 252                        reg &= ~CH2_PD;
 253                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 254                }
 255                break;
 256        case CH3_BLOCK:
 257                if (enable) {
 258                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 259                        reg |= CH3_PD;
 260                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 261                } else {
 262                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 263                        reg &= ~CH3_PD;
 264                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 265                }
 266                break;
 267        case ANALOG_TOTAL:
 268                if (enable) {
 269                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 270                        reg |= DP_PHY_PD;
 271                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 272                } else {
 273                        reg = readl(dp->reg_base + EXYNOS_DP_PHY_PD);
 274                        reg &= ~DP_PHY_PD;
 275                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 276                }
 277                break;
 278        case POWER_ALL:
 279                if (enable) {
 280                        reg = DP_PHY_PD | AUX_PD | CH3_PD | CH2_PD |
 281                                CH1_PD | CH0_PD;
 282                        writel(reg, dp->reg_base + EXYNOS_DP_PHY_PD);
 283                } else {
 284                        writel(0x00, dp->reg_base + EXYNOS_DP_PHY_PD);
 285                }
 286                break;
 287        default:
 288                break;
 289        }
 290}
 291
 292void exynos_dp_init_analog_func(struct exynos_dp_device *dp)
 293{
 294        u32 reg;
 295        int timeout_loop = 0;
 296
 297        exynos_dp_set_analog_power_down(dp, POWER_ALL, 0);
 298
 299        reg = PLL_LOCK_CHG;
 300        writel(reg, dp->reg_base + EXYNOS_DP_COMMON_INT_STA_1);
 301
 302        reg = readl(dp->reg_base + EXYNOS_DP_DEBUG_CTL);
 303        reg &= ~(F_PLL_LOCK | PLL_LOCK_CTRL);
 304        writel(reg, dp->reg_base + EXYNOS_DP_DEBUG_CTL);
 305
 306        /* Power up PLL */
 307        if (exynos_dp_get_pll_lock_status(dp) == PLL_UNLOCKED) {
 308                exynos_dp_set_pll_power_down(dp, 0);
 309
 310                while (exynos_dp_get_pll_lock_status(dp) == PLL_UNLOCKED) {
 311                        timeout_loop++;
 312                        if (DP_TIMEOUT_LOOP_COUNT < timeout_loop) {
 313                                dev_err(dp->dev, "failed to get pll lock status\n");
 314                                return;
 315                        }
 316                        usleep_range(10, 20);
 317                }
 318        }
 319
 320        /* Enable Serdes FIFO function and Link symbol clock domain module */
 321        reg = readl(dp->reg_base + EXYNOS_DP_FUNC_EN_2);
 322        reg &= ~(SERDES_FIFO_FUNC_EN_N | LS_CLK_DOMAIN_FUNC_EN_N
 323                | AUX_FUNC_EN_N);
 324        writel(reg, dp->reg_base + EXYNOS_DP_FUNC_EN_2);
 325}
 326
 327void exynos_dp_init_hpd(struct exynos_dp_device *dp)
 328{
 329        u32 reg;
 330
 331        reg = HOTPLUG_CHG | HPD_LOST | PLUG;
 332        writel(reg, dp->reg_base + EXYNOS_DP_COMMON_INT_STA_4);
 333
 334        reg = INT_HPD;
 335        writel(reg, dp->reg_base + EXYNOS_DP_INT_STA);
 336
 337        reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_3);
 338        reg &= ~(F_HPD | HPD_CTRL);
 339        writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_3);
 340}
 341
 342void exynos_dp_reset_aux(struct exynos_dp_device *dp)
 343{
 344        u32 reg;
 345
 346        /* Disable AUX channel module */
 347        reg = readl(dp->reg_base + EXYNOS_DP_FUNC_EN_2);
 348        reg |= AUX_FUNC_EN_N;
 349        writel(reg, dp->reg_base + EXYNOS_DP_FUNC_EN_2);
 350}
 351
 352void exynos_dp_init_aux(struct exynos_dp_device *dp)
 353{
 354        u32 reg;
 355
 356        /* Clear inerrupts related to AUX channel */
 357        reg = RPLY_RECEIV | AUX_ERR;
 358        writel(reg, dp->reg_base + EXYNOS_DP_INT_STA);
 359
 360        exynos_dp_reset_aux(dp);
 361
 362        /* Disable AUX transaction H/W retry */
 363        reg = AUX_BIT_PERIOD_EXPECTED_DELAY(3) | AUX_HW_RETRY_COUNT_SEL(0)|
 364                AUX_HW_RETRY_INTERVAL_600_MICROSECONDS;
 365        writel(reg, dp->reg_base + EXYNOS_DP_AUX_HW_RETRY_CTL) ;
 366
 367        /* Receive AUX Channel DEFER commands equal to DEFFER_COUNT*64 */
 368        reg = DEFER_CTRL_EN | DEFER_COUNT(1);
 369        writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_DEFER_CTL);
 370
 371        /* Enable AUX channel module */
 372        reg = readl(dp->reg_base + EXYNOS_DP_FUNC_EN_2);
 373        reg &= ~AUX_FUNC_EN_N;
 374        writel(reg, dp->reg_base + EXYNOS_DP_FUNC_EN_2);
 375}
 376
 377int exynos_dp_get_plug_in_status(struct exynos_dp_device *dp)
 378{
 379        u32 reg;
 380
 381        reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_3);
 382        if (reg & HPD_STATUS)
 383                return 0;
 384
 385        return -EINVAL;
 386}
 387
 388void exynos_dp_enable_sw_function(struct exynos_dp_device *dp)
 389{
 390        u32 reg;
 391
 392        reg = readl(dp->reg_base + EXYNOS_DP_FUNC_EN_1);
 393        reg &= ~SW_FUNC_EN_N;
 394        writel(reg, dp->reg_base + EXYNOS_DP_FUNC_EN_1);
 395}
 396
 397int exynos_dp_start_aux_transaction(struct exynos_dp_device *dp)
 398{
 399        int reg;
 400        int retval = 0;
 401        int timeout_loop = 0;
 402
 403        /* Enable AUX CH operation */
 404        reg = readl(dp->reg_base + EXYNOS_DP_AUX_CH_CTL_2);
 405        reg |= AUX_EN;
 406        writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_CTL_2);
 407
 408        /* Is AUX CH command reply received? */
 409        reg = readl(dp->reg_base + EXYNOS_DP_INT_STA);
 410        while (!(reg & RPLY_RECEIV)) {
 411                timeout_loop++;
 412                if (DP_TIMEOUT_LOOP_COUNT < timeout_loop) {
 413                        dev_err(dp->dev, "AUX CH command reply failed!\n");
 414                        return -ETIMEDOUT;
 415                }
 416                reg = readl(dp->reg_base + EXYNOS_DP_INT_STA);
 417                usleep_range(10, 11);
 418        }
 419
 420        /* Clear interrupt source for AUX CH command reply */
 421        writel(RPLY_RECEIV, dp->reg_base + EXYNOS_DP_INT_STA);
 422
 423        /* Clear interrupt source for AUX CH access error */
 424        reg = readl(dp->reg_base + EXYNOS_DP_INT_STA);
 425        if (reg & AUX_ERR) {
 426                writel(AUX_ERR, dp->reg_base + EXYNOS_DP_INT_STA);
 427                return -EREMOTEIO;
 428        }
 429
 430        /* Check AUX CH error access status */
 431        reg = readl(dp->reg_base + EXYNOS_DP_AUX_CH_STA);
 432        if ((reg & AUX_STATUS_MASK) != 0) {
 433                dev_err(dp->dev, "AUX CH error happens: %d\n\n",
 434                        reg & AUX_STATUS_MASK);
 435                return -EREMOTEIO;
 436        }
 437
 438        return retval;
 439}
 440
 441int exynos_dp_write_byte_to_dpcd(struct exynos_dp_device *dp,
 442                                unsigned int reg_addr,
 443                                unsigned char data)
 444{
 445        u32 reg;
 446        int i;
 447        int retval;
 448
 449        for (i = 0; i < 3; i++) {
 450                /* Clear AUX CH data buffer */
 451                reg = BUF_CLR;
 452                writel(reg, dp->reg_base + EXYNOS_DP_BUFFER_DATA_CTL);
 453
 454                /* Select DPCD device address */
 455                reg = AUX_ADDR_7_0(reg_addr);
 456                writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_7_0);
 457                reg = AUX_ADDR_15_8(reg_addr);
 458                writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_15_8);
 459                reg = AUX_ADDR_19_16(reg_addr);
 460                writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_19_16);
 461
 462                /* Write data buffer */
 463                reg = (unsigned int)data;
 464                writel(reg, dp->reg_base + EXYNOS_DP_BUF_DATA_0);
 465
 466                /*
 467                 * Set DisplayPort transaction and write 1 byte
 468                 * If bit 3 is 1, DisplayPort transaction.
 469                 * If Bit 3 is 0, I2C transaction.
 470                 */
 471                reg = AUX_TX_COMM_DP_TRANSACTION | AUX_TX_COMM_WRITE;
 472                writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_CTL_1);
 473
 474                /* Start AUX transaction */
 475                retval = exynos_dp_start_aux_transaction(dp);
 476                if (retval == 0)
 477                        break;
 478                else
 479                        dev_dbg(dp->dev, "%s: Aux Transaction fail!\n",
 480                                __func__);
 481        }
 482
 483        return retval;
 484}
 485
 486int exynos_dp_read_byte_from_dpcd(struct exynos_dp_device *dp,
 487                                unsigned int reg_addr,
 488                                unsigned char *data)
 489{
 490        u32 reg;
 491        int i;
 492        int retval;
 493
 494        for (i = 0; i < 10; i++) {
 495                /* Clear AUX CH data buffer */
 496                reg = BUF_CLR;
 497                writel(reg, dp->reg_base + EXYNOS_DP_BUFFER_DATA_CTL);
 498
 499                /* Select DPCD device address */
 500                reg = AUX_ADDR_7_0(reg_addr);
 501                writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_7_0);
 502                reg = AUX_ADDR_15_8(reg_addr);
 503                writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_15_8);
 504                reg = AUX_ADDR_19_16(reg_addr);
 505                writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_19_16);
 506
 507                /*
 508                 * Set DisplayPort transaction and read 1 byte
 509                 * If bit 3 is 1, DisplayPort transaction.
 510                 * If Bit 3 is 0, I2C transaction.
 511                 */
 512                reg = AUX_TX_COMM_DP_TRANSACTION | AUX_TX_COMM_READ;
 513                writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_CTL_1);
 514
 515                /* Start AUX transaction */
 516                retval = exynos_dp_start_aux_transaction(dp);
 517                if (retval == 0)
 518                        break;
 519                else
 520                        dev_dbg(dp->dev, "%s: Aux Transaction fail!\n",
 521                                __func__);
 522        }
 523
 524        /* Read data buffer */
 525        reg = readl(dp->reg_base + EXYNOS_DP_BUF_DATA_0);
 526        *data = (unsigned char)(reg & 0xff);
 527
 528        return retval;
 529}
 530
 531int exynos_dp_write_bytes_to_dpcd(struct exynos_dp_device *dp,
 532                                unsigned int reg_addr,
 533                                unsigned int count,
 534                                unsigned char data[])
 535{
 536        u32 reg;
 537        unsigned int start_offset;
 538        unsigned int cur_data_count;
 539        unsigned int cur_data_idx;
 540        int i;
 541        int retval = 0;
 542
 543        /* Clear AUX CH data buffer */
 544        reg = BUF_CLR;
 545        writel(reg, dp->reg_base + EXYNOS_DP_BUFFER_DATA_CTL);
 546
 547        start_offset = 0;
 548        while (start_offset < count) {
 549                /* Buffer size of AUX CH is 16 * 4bytes */
 550                if ((count - start_offset) > 16)
 551                        cur_data_count = 16;
 552                else
 553                        cur_data_count = count - start_offset;
 554
 555                for (i = 0; i < 10; i++) {
 556                        /* Select DPCD device address */
 557                        reg = AUX_ADDR_7_0(reg_addr + start_offset);
 558                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_7_0);
 559                        reg = AUX_ADDR_15_8(reg_addr + start_offset);
 560                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_15_8);
 561                        reg = AUX_ADDR_19_16(reg_addr + start_offset);
 562                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_19_16);
 563
 564                        for (cur_data_idx = 0; cur_data_idx < cur_data_count;
 565                             cur_data_idx++) {
 566                                reg = data[start_offset + cur_data_idx];
 567                                writel(reg, dp->reg_base + EXYNOS_DP_BUF_DATA_0
 568                                                          + 4 * cur_data_idx);
 569                        }
 570
 571                        /*
 572                         * Set DisplayPort transaction and write
 573                         * If bit 3 is 1, DisplayPort transaction.
 574                         * If Bit 3 is 0, I2C transaction.
 575                         */
 576                        reg = AUX_LENGTH(cur_data_count) |
 577                                AUX_TX_COMM_DP_TRANSACTION | AUX_TX_COMM_WRITE;
 578                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_CTL_1);
 579
 580                        /* Start AUX transaction */
 581                        retval = exynos_dp_start_aux_transaction(dp);
 582                        if (retval == 0)
 583                                break;
 584                        else
 585                                dev_dbg(dp->dev, "%s: Aux Transaction fail!\n",
 586                                        __func__);
 587                }
 588
 589                start_offset += cur_data_count;
 590        }
 591
 592        return retval;
 593}
 594
 595int exynos_dp_read_bytes_from_dpcd(struct exynos_dp_device *dp,
 596                                unsigned int reg_addr,
 597                                unsigned int count,
 598                                unsigned char data[])
 599{
 600        u32 reg;
 601        unsigned int start_offset;
 602        unsigned int cur_data_count;
 603        unsigned int cur_data_idx;
 604        int i;
 605        int retval = 0;
 606
 607        /* Clear AUX CH data buffer */
 608        reg = BUF_CLR;
 609        writel(reg, dp->reg_base + EXYNOS_DP_BUFFER_DATA_CTL);
 610
 611        start_offset = 0;
 612        while (start_offset < count) {
 613                /* Buffer size of AUX CH is 16 * 4bytes */
 614                if ((count - start_offset) > 16)
 615                        cur_data_count = 16;
 616                else
 617                        cur_data_count = count - start_offset;
 618
 619                /* AUX CH Request Transaction process */
 620                for (i = 0; i < 10; i++) {
 621                        /* Select DPCD device address */
 622                        reg = AUX_ADDR_7_0(reg_addr + start_offset);
 623                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_7_0);
 624                        reg = AUX_ADDR_15_8(reg_addr + start_offset);
 625                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_15_8);
 626                        reg = AUX_ADDR_19_16(reg_addr + start_offset);
 627                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_19_16);
 628
 629                        /*
 630                         * Set DisplayPort transaction and read
 631                         * If bit 3 is 1, DisplayPort transaction.
 632                         * If Bit 3 is 0, I2C transaction.
 633                         */
 634                        reg = AUX_LENGTH(cur_data_count) |
 635                                AUX_TX_COMM_DP_TRANSACTION | AUX_TX_COMM_READ;
 636                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_CTL_1);
 637
 638                        /* Start AUX transaction */
 639                        retval = exynos_dp_start_aux_transaction(dp);
 640                        if (retval == 0)
 641                                break;
 642                        else
 643                                dev_dbg(dp->dev, "%s: Aux Transaction fail!\n",
 644                                        __func__);
 645                }
 646
 647                for (cur_data_idx = 0; cur_data_idx < cur_data_count;
 648                    cur_data_idx++) {
 649                        reg = readl(dp->reg_base + EXYNOS_DP_BUF_DATA_0
 650                                                 + 4 * cur_data_idx);
 651                        data[start_offset + cur_data_idx] =
 652                                (unsigned char)reg;
 653                }
 654
 655                start_offset += cur_data_count;
 656        }
 657
 658        return retval;
 659}
 660
 661int exynos_dp_select_i2c_device(struct exynos_dp_device *dp,
 662                                unsigned int device_addr,
 663                                unsigned int reg_addr)
 664{
 665        u32 reg;
 666        int retval;
 667
 668        /* Set EDID device address */
 669        reg = device_addr;
 670        writel(reg, dp->reg_base + EXYNOS_DP_AUX_ADDR_7_0);
 671        writel(0x0, dp->reg_base + EXYNOS_DP_AUX_ADDR_15_8);
 672        writel(0x0, dp->reg_base + EXYNOS_DP_AUX_ADDR_19_16);
 673
 674        /* Set offset from base address of EDID device */
 675        writel(reg_addr, dp->reg_base + EXYNOS_DP_BUF_DATA_0);
 676
 677        /*
 678         * Set I2C transaction and write address
 679         * If bit 3 is 1, DisplayPort transaction.
 680         * If Bit 3 is 0, I2C transaction.
 681         */
 682        reg = AUX_TX_COMM_I2C_TRANSACTION | AUX_TX_COMM_MOT |
 683                AUX_TX_COMM_WRITE;
 684        writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_CTL_1);
 685
 686        /* Start AUX transaction */
 687        retval = exynos_dp_start_aux_transaction(dp);
 688        if (retval != 0)
 689                dev_dbg(dp->dev, "%s: Aux Transaction fail!\n", __func__);
 690
 691        return retval;
 692}
 693
 694int exynos_dp_read_byte_from_i2c(struct exynos_dp_device *dp,
 695                                unsigned int device_addr,
 696                                unsigned int reg_addr,
 697                                unsigned int *data)
 698{
 699        u32 reg;
 700        int i;
 701        int retval;
 702
 703        for (i = 0; i < 10; i++) {
 704                /* Clear AUX CH data buffer */
 705                reg = BUF_CLR;
 706                writel(reg, dp->reg_base + EXYNOS_DP_BUFFER_DATA_CTL);
 707
 708                /* Select EDID device */
 709                retval = exynos_dp_select_i2c_device(dp, device_addr, reg_addr);
 710                if (retval != 0) {
 711                        dev_err(dp->dev, "Select EDID device fail!\n");
 712                        continue;
 713                }
 714
 715                /*
 716                 * Set I2C transaction and read data
 717                 * If bit 3 is 1, DisplayPort transaction.
 718                 * If Bit 3 is 0, I2C transaction.
 719                 */
 720                reg = AUX_TX_COMM_I2C_TRANSACTION |
 721                        AUX_TX_COMM_READ;
 722                writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_CTL_1);
 723
 724                /* Start AUX transaction */
 725                retval = exynos_dp_start_aux_transaction(dp);
 726                if (retval == 0)
 727                        break;
 728                else
 729                        dev_dbg(dp->dev, "%s: Aux Transaction fail!\n",
 730                                __func__);
 731        }
 732
 733        /* Read data */
 734        if (retval == 0)
 735                *data = readl(dp->reg_base + EXYNOS_DP_BUF_DATA_0);
 736
 737        return retval;
 738}
 739
 740int exynos_dp_read_bytes_from_i2c(struct exynos_dp_device *dp,
 741                                unsigned int device_addr,
 742                                unsigned int reg_addr,
 743                                unsigned int count,
 744                                unsigned char edid[])
 745{
 746        u32 reg;
 747        unsigned int i, j;
 748        unsigned int cur_data_idx;
 749        unsigned int defer = 0;
 750        int retval = 0;
 751
 752        for (i = 0; i < count; i += 16) {
 753                for (j = 0; j < 100; j++) {
 754                        /* Clear AUX CH data buffer */
 755                        reg = BUF_CLR;
 756                        writel(reg, dp->reg_base + EXYNOS_DP_BUFFER_DATA_CTL);
 757
 758                        /* Set normal AUX CH command */
 759                        reg = readl(dp->reg_base + EXYNOS_DP_AUX_CH_CTL_2);
 760                        reg &= ~ADDR_ONLY;
 761                        writel(reg, dp->reg_base + EXYNOS_DP_AUX_CH_CTL_2);
 762
 763                        /*
 764                         * If Rx sends defer, Tx sends only reads
 765                         * request without sending address
 766                         */
 767                        if (!defer)
 768                                retval = exynos_dp_select_i2c_device(dp,
 769                                                device_addr, reg_addr + i);
 770                        else
 771                                defer = 0;
 772
 773                        if (retval == 0) {
 774                                /*
 775                                 * Set I2C transaction and write data
 776                                 * If bit 3 is 1, DisplayPort transaction.
 777                                 * If Bit 3 is 0, I2C transaction.
 778                                 */
 779                                reg = AUX_LENGTH(16) |
 780                                        AUX_TX_COMM_I2C_TRANSACTION |
 781                                        AUX_TX_COMM_READ;
 782                                writel(reg, dp->reg_base +
 783                                        EXYNOS_DP_AUX_CH_CTL_1);
 784
 785                                /* Start AUX transaction */
 786                                retval = exynos_dp_start_aux_transaction(dp);
 787                                if (retval == 0)
 788                                        break;
 789                                else
 790                                        dev_dbg(dp->dev,
 791                                                "%s: Aux Transaction fail!\n",
 792                                                __func__);
 793                        }
 794                        /* Check if Rx sends defer */
 795                        reg = readl(dp->reg_base + EXYNOS_DP_AUX_RX_COMM);
 796                        if (reg == AUX_RX_COMM_AUX_DEFER ||
 797                                reg == AUX_RX_COMM_I2C_DEFER) {
 798                                dev_err(dp->dev, "Defer: %d\n\n", reg);
 799                                defer = 1;
 800                        }
 801                }
 802
 803                for (cur_data_idx = 0; cur_data_idx < 16; cur_data_idx++) {
 804                        reg = readl(dp->reg_base + EXYNOS_DP_BUF_DATA_0
 805                                                 + 4 * cur_data_idx);
 806                        edid[i + cur_data_idx] = (unsigned char)reg;
 807                }
 808        }
 809
 810        return retval;
 811}
 812
 813void exynos_dp_set_link_bandwidth(struct exynos_dp_device *dp, u32 bwtype)
 814{
 815        u32 reg;
 816
 817        reg = bwtype;
 818        if ((bwtype == LINK_RATE_2_70GBPS) || (bwtype == LINK_RATE_1_62GBPS))
 819                writel(reg, dp->reg_base + EXYNOS_DP_LINK_BW_SET);
 820}
 821
 822void exynos_dp_get_link_bandwidth(struct exynos_dp_device *dp, u32 *bwtype)
 823{
 824        u32 reg;
 825
 826        reg = readl(dp->reg_base + EXYNOS_DP_LINK_BW_SET);
 827        *bwtype = reg;
 828}
 829
 830void exynos_dp_set_lane_count(struct exynos_dp_device *dp, u32 count)
 831{
 832        u32 reg;
 833
 834        reg = count;
 835        writel(reg, dp->reg_base + EXYNOS_DP_LANE_COUNT_SET);
 836}
 837
 838void exynos_dp_get_lane_count(struct exynos_dp_device *dp, u32 *count)
 839{
 840        u32 reg;
 841
 842        reg = readl(dp->reg_base + EXYNOS_DP_LANE_COUNT_SET);
 843        *count = reg;
 844}
 845
 846void exynos_dp_enable_enhanced_mode(struct exynos_dp_device *dp, bool enable)
 847{
 848        u32 reg;
 849
 850        if (enable) {
 851                reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_4);
 852                reg |= ENHANCED;
 853                writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_4);
 854        } else {
 855                reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_4);
 856                reg &= ~ENHANCED;
 857                writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_4);
 858        }
 859}
 860
 861void exynos_dp_set_training_pattern(struct exynos_dp_device *dp,
 862                                 enum pattern_set pattern)
 863{
 864        u32 reg;
 865
 866        switch (pattern) {
 867        case PRBS7:
 868                reg = SCRAMBLING_ENABLE | LINK_QUAL_PATTERN_SET_PRBS7;
 869                writel(reg, dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
 870                break;
 871        case D10_2:
 872                reg = SCRAMBLING_ENABLE | LINK_QUAL_PATTERN_SET_D10_2;
 873                writel(reg, dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
 874                break;
 875        case TRAINING_PTN1:
 876                reg = SCRAMBLING_DISABLE | SW_TRAINING_PATTERN_SET_PTN1;
 877                writel(reg, dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
 878                break;
 879        case TRAINING_PTN2:
 880                reg = SCRAMBLING_DISABLE | SW_TRAINING_PATTERN_SET_PTN2;
 881                writel(reg, dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
 882                break;
 883        case DP_NONE:
 884                reg = SCRAMBLING_ENABLE |
 885                        LINK_QUAL_PATTERN_SET_DISABLE |
 886                        SW_TRAINING_PATTERN_SET_NORMAL;
 887                writel(reg, dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
 888                break;
 889        default:
 890                break;
 891        }
 892}
 893
 894void exynos_dp_set_lane0_pre_emphasis(struct exynos_dp_device *dp, u32 level)
 895{
 896        u32 reg;
 897
 898        reg = readl(dp->reg_base + EXYNOS_DP_LN0_LINK_TRAINING_CTL);
 899        reg &= ~PRE_EMPHASIS_SET_MASK;
 900        reg |= level << PRE_EMPHASIS_SET_SHIFT;
 901        writel(reg, dp->reg_base + EXYNOS_DP_LN0_LINK_TRAINING_CTL);
 902}
 903
 904void exynos_dp_set_lane1_pre_emphasis(struct exynos_dp_device *dp, u32 level)
 905{
 906        u32 reg;
 907
 908        reg = readl(dp->reg_base + EXYNOS_DP_LN1_LINK_TRAINING_CTL);
 909        reg &= ~PRE_EMPHASIS_SET_MASK;
 910        reg |= level << PRE_EMPHASIS_SET_SHIFT;
 911        writel(reg, dp->reg_base + EXYNOS_DP_LN1_LINK_TRAINING_CTL);
 912}
 913
 914void exynos_dp_set_lane2_pre_emphasis(struct exynos_dp_device *dp, u32 level)
 915{
 916        u32 reg;
 917
 918        reg = readl(dp->reg_base + EXYNOS_DP_LN2_LINK_TRAINING_CTL);
 919        reg &= ~PRE_EMPHASIS_SET_MASK;
 920        reg |= level << PRE_EMPHASIS_SET_SHIFT;
 921        writel(reg, dp->reg_base + EXYNOS_DP_LN2_LINK_TRAINING_CTL);
 922}
 923
 924void exynos_dp_set_lane3_pre_emphasis(struct exynos_dp_device *dp, u32 level)
 925{
 926        u32 reg;
 927
 928        reg = readl(dp->reg_base + EXYNOS_DP_LN3_LINK_TRAINING_CTL);
 929        reg &= ~PRE_EMPHASIS_SET_MASK;
 930        reg |= level << PRE_EMPHASIS_SET_SHIFT;
 931        writel(reg, dp->reg_base + EXYNOS_DP_LN3_LINK_TRAINING_CTL);
 932}
 933
 934void exynos_dp_set_lane0_link_training(struct exynos_dp_device *dp,
 935                                        u32 training_lane)
 936{
 937        u32 reg;
 938
 939        reg = training_lane;
 940        writel(reg, dp->reg_base + EXYNOS_DP_LN0_LINK_TRAINING_CTL);
 941}
 942
 943void exynos_dp_set_lane1_link_training(struct exynos_dp_device *dp,
 944                                        u32 training_lane)
 945{
 946        u32 reg;
 947
 948        reg = training_lane;
 949        writel(reg, dp->reg_base + EXYNOS_DP_LN1_LINK_TRAINING_CTL);
 950}
 951
 952void exynos_dp_set_lane2_link_training(struct exynos_dp_device *dp,
 953                                        u32 training_lane)
 954{
 955        u32 reg;
 956
 957        reg = training_lane;
 958        writel(reg, dp->reg_base + EXYNOS_DP_LN2_LINK_TRAINING_CTL);
 959}
 960
 961void exynos_dp_set_lane3_link_training(struct exynos_dp_device *dp,
 962                                        u32 training_lane)
 963{
 964        u32 reg;
 965
 966        reg = training_lane;
 967        writel(reg, dp->reg_base + EXYNOS_DP_LN3_LINK_TRAINING_CTL);
 968}
 969
 970u32 exynos_dp_get_lane0_link_training(struct exynos_dp_device *dp)
 971{
 972        u32 reg;
 973
 974        reg = readl(dp->reg_base + EXYNOS_DP_LN0_LINK_TRAINING_CTL);
 975        return reg;
 976}
 977
 978u32 exynos_dp_get_lane1_link_training(struct exynos_dp_device *dp)
 979{
 980        u32 reg;
 981
 982        reg = readl(dp->reg_base + EXYNOS_DP_LN1_LINK_TRAINING_CTL);
 983        return reg;
 984}
 985
 986u32 exynos_dp_get_lane2_link_training(struct exynos_dp_device *dp)
 987{
 988        u32 reg;
 989
 990        reg = readl(dp->reg_base + EXYNOS_DP_LN2_LINK_TRAINING_CTL);
 991        return reg;
 992}
 993
 994u32 exynos_dp_get_lane3_link_training(struct exynos_dp_device *dp)
 995{
 996        u32 reg;
 997
 998        reg = readl(dp->reg_base + EXYNOS_DP_LN3_LINK_TRAINING_CTL);
 999        return reg;
1000}
1001
1002void exynos_dp_reset_macro(struct exynos_dp_device *dp)
1003{
1004        u32 reg;
1005
1006        reg = readl(dp->reg_base + EXYNOS_DP_PHY_TEST);
1007        reg |= MACRO_RST;
1008        writel(reg, dp->reg_base + EXYNOS_DP_PHY_TEST);
1009
1010        /* 10 us is the minimum reset time. */
1011        usleep_range(10, 20);
1012
1013        reg &= ~MACRO_RST;
1014        writel(reg, dp->reg_base + EXYNOS_DP_PHY_TEST);
1015}
1016
1017void exynos_dp_init_video(struct exynos_dp_device *dp)
1018{
1019        u32 reg;
1020
1021        reg = VSYNC_DET | VID_FORMAT_CHG | VID_CLK_CHG;
1022        writel(reg, dp->reg_base + EXYNOS_DP_COMMON_INT_STA_1);
1023
1024        reg = 0x0;
1025        writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_1);
1026
1027        reg = CHA_CRI(4) | CHA_CTRL;
1028        writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_2);
1029
1030        reg = 0x0;
1031        writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_3);
1032
1033        reg = VID_HRES_TH(2) | VID_VRES_TH(0);
1034        writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_8);
1035}
1036
1037void exynos_dp_set_video_color_format(struct exynos_dp_device *dp,
1038                        u32 color_depth,
1039                        u32 color_space,
1040                        u32 dynamic_range,
1041                        u32 ycbcr_coeff)
1042{
1043        u32 reg;
1044
1045        /* Configure the input color depth, color space, dynamic range */
1046        reg = (dynamic_range << IN_D_RANGE_SHIFT) |
1047                (color_depth << IN_BPC_SHIFT) |
1048                (color_space << IN_COLOR_F_SHIFT);
1049        writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_2);
1050
1051        /* Set Input Color YCbCr Coefficients to ITU601 or ITU709 */
1052        reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_3);
1053        reg &= ~IN_YC_COEFFI_MASK;
1054        if (ycbcr_coeff)
1055                reg |= IN_YC_COEFFI_ITU709;
1056        else
1057                reg |= IN_YC_COEFFI_ITU601;
1058        writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_3);
1059}
1060
1061int exynos_dp_is_slave_video_stream_clock_on(struct exynos_dp_device *dp)
1062{
1063        u32 reg;
1064
1065        reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_1);
1066        writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_1);
1067
1068        reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_1);
1069
1070        if (!(reg & DET_STA)) {
1071                dev_dbg(dp->dev, "Input stream clock not detected.\n");
1072                return -EINVAL;
1073        }
1074
1075        reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_2);
1076        writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_2);
1077
1078        reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_2);
1079        dev_dbg(dp->dev, "wait SYS_CTL_2.\n");
1080
1081        if (reg & CHA_STA) {
1082                dev_dbg(dp->dev, "Input stream clk is changing\n");
1083                return -EINVAL;
1084        }
1085
1086        return 0;
1087}
1088
1089void exynos_dp_set_video_cr_mn(struct exynos_dp_device *dp,
1090                enum clock_recovery_m_value_type type,
1091                u32 m_value,
1092                u32 n_value)
1093{
1094        u32 reg;
1095
1096        if (type == REGISTER_M) {
1097                reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_4);
1098                reg |= FIX_M_VID;
1099                writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_4);
1100                reg = m_value & 0xff;
1101                writel(reg, dp->reg_base + EXYNOS_DP_M_VID_0);
1102                reg = (m_value >> 8) & 0xff;
1103                writel(reg, dp->reg_base + EXYNOS_DP_M_VID_1);
1104                reg = (m_value >> 16) & 0xff;
1105                writel(reg, dp->reg_base + EXYNOS_DP_M_VID_2);
1106
1107                reg = n_value & 0xff;
1108                writel(reg, dp->reg_base + EXYNOS_DP_N_VID_0);
1109                reg = (n_value >> 8) & 0xff;
1110                writel(reg, dp->reg_base + EXYNOS_DP_N_VID_1);
1111                reg = (n_value >> 16) & 0xff;
1112                writel(reg, dp->reg_base + EXYNOS_DP_N_VID_2);
1113        } else  {
1114                reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_4);
1115                reg &= ~FIX_M_VID;
1116                writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_4);
1117
1118                writel(0x00, dp->reg_base + EXYNOS_DP_N_VID_0);
1119                writel(0x80, dp->reg_base + EXYNOS_DP_N_VID_1);
1120                writel(0x00, dp->reg_base + EXYNOS_DP_N_VID_2);
1121        }
1122}
1123
1124void exynos_dp_set_video_timing_mode(struct exynos_dp_device *dp, u32 type)
1125{
1126        u32 reg;
1127
1128        if (type == VIDEO_TIMING_FROM_CAPTURE) {
1129                reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1130                reg &= ~FORMAT_SEL;
1131                writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1132        } else {
1133                reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1134                reg |= FORMAT_SEL;
1135                writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1136        }
1137}
1138
1139void exynos_dp_enable_video_master(struct exynos_dp_device *dp, bool enable)
1140{
1141        u32 reg;
1142
1143        if (enable) {
1144                reg = readl(dp->reg_base + EXYNOS_DP_SOC_GENERAL_CTL);
1145                reg &= ~VIDEO_MODE_MASK;
1146                reg |= VIDEO_MASTER_MODE_EN | VIDEO_MODE_MASTER_MODE;
1147                writel(reg, dp->reg_base + EXYNOS_DP_SOC_GENERAL_CTL);
1148        } else {
1149                reg = readl(dp->reg_base + EXYNOS_DP_SOC_GENERAL_CTL);
1150                reg &= ~VIDEO_MODE_MASK;
1151                reg |= VIDEO_MODE_SLAVE_MODE;
1152                writel(reg, dp->reg_base + EXYNOS_DP_SOC_GENERAL_CTL);
1153        }
1154}
1155
1156void exynos_dp_start_video(struct exynos_dp_device *dp)
1157{
1158        u32 reg;
1159
1160        reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_1);
1161        reg |= VIDEO_EN;
1162        writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_1);
1163}
1164
1165int exynos_dp_is_video_stream_on(struct exynos_dp_device *dp)
1166{
1167        u32 reg;
1168
1169        reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_3);
1170        writel(reg, dp->reg_base + EXYNOS_DP_SYS_CTL_3);
1171
1172        reg = readl(dp->reg_base + EXYNOS_DP_SYS_CTL_3);
1173        if (!(reg & STRM_VALID)) {
1174                dev_dbg(dp->dev, "Input video stream is not detected.\n");
1175                return -EINVAL;
1176        }
1177
1178        return 0;
1179}
1180
1181void exynos_dp_config_video_slave_mode(struct exynos_dp_device *dp,
1182                        struct video_info *video_info)
1183{
1184        u32 reg;
1185
1186        reg = readl(dp->reg_base + EXYNOS_DP_FUNC_EN_1);
1187        reg &= ~(MASTER_VID_FUNC_EN_N|SLAVE_VID_FUNC_EN_N);
1188        reg |= MASTER_VID_FUNC_EN_N;
1189        writel(reg, dp->reg_base + EXYNOS_DP_FUNC_EN_1);
1190
1191        reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1192        reg &= ~INTERACE_SCAN_CFG;
1193        reg |= (video_info->interlaced << 2);
1194        writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1195
1196        reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1197        reg &= ~VSYNC_POLARITY_CFG;
1198        reg |= (video_info->v_sync_polarity << 1);
1199        writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1200
1201        reg = readl(dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1202        reg &= ~HSYNC_POLARITY_CFG;
1203        reg |= (video_info->h_sync_polarity << 0);
1204        writel(reg, dp->reg_base + EXYNOS_DP_VIDEO_CTL_10);
1205
1206        reg = AUDIO_MODE_SPDIF_MODE | VIDEO_MODE_SLAVE_MODE;
1207        writel(reg, dp->reg_base + EXYNOS_DP_SOC_GENERAL_CTL);
1208}
1209
1210void exynos_dp_enable_scrambling(struct exynos_dp_device *dp)
1211{
1212        u32 reg;
1213
1214        reg = readl(dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
1215        reg &= ~SCRAMBLING_DISABLE;
1216        writel(reg, dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
1217}
1218
1219void exynos_dp_disable_scrambling(struct exynos_dp_device *dp)
1220{
1221        u32 reg;
1222
1223        reg = readl(dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
1224        reg |= SCRAMBLING_DISABLE;
1225        writel(reg, dp->reg_base + EXYNOS_DP_TRAINING_PTN_SET);
1226}
1227