1 /* 2 * Copyright 2019 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 "hdcp.h" 27 28 #define MIN(a, b) ((a) < (b) ? (a) : (b)) 29 #define HDCP_I2C_ADDR 0x3a /* 0x74 >> 1*/ 30 #define KSV_READ_SIZE 0xf /* 0x6803b - 0x6802c */ 31 #define HDCP_MAX_AUX_TRANSACTION_SIZE 16 32 33 #define DP_CP_IRQ (1 << 2) 34 35 enum mod_hdcp_ddc_message_id { 36 MOD_HDCP_MESSAGE_ID_INVALID = -1, 37 38 /* HDCP 1.4 */ 39 40 MOD_HDCP_MESSAGE_ID_READ_BKSV = 0, 41 MOD_HDCP_MESSAGE_ID_READ_RI_R0, 42 MOD_HDCP_MESSAGE_ID_WRITE_AKSV, 43 MOD_HDCP_MESSAGE_ID_WRITE_AINFO, 44 MOD_HDCP_MESSAGE_ID_WRITE_AN, 45 MOD_HDCP_MESSAGE_ID_READ_VH_X, 46 MOD_HDCP_MESSAGE_ID_READ_VH_0, 47 MOD_HDCP_MESSAGE_ID_READ_VH_1, 48 MOD_HDCP_MESSAGE_ID_READ_VH_2, 49 MOD_HDCP_MESSAGE_ID_READ_VH_3, 50 MOD_HDCP_MESSAGE_ID_READ_VH_4, 51 MOD_HDCP_MESSAGE_ID_READ_BCAPS, 52 MOD_HDCP_MESSAGE_ID_READ_BSTATUS, 53 MOD_HDCP_MESSAGE_ID_READ_KSV_FIFO, 54 MOD_HDCP_MESSAGE_ID_READ_BINFO, 55 56 /* HDCP 2.2 */ 57 58 MOD_HDCP_MESSAGE_ID_HDCP2VERSION, 59 MOD_HDCP_MESSAGE_ID_RX_CAPS, 60 MOD_HDCP_MESSAGE_ID_WRITE_AKE_INIT, 61 MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_CERT, 62 MOD_HDCP_MESSAGE_ID_WRITE_AKE_NO_STORED_KM, 63 MOD_HDCP_MESSAGE_ID_WRITE_AKE_STORED_KM, 64 MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_H_PRIME, 65 MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_PAIRING_INFO, 66 MOD_HDCP_MESSAGE_ID_WRITE_LC_INIT, 67 MOD_HDCP_MESSAGE_ID_READ_LC_SEND_L_PRIME, 68 MOD_HDCP_MESSAGE_ID_WRITE_SKE_SEND_EKS, 69 MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST, 70 MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST_PART2, 71 MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_SEND_ACK, 72 MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_STREAM_MANAGE, 73 MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_STREAM_READY, 74 MOD_HDCP_MESSAGE_ID_READ_RXSTATUS, 75 MOD_HDCP_MESSAGE_ID_WRITE_CONTENT_STREAM_TYPE, 76 77 MOD_HDCP_MESSAGE_ID_MAX 78 }; 79 80 static const uint8_t hdcp_i2c_offsets[] = { 81 [MOD_HDCP_MESSAGE_ID_READ_BKSV] = 0x0, 82 [MOD_HDCP_MESSAGE_ID_READ_RI_R0] = 0x8, 83 [MOD_HDCP_MESSAGE_ID_WRITE_AKSV] = 0x10, 84 [MOD_HDCP_MESSAGE_ID_WRITE_AINFO] = 0x15, 85 [MOD_HDCP_MESSAGE_ID_WRITE_AN] = 0x18, 86 [MOD_HDCP_MESSAGE_ID_READ_VH_X] = 0x20, 87 [MOD_HDCP_MESSAGE_ID_READ_VH_0] = 0x20, 88 [MOD_HDCP_MESSAGE_ID_READ_VH_1] = 0x24, 89 [MOD_HDCP_MESSAGE_ID_READ_VH_2] = 0x28, 90 [MOD_HDCP_MESSAGE_ID_READ_VH_3] = 0x2C, 91 [MOD_HDCP_MESSAGE_ID_READ_VH_4] = 0x30, 92 [MOD_HDCP_MESSAGE_ID_READ_BCAPS] = 0x40, 93 [MOD_HDCP_MESSAGE_ID_READ_BSTATUS] = 0x41, 94 [MOD_HDCP_MESSAGE_ID_READ_KSV_FIFO] = 0x43, 95 [MOD_HDCP_MESSAGE_ID_READ_BINFO] = 0xFF, 96 [MOD_HDCP_MESSAGE_ID_HDCP2VERSION] = 0x50, 97 [MOD_HDCP_MESSAGE_ID_WRITE_AKE_INIT] = 0x60, 98 [MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_CERT] = 0x80, 99 [MOD_HDCP_MESSAGE_ID_WRITE_AKE_NO_STORED_KM] = 0x60, 100 [MOD_HDCP_MESSAGE_ID_WRITE_AKE_STORED_KM] = 0x60, 101 [MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_H_PRIME] = 0x80, 102 [MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_PAIRING_INFO] = 0x80, 103 [MOD_HDCP_MESSAGE_ID_WRITE_LC_INIT] = 0x60, 104 [MOD_HDCP_MESSAGE_ID_READ_LC_SEND_L_PRIME] = 0x80, 105 [MOD_HDCP_MESSAGE_ID_WRITE_SKE_SEND_EKS] = 0x60, 106 [MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST] = 0x80, 107 [MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST_PART2] = 0x80, 108 [MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_SEND_ACK] = 0x60, 109 [MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_STREAM_MANAGE] = 0x60, 110 [MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_STREAM_READY] = 0x80, 111 [MOD_HDCP_MESSAGE_ID_READ_RXSTATUS] = 0x70, 112 [MOD_HDCP_MESSAGE_ID_WRITE_CONTENT_STREAM_TYPE] = 0x0 113 }; 114 115 static const uint32_t hdcp_dpcd_addrs[] = { 116 [MOD_HDCP_MESSAGE_ID_READ_BKSV] = 0x68000, 117 [MOD_HDCP_MESSAGE_ID_READ_RI_R0] = 0x68005, 118 [MOD_HDCP_MESSAGE_ID_WRITE_AKSV] = 0x68007, 119 [MOD_HDCP_MESSAGE_ID_WRITE_AINFO] = 0x6803B, 120 [MOD_HDCP_MESSAGE_ID_WRITE_AN] = 0x6800c, 121 [MOD_HDCP_MESSAGE_ID_READ_VH_X] = 0x68014, 122 [MOD_HDCP_MESSAGE_ID_READ_VH_0] = 0x68014, 123 [MOD_HDCP_MESSAGE_ID_READ_VH_1] = 0x68018, 124 [MOD_HDCP_MESSAGE_ID_READ_VH_2] = 0x6801c, 125 [MOD_HDCP_MESSAGE_ID_READ_VH_3] = 0x68020, 126 [MOD_HDCP_MESSAGE_ID_READ_VH_4] = 0x68024, 127 [MOD_HDCP_MESSAGE_ID_READ_BCAPS] = 0x68028, 128 [MOD_HDCP_MESSAGE_ID_READ_BSTATUS] = 0x68029, 129 [MOD_HDCP_MESSAGE_ID_READ_KSV_FIFO] = 0x6802c, 130 [MOD_HDCP_MESSAGE_ID_READ_BINFO] = 0x6802a, 131 [MOD_HDCP_MESSAGE_ID_RX_CAPS] = 0x6921d, 132 [MOD_HDCP_MESSAGE_ID_WRITE_AKE_INIT] = 0x69000, 133 [MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_CERT] = 0x6900b, 134 [MOD_HDCP_MESSAGE_ID_WRITE_AKE_NO_STORED_KM] = 0x69220, 135 [MOD_HDCP_MESSAGE_ID_WRITE_AKE_STORED_KM] = 0x692a0, 136 [MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_H_PRIME] = 0x692c0, 137 [MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_PAIRING_INFO] = 0x692e0, 138 [MOD_HDCP_MESSAGE_ID_WRITE_LC_INIT] = 0x692f0, 139 [MOD_HDCP_MESSAGE_ID_READ_LC_SEND_L_PRIME] = 0x692f8, 140 [MOD_HDCP_MESSAGE_ID_WRITE_SKE_SEND_EKS] = 0x69318, 141 [MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST] = 0x69330, 142 [MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST_PART2] = 0x69340, 143 [MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_SEND_ACK] = 0x693e0, 144 [MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_STREAM_MANAGE] = 0x693f0, 145 [MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_STREAM_READY] = 0x69473, 146 [MOD_HDCP_MESSAGE_ID_READ_RXSTATUS] = 0x69493, 147 [MOD_HDCP_MESSAGE_ID_WRITE_CONTENT_STREAM_TYPE] = 0x69494 148 }; 149 150 static enum mod_hdcp_status read(struct mod_hdcp *hdcp, 151 enum mod_hdcp_ddc_message_id msg_id, 152 uint8_t *buf, 153 uint32_t buf_len) 154 { 155 bool success = true; 156 uint32_t cur_size = 0; 157 uint32_t data_offset = 0; 158 159 if (msg_id == MOD_HDCP_MESSAGE_ID_INVALID || 160 msg_id >= MOD_HDCP_MESSAGE_ID_MAX) 161 return MOD_HDCP_STATUS_DDC_FAILURE; 162 163 if (is_dp_hdcp(hdcp)) { 164 int num_dpcd_addrs = sizeof(hdcp_dpcd_addrs) / 165 sizeof(hdcp_dpcd_addrs[0]); 166 if (msg_id >= num_dpcd_addrs) 167 return MOD_HDCP_STATUS_DDC_FAILURE; 168 169 while (buf_len > 0) { 170 cur_size = MIN(buf_len, HDCP_MAX_AUX_TRANSACTION_SIZE); 171 success = hdcp->config.ddc.funcs.read_dpcd(hdcp->config.ddc.handle, 172 hdcp_dpcd_addrs[msg_id] + data_offset, 173 buf + data_offset, 174 cur_size); 175 176 if (!success) 177 break; 178 179 buf_len -= cur_size; 180 data_offset += cur_size; 181 } 182 } else { 183 int num_i2c_offsets = sizeof(hdcp_i2c_offsets) / 184 sizeof(hdcp_i2c_offsets[0]); 185 if (msg_id >= num_i2c_offsets) 186 return MOD_HDCP_STATUS_DDC_FAILURE; 187 188 success = hdcp->config.ddc.funcs.read_i2c( 189 hdcp->config.ddc.handle, 190 HDCP_I2C_ADDR, 191 hdcp_i2c_offsets[msg_id], 192 buf, 193 (uint32_t)buf_len); 194 } 195 196 return success ? MOD_HDCP_STATUS_SUCCESS : MOD_HDCP_STATUS_DDC_FAILURE; 197 } 198 199 static enum mod_hdcp_status read_repeatedly(struct mod_hdcp *hdcp, 200 enum mod_hdcp_ddc_message_id msg_id, 201 uint8_t *buf, 202 uint32_t buf_len, 203 uint8_t read_size) 204 { 205 enum mod_hdcp_status status = MOD_HDCP_STATUS_DDC_FAILURE; 206 uint32_t cur_size = 0; 207 uint32_t data_offset = 0; 208 209 while (buf_len > 0) { 210 cur_size = MIN(buf_len, read_size); 211 status = read(hdcp, msg_id, buf + data_offset, cur_size); 212 213 if (status != MOD_HDCP_STATUS_SUCCESS) 214 break; 215 216 buf_len -= cur_size; 217 data_offset += cur_size; 218 } 219 220 return status; 221 } 222 223 static enum mod_hdcp_status write(struct mod_hdcp *hdcp, 224 enum mod_hdcp_ddc_message_id msg_id, 225 uint8_t *buf, 226 uint32_t buf_len) 227 { 228 bool success = true; 229 uint32_t cur_size = 0; 230 uint32_t data_offset = 0; 231 232 if (msg_id == MOD_HDCP_MESSAGE_ID_INVALID || 233 msg_id >= MOD_HDCP_MESSAGE_ID_MAX) 234 return MOD_HDCP_STATUS_DDC_FAILURE; 235 236 if (is_dp_hdcp(hdcp)) { 237 int num_dpcd_addrs = sizeof(hdcp_dpcd_addrs) / 238 sizeof(hdcp_dpcd_addrs[0]); 239 if (msg_id >= num_dpcd_addrs) 240 return MOD_HDCP_STATUS_DDC_FAILURE; 241 242 while (buf_len > 0) { 243 cur_size = MIN(buf_len, HDCP_MAX_AUX_TRANSACTION_SIZE); 244 success = hdcp->config.ddc.funcs.write_dpcd( 245 hdcp->config.ddc.handle, 246 hdcp_dpcd_addrs[msg_id] + data_offset, 247 buf + data_offset, 248 cur_size); 249 250 if (!success) 251 break; 252 253 buf_len -= cur_size; 254 data_offset += cur_size; 255 } 256 } else { 257 int num_i2c_offsets = sizeof(hdcp_i2c_offsets) / 258 sizeof(hdcp_i2c_offsets[0]); 259 if (msg_id >= num_i2c_offsets) 260 return MOD_HDCP_STATUS_DDC_FAILURE; 261 262 hdcp->buf[0] = hdcp_i2c_offsets[msg_id]; 263 memmove(&hdcp->buf[1], buf, buf_len); 264 success = hdcp->config.ddc.funcs.write_i2c( 265 hdcp->config.ddc.handle, 266 HDCP_I2C_ADDR, 267 hdcp->buf, 268 (uint32_t)(buf_len+1)); 269 } 270 271 return success ? MOD_HDCP_STATUS_SUCCESS : MOD_HDCP_STATUS_DDC_FAILURE; 272 } 273 274 enum mod_hdcp_status mod_hdcp_read_bksv(struct mod_hdcp *hdcp) 275 { 276 return read(hdcp, MOD_HDCP_MESSAGE_ID_READ_BKSV, 277 hdcp->auth.msg.hdcp1.bksv, 278 sizeof(hdcp->auth.msg.hdcp1.bksv)); 279 } 280 281 enum mod_hdcp_status mod_hdcp_read_bcaps(struct mod_hdcp *hdcp) 282 { 283 return read(hdcp, MOD_HDCP_MESSAGE_ID_READ_BCAPS, 284 &hdcp->auth.msg.hdcp1.bcaps, 285 sizeof(hdcp->auth.msg.hdcp1.bcaps)); 286 } 287 288 enum mod_hdcp_status mod_hdcp_read_bstatus(struct mod_hdcp *hdcp) 289 { 290 enum mod_hdcp_status status; 291 292 if (is_dp_hdcp(hdcp)) 293 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_BSTATUS, 294 (uint8_t *)&hdcp->auth.msg.hdcp1.bstatus, 295 1); 296 else 297 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_BSTATUS, 298 (uint8_t *)&hdcp->auth.msg.hdcp1.bstatus, 299 sizeof(hdcp->auth.msg.hdcp1.bstatus)); 300 return status; 301 } 302 303 enum mod_hdcp_status mod_hdcp_read_r0p(struct mod_hdcp *hdcp) 304 { 305 return read(hdcp, MOD_HDCP_MESSAGE_ID_READ_RI_R0, 306 (uint8_t *)&hdcp->auth.msg.hdcp1.r0p, 307 sizeof(hdcp->auth.msg.hdcp1.r0p)); 308 } 309 310 /* special case, reading repeatedly at the same address, don't use read() */ 311 enum mod_hdcp_status mod_hdcp_read_ksvlist(struct mod_hdcp *hdcp) 312 { 313 enum mod_hdcp_status status; 314 315 if (is_dp_hdcp(hdcp)) 316 status = read_repeatedly(hdcp, MOD_HDCP_MESSAGE_ID_READ_KSV_FIFO, 317 hdcp->auth.msg.hdcp1.ksvlist, 318 hdcp->auth.msg.hdcp1.ksvlist_size, 319 KSV_READ_SIZE); 320 else 321 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_KSV_FIFO, 322 (uint8_t *)&hdcp->auth.msg.hdcp1.ksvlist, 323 hdcp->auth.msg.hdcp1.ksvlist_size); 324 return status; 325 } 326 327 enum mod_hdcp_status mod_hdcp_read_vp(struct mod_hdcp *hdcp) 328 { 329 enum mod_hdcp_status status; 330 331 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_VH_0, 332 &hdcp->auth.msg.hdcp1.vp[0], 4); 333 if (status != MOD_HDCP_STATUS_SUCCESS) 334 goto out; 335 336 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_VH_1, 337 &hdcp->auth.msg.hdcp1.vp[4], 4); 338 if (status != MOD_HDCP_STATUS_SUCCESS) 339 goto out; 340 341 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_VH_2, 342 &hdcp->auth.msg.hdcp1.vp[8], 4); 343 if (status != MOD_HDCP_STATUS_SUCCESS) 344 goto out; 345 346 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_VH_3, 347 &hdcp->auth.msg.hdcp1.vp[12], 4); 348 if (status != MOD_HDCP_STATUS_SUCCESS) 349 goto out; 350 351 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_VH_4, 352 &hdcp->auth.msg.hdcp1.vp[16], 4); 353 out: 354 return status; 355 } 356 357 enum mod_hdcp_status mod_hdcp_read_binfo(struct mod_hdcp *hdcp) 358 { 359 enum mod_hdcp_status status; 360 361 if (is_dp_hdcp(hdcp)) 362 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_BINFO, 363 (uint8_t *)&hdcp->auth.msg.hdcp1.binfo_dp, 364 sizeof(hdcp->auth.msg.hdcp1.binfo_dp)); 365 else 366 status = MOD_HDCP_STATUS_INVALID_OPERATION; 367 368 return status; 369 } 370 371 enum mod_hdcp_status mod_hdcp_write_aksv(struct mod_hdcp *hdcp) 372 { 373 return write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AKSV, 374 hdcp->auth.msg.hdcp1.aksv, 375 sizeof(hdcp->auth.msg.hdcp1.aksv)); 376 } 377 378 enum mod_hdcp_status mod_hdcp_write_ainfo(struct mod_hdcp *hdcp) 379 { 380 return write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AINFO, 381 &hdcp->auth.msg.hdcp1.ainfo, 382 sizeof(hdcp->auth.msg.hdcp1.ainfo)); 383 } 384 385 enum mod_hdcp_status mod_hdcp_write_an(struct mod_hdcp *hdcp) 386 { 387 return write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AN, 388 hdcp->auth.msg.hdcp1.an, 389 sizeof(hdcp->auth.msg.hdcp1.an)); 390 } 391 392 enum mod_hdcp_status mod_hdcp_read_hdcp2version(struct mod_hdcp *hdcp) 393 { 394 enum mod_hdcp_status status; 395 396 if (is_dp_hdcp(hdcp)) 397 status = MOD_HDCP_STATUS_INVALID_OPERATION; 398 else 399 status = read(hdcp, MOD_HDCP_MESSAGE_ID_HDCP2VERSION, 400 &hdcp->auth.msg.hdcp2.hdcp2version_hdmi, 401 sizeof(hdcp->auth.msg.hdcp2.hdcp2version_hdmi)); 402 403 return status; 404 } 405 406 enum mod_hdcp_status mod_hdcp_read_rxcaps(struct mod_hdcp *hdcp) 407 { 408 enum mod_hdcp_status status; 409 410 if (!is_dp_hdcp(hdcp)) 411 status = MOD_HDCP_STATUS_INVALID_OPERATION; 412 else 413 status = read(hdcp, MOD_HDCP_MESSAGE_ID_RX_CAPS, 414 hdcp->auth.msg.hdcp2.rxcaps_dp, 415 sizeof(hdcp->auth.msg.hdcp2.rxcaps_dp)); 416 417 return status; 418 } 419 420 enum mod_hdcp_status mod_hdcp_read_rxstatus(struct mod_hdcp *hdcp) 421 { 422 enum mod_hdcp_status status; 423 424 if (is_dp_hdcp(hdcp)) { 425 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_RXSTATUS, 426 &hdcp->auth.msg.hdcp2.rxstatus_dp, 427 1); 428 } else { 429 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_RXSTATUS, 430 (uint8_t *)&hdcp->auth.msg.hdcp2.rxstatus, 431 sizeof(hdcp->auth.msg.hdcp2.rxstatus)); 432 } 433 return status; 434 } 435 436 enum mod_hdcp_status mod_hdcp_read_ake_cert(struct mod_hdcp *hdcp) 437 { 438 enum mod_hdcp_status status; 439 440 if (is_dp_hdcp(hdcp)) { 441 hdcp->auth.msg.hdcp2.ake_cert[0] = HDCP_2_2_AKE_SEND_CERT; 442 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_CERT, 443 hdcp->auth.msg.hdcp2.ake_cert+1, 444 sizeof(hdcp->auth.msg.hdcp2.ake_cert)-1); 445 446 } else { 447 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_CERT, 448 hdcp->auth.msg.hdcp2.ake_cert, 449 sizeof(hdcp->auth.msg.hdcp2.ake_cert)); 450 } 451 return status; 452 } 453 454 enum mod_hdcp_status mod_hdcp_read_h_prime(struct mod_hdcp *hdcp) 455 { 456 enum mod_hdcp_status status; 457 458 if (is_dp_hdcp(hdcp)) { 459 hdcp->auth.msg.hdcp2.ake_h_prime[0] = HDCP_2_2_AKE_SEND_HPRIME; 460 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_H_PRIME, 461 hdcp->auth.msg.hdcp2.ake_h_prime+1, 462 sizeof(hdcp->auth.msg.hdcp2.ake_h_prime)-1); 463 464 } else { 465 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_H_PRIME, 466 hdcp->auth.msg.hdcp2.ake_h_prime, 467 sizeof(hdcp->auth.msg.hdcp2.ake_h_prime)); 468 } 469 return status; 470 } 471 472 enum mod_hdcp_status mod_hdcp_read_pairing_info(struct mod_hdcp *hdcp) 473 { 474 enum mod_hdcp_status status; 475 476 if (is_dp_hdcp(hdcp)) { 477 hdcp->auth.msg.hdcp2.ake_pairing_info[0] = HDCP_2_2_AKE_SEND_PAIRING_INFO; 478 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_PAIRING_INFO, 479 hdcp->auth.msg.hdcp2.ake_pairing_info+1, 480 sizeof(hdcp->auth.msg.hdcp2.ake_pairing_info)-1); 481 482 } else { 483 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_AKE_SEND_PAIRING_INFO, 484 hdcp->auth.msg.hdcp2.ake_pairing_info, 485 sizeof(hdcp->auth.msg.hdcp2.ake_pairing_info)); 486 } 487 return status; 488 } 489 490 enum mod_hdcp_status mod_hdcp_read_l_prime(struct mod_hdcp *hdcp) 491 { 492 enum mod_hdcp_status status; 493 494 if (is_dp_hdcp(hdcp)) { 495 hdcp->auth.msg.hdcp2.lc_l_prime[0] = HDCP_2_2_LC_SEND_LPRIME; 496 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_LC_SEND_L_PRIME, 497 hdcp->auth.msg.hdcp2.lc_l_prime+1, 498 sizeof(hdcp->auth.msg.hdcp2.lc_l_prime)-1); 499 500 } else { 501 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_LC_SEND_L_PRIME, 502 hdcp->auth.msg.hdcp2.lc_l_prime, 503 sizeof(hdcp->auth.msg.hdcp2.lc_l_prime)); 504 } 505 return status; 506 } 507 508 enum mod_hdcp_status mod_hdcp_read_rx_id_list(struct mod_hdcp *hdcp) 509 { 510 enum mod_hdcp_status status = MOD_HDCP_STATUS_SUCCESS; 511 512 if (is_dp_hdcp(hdcp)) { 513 uint32_t device_count = 0; 514 uint32_t rx_id_list_size = 0; 515 uint32_t bytes_read = 0; 516 517 hdcp->auth.msg.hdcp2.rx_id_list[0] = HDCP_2_2_REP_SEND_RECVID_LIST; 518 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST, 519 hdcp->auth.msg.hdcp2.rx_id_list+1, 520 HDCP_MAX_AUX_TRANSACTION_SIZE); 521 if (status == MOD_HDCP_STATUS_SUCCESS) { 522 bytes_read = HDCP_MAX_AUX_TRANSACTION_SIZE; 523 device_count = HDCP_2_2_DEV_COUNT_LO(hdcp->auth.msg.hdcp2.rx_id_list[2]) + 524 (HDCP_2_2_DEV_COUNT_HI(hdcp->auth.msg.hdcp2.rx_id_list[1]) << 4); 525 rx_id_list_size = MIN((21 + 5 * device_count), 526 (sizeof(hdcp->auth.msg.hdcp2.rx_id_list) - 1)); 527 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST_PART2, 528 hdcp->auth.msg.hdcp2.rx_id_list + 1 + bytes_read, 529 (rx_id_list_size - 1) / HDCP_MAX_AUX_TRANSACTION_SIZE * HDCP_MAX_AUX_TRANSACTION_SIZE); 530 } 531 } else { 532 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_SEND_RECEIVERID_LIST, 533 hdcp->auth.msg.hdcp2.rx_id_list, 534 hdcp->auth.msg.hdcp2.rx_id_list_size); 535 } 536 return status; 537 } 538 539 enum mod_hdcp_status mod_hdcp_read_stream_ready(struct mod_hdcp *hdcp) 540 { 541 enum mod_hdcp_status status; 542 543 if (is_dp_hdcp(hdcp)) { 544 hdcp->auth.msg.hdcp2.repeater_auth_stream_ready[0] = HDCP_2_2_REP_STREAM_READY; 545 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_STREAM_READY, 546 hdcp->auth.msg.hdcp2.repeater_auth_stream_ready+1, 547 sizeof(hdcp->auth.msg.hdcp2.repeater_auth_stream_ready)-1); 548 549 } else { 550 status = read(hdcp, MOD_HDCP_MESSAGE_ID_READ_REPEATER_AUTH_STREAM_READY, 551 hdcp->auth.msg.hdcp2.repeater_auth_stream_ready, 552 sizeof(hdcp->auth.msg.hdcp2.repeater_auth_stream_ready)); 553 } 554 return status; 555 } 556 557 enum mod_hdcp_status mod_hdcp_write_ake_init(struct mod_hdcp *hdcp) 558 { 559 enum mod_hdcp_status status; 560 561 if (is_dp_hdcp(hdcp)) 562 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AKE_INIT, 563 hdcp->auth.msg.hdcp2.ake_init+1, 564 sizeof(hdcp->auth.msg.hdcp2.ake_init)-1); 565 else 566 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AKE_INIT, 567 hdcp->auth.msg.hdcp2.ake_init, 568 sizeof(hdcp->auth.msg.hdcp2.ake_init)); 569 return status; 570 } 571 572 enum mod_hdcp_status mod_hdcp_write_no_stored_km(struct mod_hdcp *hdcp) 573 { 574 enum mod_hdcp_status status; 575 576 if (is_dp_hdcp(hdcp)) 577 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AKE_NO_STORED_KM, 578 hdcp->auth.msg.hdcp2.ake_no_stored_km+1, 579 sizeof(hdcp->auth.msg.hdcp2.ake_no_stored_km)-1); 580 else 581 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AKE_NO_STORED_KM, 582 hdcp->auth.msg.hdcp2.ake_no_stored_km, 583 sizeof(hdcp->auth.msg.hdcp2.ake_no_stored_km)); 584 return status; 585 } 586 587 enum mod_hdcp_status mod_hdcp_write_stored_km(struct mod_hdcp *hdcp) 588 { 589 enum mod_hdcp_status status; 590 591 if (is_dp_hdcp(hdcp)) 592 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AKE_STORED_KM, 593 hdcp->auth.msg.hdcp2.ake_stored_km+1, 594 sizeof(hdcp->auth.msg.hdcp2.ake_stored_km)-1); 595 else 596 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_AKE_STORED_KM, 597 hdcp->auth.msg.hdcp2.ake_stored_km, 598 sizeof(hdcp->auth.msg.hdcp2.ake_stored_km)); 599 return status; 600 } 601 602 enum mod_hdcp_status mod_hdcp_write_lc_init(struct mod_hdcp *hdcp) 603 { 604 enum mod_hdcp_status status; 605 606 if (is_dp_hdcp(hdcp)) 607 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_LC_INIT, 608 hdcp->auth.msg.hdcp2.lc_init+1, 609 sizeof(hdcp->auth.msg.hdcp2.lc_init)-1); 610 else 611 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_LC_INIT, 612 hdcp->auth.msg.hdcp2.lc_init, 613 sizeof(hdcp->auth.msg.hdcp2.lc_init)); 614 return status; 615 } 616 617 enum mod_hdcp_status mod_hdcp_write_eks(struct mod_hdcp *hdcp) 618 { 619 enum mod_hdcp_status status; 620 621 if (is_dp_hdcp(hdcp)) 622 status = write(hdcp, 623 MOD_HDCP_MESSAGE_ID_WRITE_SKE_SEND_EKS, 624 hdcp->auth.msg.hdcp2.ske_eks+1, 625 sizeof(hdcp->auth.msg.hdcp2.ske_eks)-1); 626 else 627 status = write(hdcp, 628 MOD_HDCP_MESSAGE_ID_WRITE_SKE_SEND_EKS, 629 hdcp->auth.msg.hdcp2.ske_eks, 630 sizeof(hdcp->auth.msg.hdcp2.ske_eks)); 631 return status; 632 } 633 634 enum mod_hdcp_status mod_hdcp_write_repeater_auth_ack(struct mod_hdcp *hdcp) 635 { 636 enum mod_hdcp_status status; 637 638 if (is_dp_hdcp(hdcp)) 639 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_SEND_ACK, 640 hdcp->auth.msg.hdcp2.repeater_auth_ack+1, 641 sizeof(hdcp->auth.msg.hdcp2.repeater_auth_ack)-1); 642 else 643 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_SEND_ACK, 644 hdcp->auth.msg.hdcp2.repeater_auth_ack, 645 sizeof(hdcp->auth.msg.hdcp2.repeater_auth_ack)); 646 return status; 647 } 648 649 enum mod_hdcp_status mod_hdcp_write_stream_manage(struct mod_hdcp *hdcp) 650 { 651 enum mod_hdcp_status status; 652 653 if (is_dp_hdcp(hdcp)) 654 status = write(hdcp, 655 MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_STREAM_MANAGE, 656 hdcp->auth.msg.hdcp2.repeater_auth_stream_manage+1, 657 hdcp->auth.msg.hdcp2.stream_manage_size-1); 658 else 659 status = write(hdcp, 660 MOD_HDCP_MESSAGE_ID_WRITE_REPEATER_AUTH_STREAM_MANAGE, 661 hdcp->auth.msg.hdcp2.repeater_auth_stream_manage, 662 hdcp->auth.msg.hdcp2.stream_manage_size); 663 return status; 664 } 665 666 enum mod_hdcp_status mod_hdcp_write_content_type(struct mod_hdcp *hdcp) 667 { 668 enum mod_hdcp_status status; 669 670 if (is_dp_hdcp(hdcp)) 671 status = write(hdcp, MOD_HDCP_MESSAGE_ID_WRITE_CONTENT_STREAM_TYPE, 672 hdcp->auth.msg.hdcp2.content_stream_type_dp+1, 673 sizeof(hdcp->auth.msg.hdcp2.content_stream_type_dp)-1); 674 else 675 status = MOD_HDCP_STATUS_INVALID_OPERATION; 676 return status; 677 } 678 679 enum mod_hdcp_status mod_hdcp_clear_cp_irq_status(struct mod_hdcp *hdcp) 680 { 681 uint8_t clear_cp_irq_bit = DP_CP_IRQ; 682 uint32_t size = 1; 683 684 if (is_dp_hdcp(hdcp)) { 685 uint32_t cp_irq_addrs = (hdcp->connection.link.dp.rev >= 0x14) 686 ? DP_DEVICE_SERVICE_IRQ_VECTOR_ESI0:DP_DEVICE_SERVICE_IRQ_VECTOR; 687 return hdcp->config.ddc.funcs.write_dpcd(hdcp->config.ddc.handle, cp_irq_addrs, 688 &clear_cp_irq_bit, size) ? MOD_HDCP_STATUS_SUCCESS : MOD_HDCP_STATUS_DDC_FAILURE; 689 } 690 691 return MOD_HDCP_STATUS_INVALID_OPERATION; 692 } 693