1 // SPDX-License-Identifier: MIT 2 /* 3 * Copyright 2023, Intel Corporation. 4 */ 5 6 #include <linux/err.h> 7 8 #include <drm/drm_print.h> 9 #include <drm/intel/i915_hdcp_interface.h> 10 11 #include "intel_display_core.h" 12 #include "intel_display_types.h" 13 #include "intel_hdcp_gsc_message.h" 14 #include "intel_parent.h" 15 16 static int 17 intel_hdcp_gsc_initiate_session(struct device *dev, struct hdcp_port_data *data, 18 struct hdcp2_ake_init *ake_data) 19 { 20 struct wired_cmd_initiate_hdcp2_session_in session_init_in = {}; 21 struct wired_cmd_initiate_hdcp2_session_out session_init_out = {}; 22 struct intel_hdcp_gsc_context *gsc_context; 23 struct intel_display *display; 24 ssize_t byte; 25 26 if (!dev || !data || !ake_data) 27 return -EINVAL; 28 29 display = to_intel_display(dev); 30 if (!display) { 31 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 32 return -ENODEV; 33 } 34 gsc_context = display->hdcp.gsc_context; 35 36 session_init_in.header.api_version = HDCP_API_VERSION; 37 session_init_in.header.command_id = WIRED_INITIATE_HDCP2_SESSION; 38 session_init_in.header.status = FW_HDCP_STATUS_SUCCESS; 39 session_init_in.header.buffer_len = 40 WIRED_CMD_BUF_LEN_INITIATE_HDCP2_SESSION_IN; 41 42 session_init_in.port.integrated_port_type = data->port_type; 43 session_init_in.port.physical_port = (u8)data->hdcp_ddi; 44 session_init_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 45 session_init_in.protocol = data->protocol; 46 47 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 48 &session_init_in, sizeof(session_init_in), 49 &session_init_out, sizeof(session_init_out)); 50 if (byte < 0) { 51 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 52 return byte; 53 } 54 55 if (session_init_out.header.status != FW_HDCP_STATUS_SUCCESS) { 56 drm_dbg_kms(display->drm, "FW cmd 0x%08X Failed. Status: 0x%X\n", 57 WIRED_INITIATE_HDCP2_SESSION, 58 session_init_out.header.status); 59 return -EIO; 60 } 61 62 ake_data->msg_id = HDCP_2_2_AKE_INIT; 63 ake_data->tx_caps = session_init_out.tx_caps; 64 memcpy(ake_data->r_tx, session_init_out.r_tx, HDCP_2_2_RTX_LEN); 65 66 return 0; 67 } 68 69 static int 70 intel_hdcp_gsc_verify_receiver_cert_prepare_km(struct device *dev, 71 struct hdcp_port_data *data, 72 struct hdcp2_ake_send_cert *rx_cert, 73 bool *km_stored, 74 struct hdcp2_ake_no_stored_km 75 *ek_pub_km, 76 size_t *msg_sz) 77 { 78 struct wired_cmd_verify_receiver_cert_in verify_rxcert_in = {}; 79 struct wired_cmd_verify_receiver_cert_out verify_rxcert_out = {}; 80 struct intel_hdcp_gsc_context *gsc_context; 81 struct intel_display *display; 82 ssize_t byte; 83 84 if (!dev || !data || !rx_cert || !km_stored || !ek_pub_km || !msg_sz) 85 return -EINVAL; 86 87 display = to_intel_display(dev); 88 if (!display) { 89 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 90 return -ENODEV; 91 } 92 gsc_context = display->hdcp.gsc_context; 93 94 verify_rxcert_in.header.api_version = HDCP_API_VERSION; 95 verify_rxcert_in.header.command_id = WIRED_VERIFY_RECEIVER_CERT; 96 verify_rxcert_in.header.status = FW_HDCP_STATUS_SUCCESS; 97 verify_rxcert_in.header.buffer_len = 98 WIRED_CMD_BUF_LEN_VERIFY_RECEIVER_CERT_IN; 99 100 verify_rxcert_in.port.integrated_port_type = data->port_type; 101 verify_rxcert_in.port.physical_port = (u8)data->hdcp_ddi; 102 verify_rxcert_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 103 104 verify_rxcert_in.cert_rx = rx_cert->cert_rx; 105 memcpy(verify_rxcert_in.r_rx, &rx_cert->r_rx, HDCP_2_2_RRX_LEN); 106 memcpy(verify_rxcert_in.rx_caps, rx_cert->rx_caps, HDCP_2_2_RXCAPS_LEN); 107 108 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 109 &verify_rxcert_in, sizeof(verify_rxcert_in), 110 &verify_rxcert_out, sizeof(verify_rxcert_out)); 111 if (byte < 0) { 112 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed: %zd\n", byte); 113 return byte; 114 } 115 116 if (verify_rxcert_out.header.status != FW_HDCP_STATUS_SUCCESS) { 117 drm_dbg_kms(display->drm, "FW cmd 0x%08X Failed. Status: 0x%X\n", 118 WIRED_VERIFY_RECEIVER_CERT, 119 verify_rxcert_out.header.status); 120 return -EIO; 121 } 122 123 *km_stored = !!verify_rxcert_out.km_stored; 124 if (verify_rxcert_out.km_stored) { 125 ek_pub_km->msg_id = HDCP_2_2_AKE_STORED_KM; 126 *msg_sz = sizeof(struct hdcp2_ake_stored_km); 127 } else { 128 ek_pub_km->msg_id = HDCP_2_2_AKE_NO_STORED_KM; 129 *msg_sz = sizeof(struct hdcp2_ake_no_stored_km); 130 } 131 132 memcpy(ek_pub_km->e_kpub_km, &verify_rxcert_out.ekm_buff, 133 sizeof(verify_rxcert_out.ekm_buff)); 134 135 return 0; 136 } 137 138 static int 139 intel_hdcp_gsc_verify_hprime(struct device *dev, struct hdcp_port_data *data, 140 struct hdcp2_ake_send_hprime *rx_hprime) 141 { 142 struct wired_cmd_ake_send_hprime_in send_hprime_in = {}; 143 struct wired_cmd_ake_send_hprime_out send_hprime_out = {}; 144 struct intel_hdcp_gsc_context *gsc_context; 145 struct intel_display *display; 146 ssize_t byte; 147 148 if (!dev || !data || !rx_hprime) 149 return -EINVAL; 150 151 display = to_intel_display(dev); 152 if (!display) { 153 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 154 return -ENODEV; 155 } 156 gsc_context = display->hdcp.gsc_context; 157 158 send_hprime_in.header.api_version = HDCP_API_VERSION; 159 send_hprime_in.header.command_id = WIRED_AKE_SEND_HPRIME; 160 send_hprime_in.header.status = FW_HDCP_STATUS_SUCCESS; 161 send_hprime_in.header.buffer_len = WIRED_CMD_BUF_LEN_AKE_SEND_HPRIME_IN; 162 163 send_hprime_in.port.integrated_port_type = data->port_type; 164 send_hprime_in.port.physical_port = (u8)data->hdcp_ddi; 165 send_hprime_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 166 167 memcpy(send_hprime_in.h_prime, rx_hprime->h_prime, 168 HDCP_2_2_H_PRIME_LEN); 169 170 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 171 &send_hprime_in, sizeof(send_hprime_in), 172 &send_hprime_out, sizeof(send_hprime_out)); 173 if (byte < 0) { 174 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 175 return byte; 176 } 177 178 if (send_hprime_out.header.status != FW_HDCP_STATUS_SUCCESS) { 179 drm_dbg_kms(display->drm, "FW cmd 0x%08X Failed. Status: 0x%X\n", 180 WIRED_AKE_SEND_HPRIME, send_hprime_out.header.status); 181 return -EIO; 182 } 183 184 return 0; 185 } 186 187 static int 188 intel_hdcp_gsc_store_pairing_info(struct device *dev, struct hdcp_port_data *data, 189 struct hdcp2_ake_send_pairing_info *pairing_info) 190 { 191 struct wired_cmd_ake_send_pairing_info_in pairing_info_in = {}; 192 struct wired_cmd_ake_send_pairing_info_out pairing_info_out = {}; 193 struct intel_hdcp_gsc_context *gsc_context; 194 struct intel_display *display; 195 ssize_t byte; 196 197 if (!dev || !data || !pairing_info) 198 return -EINVAL; 199 200 display = to_intel_display(dev); 201 if (!display) { 202 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 203 return -ENODEV; 204 } 205 gsc_context = display->hdcp.gsc_context; 206 207 pairing_info_in.header.api_version = HDCP_API_VERSION; 208 pairing_info_in.header.command_id = WIRED_AKE_SEND_PAIRING_INFO; 209 pairing_info_in.header.status = FW_HDCP_STATUS_SUCCESS; 210 pairing_info_in.header.buffer_len = 211 WIRED_CMD_BUF_LEN_SEND_PAIRING_INFO_IN; 212 213 pairing_info_in.port.integrated_port_type = data->port_type; 214 pairing_info_in.port.physical_port = (u8)data->hdcp_ddi; 215 pairing_info_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 216 217 memcpy(pairing_info_in.e_kh_km, pairing_info->e_kh_km, 218 HDCP_2_2_E_KH_KM_LEN); 219 220 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 221 &pairing_info_in, sizeof(pairing_info_in), 222 &pairing_info_out, sizeof(pairing_info_out)); 223 if (byte < 0) { 224 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 225 return byte; 226 } 227 228 if (pairing_info_out.header.status != FW_HDCP_STATUS_SUCCESS) { 229 drm_dbg_kms(display->drm, "FW cmd 0x%08X failed. Status: 0x%X\n", 230 WIRED_AKE_SEND_PAIRING_INFO, 231 pairing_info_out.header.status); 232 return -EIO; 233 } 234 235 return 0; 236 } 237 238 static int 239 intel_hdcp_gsc_initiate_locality_check(struct device *dev, 240 struct hdcp_port_data *data, 241 struct hdcp2_lc_init *lc_init_data) 242 { 243 struct wired_cmd_init_locality_check_in lc_init_in = {}; 244 struct wired_cmd_init_locality_check_out lc_init_out = {}; 245 struct intel_hdcp_gsc_context *gsc_context; 246 struct intel_display *display; 247 ssize_t byte; 248 249 if (!dev || !data || !lc_init_data) 250 return -EINVAL; 251 252 display = to_intel_display(dev); 253 if (!display) { 254 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 255 return -ENODEV; 256 } 257 gsc_context = display->hdcp.gsc_context; 258 259 lc_init_in.header.api_version = HDCP_API_VERSION; 260 lc_init_in.header.command_id = WIRED_INIT_LOCALITY_CHECK; 261 lc_init_in.header.status = FW_HDCP_STATUS_SUCCESS; 262 lc_init_in.header.buffer_len = WIRED_CMD_BUF_LEN_INIT_LOCALITY_CHECK_IN; 263 264 lc_init_in.port.integrated_port_type = data->port_type; 265 lc_init_in.port.physical_port = (u8)data->hdcp_ddi; 266 lc_init_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 267 268 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 269 &lc_init_in, sizeof(lc_init_in), 270 &lc_init_out, sizeof(lc_init_out)); 271 if (byte < 0) { 272 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 273 return byte; 274 } 275 276 if (lc_init_out.header.status != FW_HDCP_STATUS_SUCCESS) { 277 drm_dbg_kms(display->drm, "FW cmd 0x%08X Failed. status: 0x%X\n", 278 WIRED_INIT_LOCALITY_CHECK, lc_init_out.header.status); 279 return -EIO; 280 } 281 282 lc_init_data->msg_id = HDCP_2_2_LC_INIT; 283 memcpy(lc_init_data->r_n, lc_init_out.r_n, HDCP_2_2_RN_LEN); 284 285 return 0; 286 } 287 288 static int 289 intel_hdcp_gsc_verify_lprime(struct device *dev, struct hdcp_port_data *data, 290 struct hdcp2_lc_send_lprime *rx_lprime) 291 { 292 struct wired_cmd_validate_locality_in verify_lprime_in = {}; 293 struct wired_cmd_validate_locality_out verify_lprime_out = {}; 294 struct intel_hdcp_gsc_context *gsc_context; 295 struct intel_display *display; 296 ssize_t byte; 297 298 if (!dev || !data || !rx_lprime) 299 return -EINVAL; 300 301 display = to_intel_display(dev); 302 if (!display) { 303 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 304 return -ENODEV; 305 } 306 gsc_context = display->hdcp.gsc_context; 307 308 verify_lprime_in.header.api_version = HDCP_API_VERSION; 309 verify_lprime_in.header.command_id = WIRED_VALIDATE_LOCALITY; 310 verify_lprime_in.header.status = FW_HDCP_STATUS_SUCCESS; 311 verify_lprime_in.header.buffer_len = 312 WIRED_CMD_BUF_LEN_VALIDATE_LOCALITY_IN; 313 314 verify_lprime_in.port.integrated_port_type = data->port_type; 315 verify_lprime_in.port.physical_port = (u8)data->hdcp_ddi; 316 verify_lprime_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 317 318 memcpy(verify_lprime_in.l_prime, rx_lprime->l_prime, 319 HDCP_2_2_L_PRIME_LEN); 320 321 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 322 &verify_lprime_in, sizeof(verify_lprime_in), 323 &verify_lprime_out, sizeof(verify_lprime_out)); 324 if (byte < 0) { 325 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 326 return byte; 327 } 328 329 if (verify_lprime_out.header.status != FW_HDCP_STATUS_SUCCESS) { 330 drm_dbg_kms(display->drm, "FW cmd 0x%08X failed. status: 0x%X\n", 331 WIRED_VALIDATE_LOCALITY, 332 verify_lprime_out.header.status); 333 return -EIO; 334 } 335 336 return 0; 337 } 338 339 static int 340 intel_hdcp_gsc_get_session_key(struct device *dev, 341 struct hdcp_port_data *data, 342 struct hdcp2_ske_send_eks *ske_data) 343 { 344 struct wired_cmd_get_session_key_in get_skey_in = {}; 345 struct wired_cmd_get_session_key_out get_skey_out = {}; 346 struct intel_hdcp_gsc_context *gsc_context; 347 struct intel_display *display; 348 ssize_t byte; 349 350 if (!dev || !data || !ske_data) 351 return -EINVAL; 352 353 display = to_intel_display(dev); 354 if (!display) { 355 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 356 return -ENODEV; 357 } 358 gsc_context = display->hdcp.gsc_context; 359 360 get_skey_in.header.api_version = HDCP_API_VERSION; 361 get_skey_in.header.command_id = WIRED_GET_SESSION_KEY; 362 get_skey_in.header.status = FW_HDCP_STATUS_SUCCESS; 363 get_skey_in.header.buffer_len = WIRED_CMD_BUF_LEN_GET_SESSION_KEY_IN; 364 365 get_skey_in.port.integrated_port_type = data->port_type; 366 get_skey_in.port.physical_port = (u8)data->hdcp_ddi; 367 get_skey_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 368 369 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 370 &get_skey_in, sizeof(get_skey_in), 371 &get_skey_out, sizeof(get_skey_out)); 372 if (byte < 0) { 373 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 374 return byte; 375 } 376 377 if (get_skey_out.header.status != FW_HDCP_STATUS_SUCCESS) { 378 drm_dbg_kms(display->drm, "FW cmd 0x%08X failed. status: 0x%X\n", 379 WIRED_GET_SESSION_KEY, get_skey_out.header.status); 380 return -EIO; 381 } 382 383 ske_data->msg_id = HDCP_2_2_SKE_SEND_EKS; 384 memcpy(ske_data->e_dkey_ks, get_skey_out.e_dkey_ks, 385 HDCP_2_2_E_DKEY_KS_LEN); 386 memcpy(ske_data->riv, get_skey_out.r_iv, HDCP_2_2_RIV_LEN); 387 388 return 0; 389 } 390 391 static int 392 intel_hdcp_gsc_repeater_check_flow_prepare_ack(struct device *dev, 393 struct hdcp_port_data *data, 394 struct hdcp2_rep_send_receiverid_list 395 *rep_topology, 396 struct hdcp2_rep_send_ack 397 *rep_send_ack) 398 { 399 struct wired_cmd_verify_repeater_in verify_repeater_in = {}; 400 struct wired_cmd_verify_repeater_out verify_repeater_out = {}; 401 struct intel_hdcp_gsc_context *gsc_context; 402 struct intel_display *display; 403 ssize_t byte; 404 405 if (!dev || !rep_topology || !rep_send_ack || !data) 406 return -EINVAL; 407 408 display = to_intel_display(dev); 409 if (!display) { 410 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 411 return -ENODEV; 412 } 413 gsc_context = display->hdcp.gsc_context; 414 415 verify_repeater_in.header.api_version = HDCP_API_VERSION; 416 verify_repeater_in.header.command_id = WIRED_VERIFY_REPEATER; 417 verify_repeater_in.header.status = FW_HDCP_STATUS_SUCCESS; 418 verify_repeater_in.header.buffer_len = 419 WIRED_CMD_BUF_LEN_VERIFY_REPEATER_IN; 420 421 verify_repeater_in.port.integrated_port_type = data->port_type; 422 verify_repeater_in.port.physical_port = (u8)data->hdcp_ddi; 423 verify_repeater_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 424 425 memcpy(verify_repeater_in.rx_info, rep_topology->rx_info, 426 HDCP_2_2_RXINFO_LEN); 427 memcpy(verify_repeater_in.seq_num_v, rep_topology->seq_num_v, 428 HDCP_2_2_SEQ_NUM_LEN); 429 memcpy(verify_repeater_in.v_prime, rep_topology->v_prime, 430 HDCP_2_2_V_PRIME_HALF_LEN); 431 memcpy(verify_repeater_in.receiver_ids, rep_topology->receiver_ids, 432 HDCP_2_2_RECEIVER_IDS_MAX_LEN); 433 434 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 435 &verify_repeater_in, sizeof(verify_repeater_in), 436 &verify_repeater_out, sizeof(verify_repeater_out)); 437 if (byte < 0) { 438 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 439 return byte; 440 } 441 442 if (verify_repeater_out.header.status != FW_HDCP_STATUS_SUCCESS) { 443 drm_dbg_kms(display->drm, "FW cmd 0x%08X failed. status: 0x%X\n", 444 WIRED_VERIFY_REPEATER, 445 verify_repeater_out.header.status); 446 return -EIO; 447 } 448 449 memcpy(rep_send_ack->v, verify_repeater_out.v, 450 HDCP_2_2_V_PRIME_HALF_LEN); 451 rep_send_ack->msg_id = HDCP_2_2_REP_SEND_ACK; 452 453 return 0; 454 } 455 456 static int 457 intel_hdcp_gsc_verify_mprime(struct device *dev, 458 struct hdcp_port_data *data, 459 struct hdcp2_rep_stream_ready *stream_ready) 460 { 461 struct wired_cmd_repeater_auth_stream_req_in *verify_mprime_in; 462 struct wired_cmd_repeater_auth_stream_req_out verify_mprime_out = {}; 463 struct intel_hdcp_gsc_context *gsc_context; 464 struct intel_display *display; 465 ssize_t byte; 466 size_t cmd_size; 467 468 if (!dev || !stream_ready || !data) 469 return -EINVAL; 470 471 display = to_intel_display(dev); 472 if (!display) { 473 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 474 return -ENODEV; 475 } 476 gsc_context = display->hdcp.gsc_context; 477 478 cmd_size = struct_size(verify_mprime_in, streams, data->k); 479 if (cmd_size == SIZE_MAX) 480 return -EINVAL; 481 482 verify_mprime_in = kzalloc(cmd_size, GFP_KERNEL); 483 if (!verify_mprime_in) 484 return -ENOMEM; 485 486 verify_mprime_in->header.api_version = HDCP_API_VERSION; 487 verify_mprime_in->header.command_id = WIRED_REPEATER_AUTH_STREAM_REQ; 488 verify_mprime_in->header.status = FW_HDCP_STATUS_SUCCESS; 489 verify_mprime_in->header.buffer_len = cmd_size - sizeof(verify_mprime_in->header); 490 491 verify_mprime_in->port.integrated_port_type = data->port_type; 492 verify_mprime_in->port.physical_port = (u8)data->hdcp_ddi; 493 verify_mprime_in->port.attached_transcoder = (u8)data->hdcp_transcoder; 494 495 memcpy(verify_mprime_in->m_prime, stream_ready->m_prime, HDCP_2_2_MPRIME_LEN); 496 drm_hdcp_cpu_to_be24(verify_mprime_in->seq_num_m, data->seq_num_m); 497 498 memcpy(verify_mprime_in->streams, data->streams, 499 array_size(data->k, sizeof(*data->streams))); 500 501 verify_mprime_in->k = cpu_to_be16(data->k); 502 503 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 504 verify_mprime_in, cmd_size, 505 &verify_mprime_out, sizeof(verify_mprime_out)); 506 kfree(verify_mprime_in); 507 if (byte < 0) { 508 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 509 return byte; 510 } 511 512 if (verify_mprime_out.header.status != FW_HDCP_STATUS_SUCCESS) { 513 drm_dbg_kms(display->drm, "FW cmd 0x%08X failed. status: 0x%X\n", 514 WIRED_REPEATER_AUTH_STREAM_REQ, 515 verify_mprime_out.header.status); 516 return -EIO; 517 } 518 519 return 0; 520 } 521 522 static int intel_hdcp_gsc_enable_authentication(struct device *dev, 523 struct hdcp_port_data *data) 524 { 525 struct wired_cmd_enable_auth_in enable_auth_in = {}; 526 struct wired_cmd_enable_auth_out enable_auth_out = {}; 527 struct intel_hdcp_gsc_context *gsc_context; 528 struct intel_display *display; 529 ssize_t byte; 530 531 if (!dev || !data) 532 return -EINVAL; 533 534 display = to_intel_display(dev); 535 if (!display) { 536 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 537 return -ENODEV; 538 } 539 gsc_context = display->hdcp.gsc_context; 540 541 enable_auth_in.header.api_version = HDCP_API_VERSION; 542 enable_auth_in.header.command_id = WIRED_ENABLE_AUTH; 543 enable_auth_in.header.status = FW_HDCP_STATUS_SUCCESS; 544 enable_auth_in.header.buffer_len = WIRED_CMD_BUF_LEN_ENABLE_AUTH_IN; 545 546 enable_auth_in.port.integrated_port_type = data->port_type; 547 enable_auth_in.port.physical_port = (u8)data->hdcp_ddi; 548 enable_auth_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 549 enable_auth_in.stream_type = data->streams[0].stream_type; 550 551 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 552 &enable_auth_in, sizeof(enable_auth_in), 553 &enable_auth_out, sizeof(enable_auth_out)); 554 if (byte < 0) { 555 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 556 return byte; 557 } 558 559 if (enable_auth_out.header.status != FW_HDCP_STATUS_SUCCESS) { 560 drm_dbg_kms(display->drm, "FW cmd 0x%08X failed. status: 0x%X\n", 561 WIRED_ENABLE_AUTH, enable_auth_out.header.status); 562 return -EIO; 563 } 564 565 return 0; 566 } 567 568 static int 569 intel_hdcp_gsc_close_session(struct device *dev, struct hdcp_port_data *data) 570 { 571 struct wired_cmd_close_session_in session_close_in = {}; 572 struct wired_cmd_close_session_out session_close_out = {}; 573 struct intel_hdcp_gsc_context *gsc_context; 574 struct intel_display *display; 575 ssize_t byte; 576 577 if (!dev || !data) 578 return -EINVAL; 579 580 display = to_intel_display(dev); 581 if (!display) { 582 dev_err(dev, "DRM not initialized, aborting HDCP.\n"); 583 return -ENODEV; 584 } 585 gsc_context = display->hdcp.gsc_context; 586 587 session_close_in.header.api_version = HDCP_API_VERSION; 588 session_close_in.header.command_id = WIRED_CLOSE_SESSION; 589 session_close_in.header.status = FW_HDCP_STATUS_SUCCESS; 590 session_close_in.header.buffer_len = 591 WIRED_CMD_BUF_LEN_CLOSE_SESSION_IN; 592 593 session_close_in.port.integrated_port_type = data->port_type; 594 session_close_in.port.physical_port = (u8)data->hdcp_ddi; 595 session_close_in.port.attached_transcoder = (u8)data->hdcp_transcoder; 596 597 byte = intel_parent_hdcp_gsc_msg_send(display, gsc_context, 598 &session_close_in, sizeof(session_close_in), 599 &session_close_out, sizeof(session_close_out)); 600 if (byte < 0) { 601 drm_dbg_kms(display->drm, "intel_hdcp_gsc_msg_send failed. %zd\n", byte); 602 return byte; 603 } 604 605 if (session_close_out.header.status != FW_HDCP_STATUS_SUCCESS) { 606 drm_dbg_kms(display->drm, "Session Close Failed. status: 0x%X\n", 607 session_close_out.header.status); 608 return -EIO; 609 } 610 611 return 0; 612 } 613 614 static const struct i915_hdcp_ops gsc_hdcp_ops = { 615 .initiate_hdcp2_session = intel_hdcp_gsc_initiate_session, 616 .verify_receiver_cert_prepare_km = 617 intel_hdcp_gsc_verify_receiver_cert_prepare_km, 618 .verify_hprime = intel_hdcp_gsc_verify_hprime, 619 .store_pairing_info = intel_hdcp_gsc_store_pairing_info, 620 .initiate_locality_check = intel_hdcp_gsc_initiate_locality_check, 621 .verify_lprime = intel_hdcp_gsc_verify_lprime, 622 .get_session_key = intel_hdcp_gsc_get_session_key, 623 .repeater_check_flow_prepare_ack = 624 intel_hdcp_gsc_repeater_check_flow_prepare_ack, 625 .verify_mprime = intel_hdcp_gsc_verify_mprime, 626 .enable_hdcp_authentication = intel_hdcp_gsc_enable_authentication, 627 .close_hdcp_session = intel_hdcp_gsc_close_session, 628 }; 629 630 int intel_hdcp_gsc_init(struct intel_display *display) 631 { 632 struct intel_hdcp_gsc_context *gsc_context; 633 struct i915_hdcp_arbiter *arbiter; 634 int ret = 0; 635 636 arbiter = kzalloc_obj(*arbiter); 637 if (!arbiter) 638 return -ENOMEM; 639 640 mutex_lock(&display->hdcp.hdcp_mutex); 641 642 gsc_context = intel_parent_hdcp_gsc_context_alloc(display); 643 if (IS_ERR(gsc_context)) { 644 ret = PTR_ERR(gsc_context); 645 kfree(arbiter); 646 goto out; 647 } 648 649 display->hdcp.arbiter = arbiter; 650 display->hdcp.arbiter->hdcp_dev = display->drm->dev; 651 display->hdcp.arbiter->ops = &gsc_hdcp_ops; 652 display->hdcp.gsc_context = gsc_context; 653 654 out: 655 mutex_unlock(&display->hdcp.hdcp_mutex); 656 657 return ret; 658 } 659 660 void intel_hdcp_gsc_fini(struct intel_display *display) 661 { 662 intel_parent_hdcp_gsc_context_free(display, display->hdcp.gsc_context); 663 display->hdcp.gsc_context = NULL; 664 kfree(display->hdcp.arbiter); 665 display->hdcp.arbiter = NULL; 666 } 667