ast_dp501.c (10424B)
1// SPDX-License-Identifier: GPL-2.0 2 3#include <linux/delay.h> 4#include <linux/firmware.h> 5#include <linux/module.h> 6 7#include "ast_drv.h" 8 9MODULE_FIRMWARE("ast_dp501_fw.bin"); 10 11static void ast_release_firmware(void *data) 12{ 13 struct ast_private *ast = data; 14 15 release_firmware(ast->dp501_fw); 16 ast->dp501_fw = NULL; 17} 18 19static int ast_load_dp501_microcode(struct drm_device *dev) 20{ 21 struct ast_private *ast = to_ast_private(dev); 22 int ret; 23 24 ret = request_firmware(&ast->dp501_fw, "ast_dp501_fw.bin", dev->dev); 25 if (ret) 26 return ret; 27 28 return devm_add_action_or_reset(dev->dev, ast_release_firmware, ast); 29} 30 31static void send_ack(struct ast_private *ast) 32{ 33 u8 sendack; 34 sendack = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9b, 0xff); 35 sendack |= 0x80; 36 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9b, 0x00, sendack); 37} 38 39static void send_nack(struct ast_private *ast) 40{ 41 u8 sendack; 42 sendack = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9b, 0xff); 43 sendack &= ~0x80; 44 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9b, 0x00, sendack); 45} 46 47static bool wait_ack(struct ast_private *ast) 48{ 49 u8 waitack; 50 u32 retry = 0; 51 do { 52 waitack = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xd2, 0xff); 53 waitack &= 0x80; 54 udelay(100); 55 } while ((!waitack) && (retry++ < 1000)); 56 57 if (retry < 1000) 58 return true; 59 else 60 return false; 61} 62 63static bool wait_nack(struct ast_private *ast) 64{ 65 u8 waitack; 66 u32 retry = 0; 67 do { 68 waitack = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xd2, 0xff); 69 waitack &= 0x80; 70 udelay(100); 71 } while ((waitack) && (retry++ < 1000)); 72 73 if (retry < 1000) 74 return true; 75 else 76 return false; 77} 78 79static void set_cmd_trigger(struct ast_private *ast) 80{ 81 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9b, ~0x40, 0x40); 82} 83 84static void clear_cmd_trigger(struct ast_private *ast) 85{ 86 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9b, ~0x40, 0x00); 87} 88 89#if 0 90static bool wait_fw_ready(struct ast_private *ast) 91{ 92 u8 waitready; 93 u32 retry = 0; 94 do { 95 waitready = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xd2, 0xff); 96 waitready &= 0x40; 97 udelay(100); 98 } while ((!waitready) && (retry++ < 1000)); 99 100 if (retry < 1000) 101 return true; 102 else 103 return false; 104} 105#endif 106 107static bool ast_write_cmd(struct drm_device *dev, u8 data) 108{ 109 struct ast_private *ast = to_ast_private(dev); 110 int retry = 0; 111 if (wait_nack(ast)) { 112 send_nack(ast); 113 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9a, 0x00, data); 114 send_ack(ast); 115 set_cmd_trigger(ast); 116 do { 117 if (wait_ack(ast)) { 118 clear_cmd_trigger(ast); 119 send_nack(ast); 120 return true; 121 } 122 } while (retry++ < 100); 123 } 124 clear_cmd_trigger(ast); 125 send_nack(ast); 126 return false; 127} 128 129static bool ast_write_data(struct drm_device *dev, u8 data) 130{ 131 struct ast_private *ast = to_ast_private(dev); 132 133 if (wait_nack(ast)) { 134 send_nack(ast); 135 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9a, 0x00, data); 136 send_ack(ast); 137 if (wait_ack(ast)) { 138 send_nack(ast); 139 return true; 140 } 141 } 142 send_nack(ast); 143 return false; 144} 145 146#if 0 147static bool ast_read_data(struct drm_device *dev, u8 *data) 148{ 149 struct ast_private *ast = to_ast_private(dev); 150 u8 tmp; 151 152 *data = 0; 153 154 if (wait_ack(ast) == false) 155 return false; 156 tmp = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xd3, 0xff); 157 *data = tmp; 158 if (wait_nack(ast) == false) { 159 send_nack(ast); 160 return false; 161 } 162 send_nack(ast); 163 return true; 164} 165 166static void clear_cmd(struct ast_private *ast) 167{ 168 send_nack(ast); 169 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x9a, 0x00, 0x00); 170} 171#endif 172 173void ast_set_dp501_video_output(struct drm_device *dev, u8 mode) 174{ 175 ast_write_cmd(dev, 0x40); 176 ast_write_data(dev, mode); 177 178 msleep(10); 179} 180 181static u32 get_fw_base(struct ast_private *ast) 182{ 183 return ast_mindwm(ast, 0x1e6e2104) & 0x7fffffff; 184} 185 186bool ast_backup_fw(struct drm_device *dev, u8 *addr, u32 size) 187{ 188 struct ast_private *ast = to_ast_private(dev); 189 u32 i, data; 190 u32 boot_address; 191 192 if (ast->config_mode != ast_use_p2a) 193 return false; 194 195 data = ast_mindwm(ast, 0x1e6e2100) & 0x01; 196 if (data) { 197 boot_address = get_fw_base(ast); 198 for (i = 0; i < size; i += 4) 199 *(u32 *)(addr + i) = ast_mindwm(ast, boot_address + i); 200 return true; 201 } 202 return false; 203} 204 205static bool ast_launch_m68k(struct drm_device *dev) 206{ 207 struct ast_private *ast = to_ast_private(dev); 208 u32 i, data, len = 0; 209 u32 boot_address; 210 u8 *fw_addr = NULL; 211 u8 jreg; 212 213 if (ast->config_mode != ast_use_p2a) 214 return false; 215 216 data = ast_mindwm(ast, 0x1e6e2100) & 0x01; 217 if (!data) { 218 219 if (ast->dp501_fw_addr) { 220 fw_addr = ast->dp501_fw_addr; 221 len = 32*1024; 222 } else { 223 if (!ast->dp501_fw && 224 ast_load_dp501_microcode(dev) < 0) 225 return false; 226 227 fw_addr = (u8 *)ast->dp501_fw->data; 228 len = ast->dp501_fw->size; 229 } 230 /* Get BootAddress */ 231 ast_moutdwm(ast, 0x1e6e2000, 0x1688a8a8); 232 data = ast_mindwm(ast, 0x1e6e0004); 233 switch (data & 0x03) { 234 case 0: 235 boot_address = 0x44000000; 236 break; 237 default: 238 case 1: 239 boot_address = 0x48000000; 240 break; 241 case 2: 242 boot_address = 0x50000000; 243 break; 244 case 3: 245 boot_address = 0x60000000; 246 break; 247 } 248 boot_address -= 0x200000; /* -2MB */ 249 250 /* copy image to buffer */ 251 for (i = 0; i < len; i += 4) { 252 data = *(u32 *)(fw_addr + i); 253 ast_moutdwm(ast, boot_address + i, data); 254 } 255 256 /* Init SCU */ 257 ast_moutdwm(ast, 0x1e6e2000, 0x1688a8a8); 258 259 /* Launch FW */ 260 ast_moutdwm(ast, 0x1e6e2104, 0x80000000 + boot_address); 261 ast_moutdwm(ast, 0x1e6e2100, 1); 262 263 /* Update Scratch */ 264 data = ast_mindwm(ast, 0x1e6e2040) & 0xfffff1ff; /* D[11:9] = 100b: UEFI handling */ 265 data |= 0x800; 266 ast_moutdwm(ast, 0x1e6e2040, data); 267 268 jreg = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0x99, 0xfc); /* D[1:0]: Reserved Video Buffer */ 269 jreg |= 0x02; 270 ast_set_index_reg(ast, AST_IO_CRTC_PORT, 0x99, jreg); 271 } 272 return true; 273} 274 275bool ast_dp501_read_edid(struct drm_device *dev, u8 *ediddata) 276{ 277 struct ast_private *ast = to_ast_private(dev); 278 u32 i, boot_address, offset, data; 279 u32 *pEDIDidx; 280 281 if (ast->config_mode == ast_use_p2a) { 282 boot_address = get_fw_base(ast); 283 284 /* validate FW version */ 285 offset = AST_DP501_GBL_VERSION; 286 data = ast_mindwm(ast, boot_address + offset); 287 if ((data & AST_DP501_FW_VERSION_MASK) != AST_DP501_FW_VERSION_1) 288 return false; 289 290 /* validate PnP Monitor */ 291 offset = AST_DP501_PNPMONITOR; 292 data = ast_mindwm(ast, boot_address + offset); 293 if (!(data & AST_DP501_PNP_CONNECTED)) 294 return false; 295 296 /* Read EDID */ 297 offset = AST_DP501_EDID_DATA; 298 for (i = 0; i < 128; i += 4) { 299 data = ast_mindwm(ast, boot_address + offset + i); 300 pEDIDidx = (u32 *)(ediddata + i); 301 *pEDIDidx = data; 302 } 303 } else { 304 if (!ast->dp501_fw_buf) 305 return false; 306 307 /* dummy read */ 308 offset = 0x0000; 309 data = readl(ast->dp501_fw_buf + offset); 310 311 /* validate FW version */ 312 offset = AST_DP501_GBL_VERSION; 313 data = readl(ast->dp501_fw_buf + offset); 314 if ((data & AST_DP501_FW_VERSION_MASK) != AST_DP501_FW_VERSION_1) 315 return false; 316 317 /* validate PnP Monitor */ 318 offset = AST_DP501_PNPMONITOR; 319 data = readl(ast->dp501_fw_buf + offset); 320 if (!(data & AST_DP501_PNP_CONNECTED)) 321 return false; 322 323 /* Read EDID */ 324 offset = AST_DP501_EDID_DATA; 325 for (i = 0; i < 128; i += 4) { 326 data = readl(ast->dp501_fw_buf + offset + i); 327 pEDIDidx = (u32 *)(ediddata + i); 328 *pEDIDidx = data; 329 } 330 } 331 332 return true; 333} 334 335static bool ast_init_dvo(struct drm_device *dev) 336{ 337 struct ast_private *ast = to_ast_private(dev); 338 u8 jreg; 339 u32 data; 340 ast_write32(ast, 0xf004, 0x1e6e0000); 341 ast_write32(ast, 0xf000, 0x1); 342 ast_write32(ast, 0x12000, 0x1688a8a8); 343 344 jreg = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xd0, 0xff); 345 if (!(jreg & 0x80)) { 346 /* Init SCU DVO Settings */ 347 data = ast_read32(ast, 0x12008); 348 /* delay phase */ 349 data &= 0xfffff8ff; 350 data |= 0x00000500; 351 ast_write32(ast, 0x12008, data); 352 353 if (ast->chip == AST2300) { 354 data = ast_read32(ast, 0x12084); 355 /* multi-pins for DVO single-edge */ 356 data |= 0xfffe0000; 357 ast_write32(ast, 0x12084, data); 358 359 data = ast_read32(ast, 0x12088); 360 /* multi-pins for DVO single-edge */ 361 data |= 0x000fffff; 362 ast_write32(ast, 0x12088, data); 363 364 data = ast_read32(ast, 0x12090); 365 /* multi-pins for DVO single-edge */ 366 data &= 0xffffffcf; 367 data |= 0x00000020; 368 ast_write32(ast, 0x12090, data); 369 } else { /* AST2400 */ 370 data = ast_read32(ast, 0x12088); 371 /* multi-pins for DVO single-edge */ 372 data |= 0x30000000; 373 ast_write32(ast, 0x12088, data); 374 375 data = ast_read32(ast, 0x1208c); 376 /* multi-pins for DVO single-edge */ 377 data |= 0x000000cf; 378 ast_write32(ast, 0x1208c, data); 379 380 data = ast_read32(ast, 0x120a4); 381 /* multi-pins for DVO single-edge */ 382 data |= 0xffff0000; 383 ast_write32(ast, 0x120a4, data); 384 385 data = ast_read32(ast, 0x120a8); 386 /* multi-pins for DVO single-edge */ 387 data |= 0x0000000f; 388 ast_write32(ast, 0x120a8, data); 389 390 data = ast_read32(ast, 0x12094); 391 /* multi-pins for DVO single-edge */ 392 data |= 0x00000002; 393 ast_write32(ast, 0x12094, data); 394 } 395 } 396 397 /* Force to DVO */ 398 data = ast_read32(ast, 0x1202c); 399 data &= 0xfffbffff; 400 ast_write32(ast, 0x1202c, data); 401 402 /* Init VGA DVO Settings */ 403 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xa3, 0xcf, 0x80); 404 return true; 405} 406 407 408static void ast_init_analog(struct drm_device *dev) 409{ 410 struct ast_private *ast = to_ast_private(dev); 411 u32 data; 412 413 /* 414 * Set DAC source to VGA mode in SCU2C via the P2A 415 * bridge. First configure the P2U to target the SCU 416 * in case it isn't at this stage. 417 */ 418 ast_write32(ast, 0xf004, 0x1e6e0000); 419 ast_write32(ast, 0xf000, 0x1); 420 421 /* Then unlock the SCU with the magic password */ 422 ast_write32(ast, 0x12000, 0x1688a8a8); 423 ast_write32(ast, 0x12000, 0x1688a8a8); 424 ast_write32(ast, 0x12000, 0x1688a8a8); 425 426 /* Finally, clear bits [17:16] of SCU2c */ 427 data = ast_read32(ast, 0x1202c); 428 data &= 0xfffcffff; 429 ast_write32(ast, 0, data); 430 431 /* Disable DVO */ 432 ast_set_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xa3, 0xcf, 0x00); 433} 434 435void ast_init_3rdtx(struct drm_device *dev) 436{ 437 struct ast_private *ast = to_ast_private(dev); 438 u8 jreg; 439 440 if (ast->chip == AST2300 || ast->chip == AST2400) { 441 jreg = ast_get_index_reg_mask(ast, AST_IO_CRTC_PORT, 0xd1, 0xff); 442 switch (jreg & 0x0e) { 443 case 0x04: 444 ast_init_dvo(dev); 445 break; 446 case 0x08: 447 ast_launch_m68k(dev); 448 break; 449 case 0x0c: 450 ast_init_dvo(dev); 451 break; 452 default: 453 if (ast->tx_chip_types & BIT(AST_TX_SIL164)) 454 ast_init_dvo(dev); 455 else 456 ast_init_analog(dev); 457 } 458 } 459}