blob: 13175d04183354ab4ad2b18ade33d5a5dd1599f0 [file] [log] [blame]
Sankeerth Billakanti37886d92019-01-24 18:01:28 +05301/* Copyright (c) 2015-2019, The Linux Foundation. All rights reserved.
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07002 *
3 * This program is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License version 2 and
5 * only version 2 as published by the Free Software Foundation.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 * GNU General Public License for more details.
11 */
12
13#define pr_fmt(fmt) "[hdcp-lib] %s: " fmt, __func__
14
15#include <linux/platform_device.h>
16#include <linux/kernel.h>
17#include <linux/slab.h>
18#include <linux/module.h>
19#include <linux/fs.h>
20#include <linux/file.h>
21#include <linux/uaccess.h>
22#include <linux/cdev.h>
23#include <linux/sched.h>
24#include <linux/list.h>
25#include <linux/mutex.h>
26#include <linux/io.h>
27#include <linux/ion.h>
28#include <linux/types.h>
29#include <linux/device.h>
30#include <linux/sched.h>
31#include <linux/delay.h>
32#include <linux/completion.h>
33#include <linux/errno.h>
34#include <linux/hdcp_qseecom.h>
35#include <linux/kthread.h>
36#include <linux/of.h>
37#include <video/msm_hdmi_hdcp_mgr.h>
38
39#include "qseecom_kernel.h"
40
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -070041#define TZAPP_NAME "hdcp2p2"
42#define HDCP1_APP_NAME "hdcp1"
43#define QSEECOM_SBUFF_SIZE 0x1000
44
45#define MAX_TX_MESSAGE_SIZE 129
46#define MAX_RX_MESSAGE_SIZE 534
47#define MAX_TOPOLOGY_ELEMS 32
48#define HDCP1_AKSV_SIZE 8
49
50/* parameters related to LC_Init message */
51#define MESSAGE_ID_SIZE 1
52#define LC_INIT_MESSAGE_SIZE (MESSAGE_ID_SIZE+BITS_64_IN_BYTES)
53
54/* parameters related to SKE_Send_EKS message */
55#define SKE_SEND_EKS_MESSAGE_SIZE \
56 (MESSAGE_ID_SIZE+BITS_128_IN_BYTES+BITS_64_IN_BYTES)
57
58/* all message IDs */
59#define INVALID_MESSAGE_ID 0
60#define AKE_INIT_MESSAGE_ID 2
61#define AKE_SEND_CERT_MESSAGE_ID 3
62#define AKE_NO_STORED_KM_MESSAGE_ID 4
63#define AKE_STORED_KM_MESSAGE_ID 5
64#define AKE_SEND_H_PRIME_MESSAGE_ID 7
65#define AKE_SEND_PAIRING_INFO_MESSAGE_ID 8
66#define LC_INIT_MESSAGE_ID 9
67#define LC_SEND_L_PRIME_MESSAGE_ID 10
68#define SKE_SEND_EKS_MESSAGE_ID 11
69#define REPEATER_AUTH_SEND_RECEIVERID_LIST_MESSAGE_ID 12
70#define REPEATER_AUTH_SEND_ACK_MESSAGE_ID 15
71#define REPEATER_AUTH_STREAM_MANAGE_MESSAGE_ID 16
72#define REPEATER_AUTH_STREAM_READY_MESSAGE_ID 17
73#define SKE_SEND_TYPE_ID 18
74#define HDCP2P2_MAX_MESSAGES 19
75
76#define HDCP1_SET_KEY_MESSAGE_ID 202
77#define HDCP1_SET_ENC_MESSAGE_ID 205
78
79#define BITS_40_IN_BYTES 5
80#define BITS_64_IN_BYTES 8
81#define BITS_128_IN_BYTES 16
82#define RXCAPS_SIZE 3
83#define RXINFO_SIZE 2
84#define SEQ_NUM_V_SIZE 3
85
86#define RCVR_ID_SIZE BITS_40_IN_BYTES
87#define MAX_RCVR_IDS_ALLOWED_IN_LIST 31
88#define MAX_RCVR_ID_LIST_SIZE \
89 (RCVR_ID_SIZE * MAX_RCVR_IDS_ALLOWED_IN_LIST)
90/*
91 * Minimum wait as per standard is 200 ms. Keep it 220 ms
92 * to be on safe side.
93 */
94#define SLEEP_SET_HW_KEY_MS 220
95
96/* hdcp command status */
97#define HDCP_SUCCESS 0
98
99/* flags set by tz in response message */
100#define HDCP_TXMTR_SUBSTATE_WAITING_FOR_RECIEVERID_LIST 1
101
102#define HDCP_TXMTR_SERVICE_ID 0x0001000
103#define SERVICE_CREATE_CMD(x) (HDCP_TXMTR_SERVICE_ID | x)
104
105#define HDCP_TXMTR_INIT SERVICE_CREATE_CMD(1)
106#define HDCP_TXMTR_DEINIT SERVICE_CREATE_CMD(2)
107#define HDCP_TXMTR_PROCESS_RECEIVED_MESSAGE SERVICE_CREATE_CMD(3)
108#define HDCP_TXMTR_SEND_MESSAGE_TIMEOUT SERVICE_CREATE_CMD(4)
109#define HDCP_TXMTR_SET_HW_KEY SERVICE_CREATE_CMD(5)
110#define HDCP_TXMTR_QUERY_STREAM_TYPE SERVICE_CREATE_CMD(6)
111#define HDCP_LIB_INIT SERVICE_CREATE_CMD(11)
112#define HDCP_LIB_DEINIT SERVICE_CREATE_CMD(12)
113#define HDCP_TXMTR_GET_VERSION SERVICE_CREATE_CMD(14)
114#define HDCP_TXMTR_VERIFY_KEY SERVICE_CREATE_CMD(15)
115#define HDCP_SESSION_INIT SERVICE_CREATE_CMD(16)
116#define HDCP_SESSION_DEINIT SERVICE_CREATE_CMD(17)
117#define HDCP_TXMTR_START_AUTHENTICATE SERVICE_CREATE_CMD(18)
118
119#define HCDP_TXMTR_GET_MAJOR_VERSION(v) (((v) >> 16) & 0xFF)
120#define HCDP_TXMTR_GET_MINOR_VERSION(v) (((v) >> 8) & 0xFF)
121#define HCDP_TXMTR_GET_PATCH_VERSION(v) ((v) & 0xFF)
122
123#define HDCP_CLIENT_MAJOR_VERSION 2
124#define HDCP_CLIENT_MINOR_VERSION 1
125#define HDCP_CLIENT_PATCH_VERSION 0
126#define HDCP_CLIENT_MAKE_VERSION(maj, min, patch) \
127 ((((maj) & 0xFF) << 16) | (((min) & 0xFF) << 8) | ((patch) & 0xFF))
128
129#define REAUTH_REQ BIT(3)
130#define LINK_INTEGRITY_FAILURE BIT(4)
131
132#define HDCP_LIB_EXECUTE(x) {\
133 kthread_queue_work(&handle->worker, &handle->wk_##x);\
134}
135
136static const struct hdcp_msg_data hdcp_msg_lookup[HDCP2P2_MAX_MESSAGES] = {
137 [AKE_INIT_MESSAGE_ID] = { 2,
138 { {"rtx", 0x69000, 8}, {"TxCaps", 0x69008, 3} },
139 0 },
140 [AKE_SEND_CERT_MESSAGE_ID] = { 3,
141 { {"cert-rx", 0x6900B, 522}, {"rrx", 0x69215, 8},
142 {"RxCaps", 0x6921D, 3} },
143 0 },
144 [AKE_NO_STORED_KM_MESSAGE_ID] = { 1,
145 { {"Ekpub_km", 0x69220, 128} },
146 0 },
147 [AKE_STORED_KM_MESSAGE_ID] = { 2,
148 { {"Ekh_km", 0x692A0, 16}, {"m", 0x692B0, 16} },
149 0 },
150 [AKE_SEND_H_PRIME_MESSAGE_ID] = { 1,
151 { {"H'", 0x692C0, 32} },
152 (1 << 1) },
153 [AKE_SEND_PAIRING_INFO_MESSAGE_ID] = { 1,
154 { {"Ekh_km", 0x692E0, 16} },
155 (1 << 2) },
156 [LC_INIT_MESSAGE_ID] = { 1,
157 { {"rn", 0x692F0, 8} },
158 0 },
159 [LC_SEND_L_PRIME_MESSAGE_ID] = { 1,
160 { {"L'", 0x692F8, 32} },
161 0 },
162 [SKE_SEND_EKS_MESSAGE_ID] = { 2,
163 { {"Edkey_ks", 0x69318, 16}, {"riv", 0x69328, 8} },
164 0 },
165 [SKE_SEND_TYPE_ID] = { 1,
166 { {"type", 0x69494, 1} },
167 0 },
168 [REPEATER_AUTH_SEND_RECEIVERID_LIST_MESSAGE_ID] = { 4,
169 { {"RxInfo", 0x69330, 2}, {"seq_num_V", 0x69332, 3},
170 {"V'", 0x69335, 16}, {"ridlist", 0x69345, 155} },
171 (1 << 0) },
172 [REPEATER_AUTH_SEND_ACK_MESSAGE_ID] = { 1,
173 { {"V", 0x693E0, 16} },
174 0 },
175 [REPEATER_AUTH_STREAM_MANAGE_MESSAGE_ID] = { 3,
176 { {"seq_num_M", 0x693F0, 3}, {"k", 0x693F3, 2},
177 {"streamID_Type", 0x693F5, 126} },
178 0 },
179 [REPEATER_AUTH_STREAM_READY_MESSAGE_ID] = { 1,
180 { {"M'", 0x69473, 32} },
181 0 }
182};
183
184enum hdcp_state {
185 HDCP_STATE_INIT = 0x00,
186 HDCP_STATE_APP_LOADED = 0x01,
187 HDCP_STATE_SESSION_INIT = 0x02,
188 HDCP_STATE_TXMTR_INIT = 0x04,
189 HDCP_STATE_AUTHENTICATED = 0x08,
190 HDCP_STATE_ERROR = 0x10
191};
192
193enum hdcp_element {
194 HDCP_TYPE_UNKNOWN,
195 HDCP_TYPE_RECEIVER,
196 HDCP_TYPE_REPEATER,
197};
198
199enum hdcp_version {
200 HDCP_VERSION_UNKNOWN,
201 HDCP_VERSION_2_2,
202 HDCP_VERSION_1_4
203};
204
205struct receiver_info {
206 unsigned char rcvrInfo[RCVR_ID_SIZE];
207 enum hdcp_element elem_type;
208 enum hdcp_version hdcp_version;
209};
210
211struct topology_info {
212 unsigned int nNumRcvrs;
213 struct receiver_info rcvinfo[MAX_TOPOLOGY_ELEMS];
214};
215
216struct __attribute__ ((__packed__)) hdcp1_key_set_req {
217 uint32_t commandid;
218};
219
220struct __attribute__ ((__packed__)) hdcp1_key_set_rsp {
221 uint32_t commandid;
222 uint32_t ret;
223 uint8_t ksv[HDCP1_AKSV_SIZE];
224};
225
226struct __attribute__ ((__packed__)) hdcp_version_req {
227 uint32_t commandid;
228};
229
230struct __attribute__ ((__packed__)) hdcp_version_rsp {
231 uint32_t commandid;
232 uint32_t commandId;
233 uint32_t appversion;
234};
235
236struct __attribute__ ((__packed__)) hdcp_verify_key_req {
237 uint32_t commandid;
238};
239
240struct __attribute__ ((__packed__)) hdcp_verify_key_rsp {
241 uint32_t status;
242 uint32_t commandId;
243};
244
245struct __attribute__ ((__packed__)) hdcp_lib_init_req_v1 {
246 uint32_t commandid;
247};
248
249struct __attribute__ ((__packed__)) hdcp_lib_init_rsp_v1 {
250 uint32_t status;
251 uint32_t commandid;
252 uint32_t ctxhandle;
253 uint32_t timeout;
254 uint32_t msglen;
255 uint8_t message[MAX_TX_MESSAGE_SIZE];
256};
257
258struct __attribute__ ((__packed__)) hdcp_lib_init_req {
259 uint32_t commandid;
260 uint32_t clientversion;
261};
262
263struct __attribute__ ((__packed__)) hdcp_lib_init_rsp {
264 uint32_t status;
265 uint32_t commandid;
266 uint32_t appversion;
267};
268
269struct __attribute__ ((__packed__)) hdcp_lib_deinit_req {
270 uint32_t commandid;
271};
272
273struct __attribute__ ((__packed__)) hdcp_lib_deinit_rsp {
274 uint32_t status;
275 uint32_t commandid;
276};
277
278struct __attribute__ ((__packed__)) hdcp_lib_session_init_req {
279 uint32_t commandid;
280 uint32_t deviceid;
281};
282
283struct __attribute__ ((__packed__)) hdcp_lib_session_init_rsp {
284 uint32_t status;
285 uint32_t commandid;
286 uint32_t sessionid;
287};
288
289struct __attribute__ ((__packed__)) hdcp_lib_session_deinit_req {
290 uint32_t commandid;
291 uint32_t sessionid;
292};
293
294struct __attribute__ ((__packed__)) hdcp_lib_session_deinit_rsp {
295 uint32_t status;
296 uint32_t commandid;
297};
298
299struct __attribute__ ((__packed__)) hdcp_tx_init_req_v1 {
300 uint32_t commandid;
301};
302
303struct __attribute__ ((__packed__)) hdcp_tx_init_rsp_v1 {
304 uint32_t status;
305 uint32_t commandid;
306 uint32_t ctxhandle;
307 uint32_t timeout;
308 uint32_t msglen;
309 uint8_t message[MAX_TX_MESSAGE_SIZE];
310};
311
312struct __attribute__ ((__packed__)) hdcp_tx_init_req {
313 uint32_t commandid;
314 uint32_t sessionid;
315};
316
317struct __attribute__ ((__packed__)) hdcp_tx_init_rsp {
318 uint32_t status;
319 uint32_t commandid;
320 uint32_t ctxhandle;
321};
322
323struct __attribute__ ((__packed__)) hdcp_deinit_req {
324 uint32_t commandid;
325 uint32_t ctxhandle;
326};
327
328struct __attribute__ ((__packed__)) hdcp_deinit_rsp {
329 uint32_t status;
330 uint32_t commandid;
331};
332
333struct __attribute__ ((__packed__)) hdcp_rcvd_msg_req {
334 uint32_t commandid;
335 uint32_t ctxhandle;
336 uint32_t msglen;
337 uint8_t msg[MAX_RX_MESSAGE_SIZE];
338};
339
340struct __attribute__ ((__packed__)) hdcp_rcvd_msg_rsp {
341 uint32_t status;
342 uint32_t commandid;
343 uint32_t state;
344 uint32_t timeout;
345 uint32_t flag;
346 uint32_t msglen;
347 uint8_t msg[MAX_TX_MESSAGE_SIZE];
348};
349
350struct __attribute__ ((__packed__)) hdcp_set_hw_key_req {
351 uint32_t commandid;
352 uint32_t ctxhandle;
353};
354
355struct __attribute__ ((__packed__)) hdcp_set_hw_key_rsp {
356 uint32_t status;
357 uint32_t commandid;
358};
359
360struct __attribute__ ((__packed__)) hdcp_send_timeout_req {
361 uint32_t commandid;
362 uint32_t ctxhandle;
363};
364
365struct __attribute__ ((__packed__)) hdcp_send_timeout_rsp {
366 uint32_t status;
367 uint32_t commandid;
368 uint32_t timeout;
369 uint32_t msglen;
370 uint8_t message[MAX_TX_MESSAGE_SIZE];
371};
372
373struct __attribute__ ((__packed__)) hdcp_query_stream_type_req {
374 uint32_t commandid;
375 uint32_t ctxhandle;
376};
377
378struct __attribute__ ((__packed__)) hdcp_query_stream_type_rsp {
379 uint32_t status;
380 uint32_t commandid;
381 uint32_t timeout;
382 uint32_t msglen;
383 uint8_t msg[MAX_TX_MESSAGE_SIZE];
384};
385
386struct __attribute__ ((__packed__)) hdcp_set_stream_type_req {
387 uint32_t commandid;
388 uint32_t ctxhandle;
389 uint8_t streamtype;
390};
391
392struct __attribute__ ((__packed__)) hdcp_set_stream_type_rsp {
393 uint32_t status;
394 uint32_t commandid;
395 uint32_t timeout;
396 uint32_t msglen;
397 uint8_t message[MAX_TX_MESSAGE_SIZE];
398};
399
400struct __attribute__ ((__packed__)) hdcp_update_srm_req {
401 uint32_t commandid;
402 uint32_t ctxhandle;
403 uint32_t srmoffset;
404 uint32_t srmlength;
405};
406
407struct __attribute__ ((__packed__)) hdcp_update_srm_rsp {
408 uint32_t status;
409 uint32_t commandid;
410};
411
412struct __attribute__ ((__packed__)) hdcp_get_topology_req {
413 uint32_t commandid;
414 uint32_t ctxhandle;
415};
416
417struct __attribute__ ((__packed__)) hdcp_get_topology_rsp {
418 uint32_t status;
419 uint32_t commandid;
420 struct topology_info topologyinfo;
421};
422
423struct __attribute__ ((__packed__)) rxvr_info_struct {
424 uint8_t rcvrCert[522];
425 uint8_t rrx[BITS_64_IN_BYTES];
426 uint8_t rxcaps[RXCAPS_SIZE];
427 bool repeater;
428};
429
430struct __attribute__ ((__packed__)) repeater_info_struct {
431 uint8_t RxInfo[RXINFO_SIZE];
432 uint8_t seq_num_V[SEQ_NUM_V_SIZE];
433 bool seq_num_V_Rollover_flag;
434 uint8_t ReceiverIDList[MAX_RCVR_ID_LIST_SIZE];
435 uint32_t ReceiverIDListLen;
436};
437
438struct __attribute__ ((__packed__)) hdcp1_set_enc_req {
439 uint32_t commandid;
440 uint32_t enable;
441};
442
443struct __attribute__ ((__packed__)) hdcp1_set_enc_rsp {
444 uint32_t commandid;
445 uint32_t ret;
446};
447
448struct __attribute__ ((__packed__)) hdcp_start_auth_req {
449 uint32_t commandid;
450 uint32_t ctxHandle;
451};
452
453struct __attribute__ ((__packed__)) hdcp_start_auth_rsp {
454 uint32_t status;
455 uint32_t commandid;
456 uint32_t ctxhandle;
457 uint32_t timeout;
458 uint32_t msglen;
459 uint8_t message[MAX_TX_MESSAGE_SIZE];
460};
461
462struct hdcp_lib_handle {
463 unsigned char *listener_buf;
464 uint32_t msglen;
465 uint32_t tz_ctxhandle;
466 uint32_t hdcp_timeout;
467 uint32_t timeout_left;
468 uint32_t wait_timeout;
469 bool no_stored_km_flag;
470 bool feature_supported;
471 bool authenticated;
472 void *client_ctx;
473 struct hdcp_client_ops *client_ops;
474 struct mutex msg_lock;
475 struct mutex wakeup_mutex;
476 enum hdcp_state hdcp_state;
477 enum hdcp_lib_wakeup_cmd wakeup_cmd;
478 bool repeater_flag;
479 bool update_stream;
480 struct qseecom_handle *qseecom_handle;
481 int last_msg_sent;
482 int last_msg;
483 char *last_msg_recvd_buf;
484 uint32_t last_msg_recvd_len;
485 atomic_t hdcp_off;
486 uint32_t session_id;
487 enum hdcp_device_type device_type;
488
489 struct task_struct *thread;
490 struct completion poll_wait;
491
492 struct kthread_worker worker;
493 struct kthread_work wk_init;
494 struct kthread_work wk_msg_sent;
495 struct kthread_work wk_msg_recvd;
496 struct kthread_work wk_timeout;
497 struct kthread_work wk_clean;
498 struct kthread_work wk_wait;
499 struct kthread_work wk_stream;
500
501 int (*hdcp_app_init)(struct hdcp_lib_handle *handle);
502 int (*hdcp_txmtr_init)(struct hdcp_lib_handle *handle);
503};
504
505struct hdcp_lib_message_map {
506 int msg_id;
507 const char *msg_name;
508};
509
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -0700510static void hdcp_lib_clean(struct hdcp_lib_handle *handle);
511static void hdcp_lib_init(struct hdcp_lib_handle *handle);
512static void hdcp_lib_msg_sent(struct hdcp_lib_handle *handle);
513static void hdcp_lib_msg_recvd(struct hdcp_lib_handle *handle);
514static void hdcp_lib_timeout(struct hdcp_lib_handle *handle);
515static void hdcp_lib_stream(struct hdcp_lib_handle *handle);
516static int hdcp_lib_txmtr_init(struct hdcp_lib_handle *handle);
517
518static struct qseecom_handle *hdcp1_handle;
519static bool hdcp1_supported = true;
520static bool hdcp1_enc_enabled;
521static struct mutex hdcp1_ta_cmd_lock;
522
523static const char *hdcp_lib_message_name(int msg_id)
524{
525 /*
526 * Message ID map. The first number indicates the message number
527 * assigned to the message by the HDCP 2.2 spec. This is also the first
528 * byte of every HDCP 2.2 authentication protocol message.
529 */
530 static struct hdcp_lib_message_map hdcp_lib_msg_map[] = {
531 {2, "AKE_INIT"},
532 {3, "AKE_SEND_CERT"},
533 {4, "AKE_NO_STORED_KM"},
534 {5, "AKE_STORED_KM"},
535 {7, "AKE_SEND_H_PRIME"},
536 {8, "AKE_SEND_PAIRING_INFO"},
537 {9, "LC_INIT"},
538 {10, "LC_SEND_L_PRIME"},
539 {11, "SKE_SEND_EKS"},
540 {12, "REPEATER_AUTH_SEND_RECEIVERID_LIST"},
541 {15, "REPEATER_AUTH_SEND_ACK"},
542 {16, "REPEATER_AUTH_STREAM_MANAGE"},
543 {17, "REPEATER_AUTH_STREAM_READY"},
544 {18, "SKE_SEND_TYPE_ID"},
545 };
546 int i;
547
548 for (i = 0; i < ARRAY_SIZE(hdcp_lib_msg_map); i++) {
549 if (msg_id == hdcp_lib_msg_map[i].msg_id)
550 return hdcp_lib_msg_map[i].msg_name;
551 }
552 return "UNKNOWN";
553}
554
555static int hdcp_lib_get_next_message(struct hdcp_lib_handle *handle,
556 struct hdcp_wakeup_data *data)
557{
558 switch (handle->last_msg) {
559 case INVALID_MESSAGE_ID:
560 return AKE_INIT_MESSAGE_ID;
561 case AKE_INIT_MESSAGE_ID:
562 return AKE_SEND_CERT_MESSAGE_ID;
563 case AKE_SEND_CERT_MESSAGE_ID:
564 if (handle->no_stored_km_flag)
565 return AKE_NO_STORED_KM_MESSAGE_ID;
566 else
567 return AKE_STORED_KM_MESSAGE_ID;
568 case AKE_STORED_KM_MESSAGE_ID:
569 case AKE_NO_STORED_KM_MESSAGE_ID:
570 return AKE_SEND_H_PRIME_MESSAGE_ID;
571 case AKE_SEND_H_PRIME_MESSAGE_ID:
572 if (handle->no_stored_km_flag)
573 return AKE_SEND_PAIRING_INFO_MESSAGE_ID;
574 else
575 return LC_INIT_MESSAGE_ID;
576 case AKE_SEND_PAIRING_INFO_MESSAGE_ID:
577 return LC_INIT_MESSAGE_ID;
578 case LC_INIT_MESSAGE_ID:
579 return LC_SEND_L_PRIME_MESSAGE_ID;
580 case LC_SEND_L_PRIME_MESSAGE_ID:
581 return SKE_SEND_EKS_MESSAGE_ID;
582 case SKE_SEND_EKS_MESSAGE_ID:
583 if (!handle->repeater_flag)
584 return SKE_SEND_TYPE_ID;
585 case SKE_SEND_TYPE_ID:
586 case REPEATER_AUTH_STREAM_READY_MESSAGE_ID:
587 case REPEATER_AUTH_SEND_ACK_MESSAGE_ID:
588 if (!handle->repeater_flag)
589 return INVALID_MESSAGE_ID;
590
591 if (data->cmd == HDCP_WKUP_CMD_SEND_MESSAGE)
592 return REPEATER_AUTH_STREAM_MANAGE_MESSAGE_ID;
593 else
594 return REPEATER_AUTH_SEND_RECEIVERID_LIST_MESSAGE_ID;
595 case REPEATER_AUTH_SEND_RECEIVERID_LIST_MESSAGE_ID:
596 return REPEATER_AUTH_SEND_ACK_MESSAGE_ID;
597 case REPEATER_AUTH_STREAM_MANAGE_MESSAGE_ID:
598 return REPEATER_AUTH_STREAM_READY_MESSAGE_ID;
599 default:
600 pr_err("Uknown message ID (%d)", handle->last_msg);
601 return -EINVAL;
602 }
603}
604
605static void hdcp_lib_wait_for_response(struct hdcp_lib_handle *handle,
606 struct hdcp_wakeup_data *data)
607{
608 switch (handle->last_msg) {
609 case AKE_SEND_H_PRIME_MESSAGE_ID:
610 if (handle->no_stored_km_flag)
611 handle->wait_timeout = HZ;
612 else
613 handle->wait_timeout = HZ / 4;
614 break;
615 case AKE_SEND_PAIRING_INFO_MESSAGE_ID:
616 handle->wait_timeout = HZ / 4;
617 break;
618 case REPEATER_AUTH_SEND_RECEIVERID_LIST_MESSAGE_ID:
619 if (!handle->authenticated)
620 handle->wait_timeout = HZ * 3;
621 else
622 handle->wait_timeout = 0;
623 break;
624 default:
625 handle->wait_timeout = 0;
626 }
627
628 if (handle->wait_timeout)
629 kthread_queue_work(&handle->worker, &handle->wk_wait);
630}
631
632static void hdcp_lib_wakeup_client(struct hdcp_lib_handle *handle,
633 struct hdcp_wakeup_data *data)
634{
635 int rc = 0, i;
636
637 if (!handle || !handle->client_ops || !handle->client_ops->wakeup ||
638 !data || (data->cmd == HDCP_WKUP_CMD_INVALID))
639 return;
640
641 data->abort_mask = REAUTH_REQ | LINK_INTEGRITY_FAILURE;
642
643 if (data->cmd == HDCP_WKUP_CMD_RECV_MESSAGE ||
644 data->cmd == HDCP_WKUP_CMD_LINK_POLL)
645 handle->last_msg = hdcp_lib_get_next_message(handle, data);
646
647 if (handle->last_msg != INVALID_MESSAGE_ID &&
648 data->cmd != HDCP_WKUP_CMD_STATUS_SUCCESS &&
649 data->cmd != HDCP_WKUP_CMD_STATUS_FAILED) {
650 u32 msg_num, rx_status;
651 const struct hdcp_msg_part *msg;
652
653 pr_debug("lib->client: %s (%s)\n",
654 hdcp_cmd_to_str(data->cmd),
655 hdcp_lib_message_name(handle->last_msg));
656
657 data->message_data = &hdcp_msg_lookup[handle->last_msg];
658
659 msg_num = data->message_data->num_messages;
660 msg = data->message_data->messages;
661 rx_status = data->message_data->rx_status;
662
663 pr_debug("%10s | %6s | %4s\n", "name", "offset", "len");
664
665 for (i = 0; i < msg_num; i++)
666 pr_debug("%10s | %6x | %4d\n",
667 msg[i].name, msg[i].offset,
668 msg[i].length);
669 } else {
670 pr_debug("lib->client: %s\n", hdcp_cmd_to_str(data->cmd));
671 }
672
673 rc = handle->client_ops->wakeup(data);
674 if (rc)
675 pr_err("error sending %s to client\n",
676 hdcp_cmd_to_str(data->cmd));
677
678 hdcp_lib_wait_for_response(handle, data);
679}
680
681static inline void hdcp_lib_send_message(struct hdcp_lib_handle *handle)
682{
683 char msg_name[50];
684 struct hdcp_wakeup_data cdata = {
685 HDCP_WKUP_CMD_SEND_MESSAGE
686 };
687
688 cdata.context = handle->client_ctx;
689 cdata.send_msg_buf = handle->listener_buf;
690 cdata.send_msg_len = handle->msglen;
691 cdata.timeout = handle->hdcp_timeout;
692
693 snprintf(msg_name, sizeof(msg_name), "%s: ",
694 hdcp_lib_message_name((int)cdata.send_msg_buf[0]));
695
696 print_hex_dump(KERN_DEBUG, msg_name,
697 DUMP_PREFIX_NONE, 16, 1, cdata.send_msg_buf,
698 cdata.send_msg_len, false);
699
700 hdcp_lib_wakeup_client(handle, &cdata);
701}
702
703static int hdcp_lib_enable_encryption(struct hdcp_lib_handle *handle)
704{
705 int rc = 0;
706 struct hdcp_set_hw_key_req *req_buf;
707 struct hdcp_set_hw_key_rsp *rsp_buf;
708
709 if (!handle || !handle->qseecom_handle ||
710 !handle->qseecom_handle->sbuf) {
711 pr_err("invalid handle\n");
712 rc = -EINVAL;
713 goto error;
714 }
715
716 /*
717 * wait at least 200ms before enabling encryption
718 * as per hdcp2p2 sepcifications.
719 */
720 msleep(SLEEP_SET_HW_KEY_MS);
721
722 req_buf = (struct hdcp_set_hw_key_req *)(handle->qseecom_handle->sbuf);
723 req_buf->commandid = HDCP_TXMTR_SET_HW_KEY;
724 req_buf->ctxhandle = handle->tz_ctxhandle;
725
726 rsp_buf = (struct hdcp_set_hw_key_rsp *)
727 (handle->qseecom_handle->sbuf +
728 QSEECOM_ALIGN(sizeof(struct hdcp_set_hw_key_req)));
729
730 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
731 QSEECOM_ALIGN(sizeof
732 (struct hdcp_set_hw_key_req)),
733 rsp_buf,
734 QSEECOM_ALIGN(sizeof
735 (struct hdcp_set_hw_key_rsp)));
736
Tatenda Chipeperekwa8a77c8a2018-01-30 14:50:11 -0800737 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS)) {
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -0700738 pr_err("qseecom cmd failed with err = %d status = %d\n",
739 rc, rsp_buf->status);
740 rc = -EINVAL;
741 goto error;
742 }
743
744 /* reached an authenticated state */
745 handle->hdcp_state |= HDCP_STATE_AUTHENTICATED;
746
747 pr_debug("success\n");
748 return 0;
749error:
750 if (handle && !atomic_read(&handle->hdcp_off))
751 HDCP_LIB_EXECUTE(clean);
752
753 return rc;
754}
755
756static int hdcp_lib_get_version(struct hdcp_lib_handle *handle)
757{
758 int rc = 0;
759 struct hdcp_version_req *req_buf;
760 struct hdcp_version_rsp *rsp_buf;
761 uint32_t app_major_version = 0;
762
763 if (!handle) {
764 pr_err("invalid input\n");
765 rc = -EINVAL;
766 goto exit;
767 }
768
769 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
770 pr_err("library not loaded\n");
771 rc = -EINVAL;
772 goto exit;
773 }
774
775 /* get the TZ hdcp2p2 app version */
776 req_buf = (struct hdcp_version_req *)handle->qseecom_handle->sbuf;
777 req_buf->commandid = HDCP_TXMTR_GET_VERSION;
778
779 rsp_buf = (struct hdcp_version_rsp *)
780 (handle->qseecom_handle->sbuf +
781 QSEECOM_ALIGN(sizeof(struct hdcp_version_req)));
782
783 rc = qseecom_send_command(handle->qseecom_handle,
784 req_buf,
785 QSEECOM_ALIGN(sizeof
786 (struct hdcp_lib_init_req)),
787 rsp_buf,
788 QSEECOM_ALIGN(sizeof
789 (struct hdcp_lib_init_rsp)));
790
791 if (rc < 0) {
792 pr_err("qseecom cmd failed err = %d\n", rc);
793 goto exit;
794 }
795
796 app_major_version = HCDP_TXMTR_GET_MAJOR_VERSION(rsp_buf->appversion);
797
798 pr_debug("hdcp2p2 app major version %d, app version %d\n",
799 app_major_version, rsp_buf->appversion);
800
801exit:
802 return rc;
803}
804
805static int hdcp_lib_verify_keys(struct hdcp_lib_handle *handle)
806{
807 int rc = -EINVAL;
808 struct hdcp_verify_key_req *req_buf;
809 struct hdcp_verify_key_rsp *rsp_buf;
810
811 if (!handle) {
812 pr_err("invalid input\n");
813 goto exit;
814 }
815
816 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
817 pr_err("app not loaded\n");
818 goto exit;
819 }
820
821 req_buf = (struct hdcp_verify_key_req *)handle->qseecom_handle->sbuf;
822 req_buf->commandid = HDCP_TXMTR_VERIFY_KEY;
823
824 rsp_buf = (struct hdcp_verify_key_rsp *)
825 (handle->qseecom_handle->sbuf +
826 QSEECOM_ALIGN(sizeof(struct hdcp_verify_key_req)));
827
828 rc = qseecom_send_command(handle->qseecom_handle,
829 req_buf,
830 QSEECOM_ALIGN(sizeof
831 (struct hdcp_verify_key_req)),
832 rsp_buf,
833 QSEECOM_ALIGN(sizeof
834 (struct hdcp_verify_key_rsp)));
835
836 if (rc < 0) {
837 pr_err("qseecom cmd failed err = %d\n", rc);
838 goto exit;
839 }
840
841 return rsp_buf->status;
842exit:
843 return rc;
844}
845
846static int hdcp_app_init(struct hdcp_lib_handle *handle)
847{
848 int rc = 0;
849 struct hdcp_lib_init_req *req_buf;
850 struct hdcp_lib_init_rsp *rsp_buf;
851 uint32_t app_minor_version = 0;
852
853 if (!handle) {
854 pr_err("invalid input\n");
855 goto exit;
856 }
857
858 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
859 pr_err("library not loaded\n");
860 goto exit;
861 }
862
863 /* now load the app by sending hdcp_lib_init */
864 req_buf = (struct hdcp_lib_init_req *)handle->qseecom_handle->sbuf;
865 req_buf->commandid = HDCP_LIB_INIT;
866 req_buf->clientversion =
867 HDCP_CLIENT_MAKE_VERSION(HDCP_CLIENT_MAJOR_VERSION,
868 HDCP_CLIENT_MINOR_VERSION,
869 HDCP_CLIENT_PATCH_VERSION);
870 rsp_buf = (struct hdcp_lib_init_rsp *)
871 (handle->qseecom_handle->sbuf +
872 QSEECOM_ALIGN(sizeof(struct hdcp_lib_init_req)));
873
874 rc = qseecom_send_command(handle->qseecom_handle,
875 req_buf,
876 QSEECOM_ALIGN(sizeof
877 (struct hdcp_lib_init_req)),
878 rsp_buf,
879 QSEECOM_ALIGN(sizeof
880 (struct hdcp_lib_init_rsp)));
881
882 if (rc < 0) {
883 pr_err("qseecom cmd failed err = %d\n", rc);
884 goto exit;
885 }
886
887 app_minor_version = HCDP_TXMTR_GET_MINOR_VERSION(rsp_buf->appversion);
888 if (app_minor_version != HDCP_CLIENT_MINOR_VERSION) {
889 pr_err
890 ("client-app minor version mismatch app(%d), client(%d)\n",
891 app_minor_version, HDCP_CLIENT_MINOR_VERSION);
892 rc = -1;
893 goto exit;
894 }
895 pr_debug("success\n");
896 pr_debug("client version major(%d), minor(%d), patch(%d)\n",
897 HDCP_CLIENT_MAJOR_VERSION, HDCP_CLIENT_MINOR_VERSION,
898 HDCP_CLIENT_PATCH_VERSION);
899 pr_debug("app version major(%d), minor(%d), patch(%d)\n",
900 HCDP_TXMTR_GET_MAJOR_VERSION(rsp_buf->appversion),
901 HCDP_TXMTR_GET_MINOR_VERSION(rsp_buf->appversion),
902 HCDP_TXMTR_GET_PATCH_VERSION(rsp_buf->appversion));
903
904exit:
905 return rc;
906}
907
908static int hdcp_lib_library_load(struct hdcp_lib_handle *handle)
909{
910 int rc = 0;
911
912 if (!handle) {
913 pr_err("invalid input\n");
914 goto exit;
915 }
916
917 if (handle->hdcp_state & HDCP_STATE_APP_LOADED) {
918 pr_err("library already loaded\n");
919 goto exit;
920 }
921
922 /*
923 * allocating resource for qseecom handle
924 * the app is not loaded here
925 */
926 rc = qseecom_start_app(&(handle->qseecom_handle),
927 TZAPP_NAME, QSEECOM_SBUFF_SIZE);
928 if (rc) {
929 pr_err("qseecom_start_app failed %d\n", rc);
930 goto exit;
931 }
932
933 handle->hdcp_state |= HDCP_STATE_APP_LOADED;
934 pr_debug("qseecom_start_app success\n");
935
936 rc = hdcp_lib_get_version(handle);
937 if (rc) {
938 pr_err("library get version failed\n");
939 goto exit;
940 }
941
942 handle->hdcp_app_init = hdcp_app_init;
943 handle->hdcp_txmtr_init = hdcp_lib_txmtr_init;
944
945 if (handle->hdcp_app_init == NULL) {
946 pr_err("invalid app init function pointer\n");
947 goto exit;
948 }
949
950 rc = handle->hdcp_app_init(handle);
951 if (rc) {
952 pr_err("app init failed\n");
953 goto exit;
954 }
955exit:
956 return rc;
957}
958
959static int hdcp_lib_library_unload(struct hdcp_lib_handle *handle)
960{
961 int rc = 0;
962 struct hdcp_lib_deinit_req *req_buf;
963 struct hdcp_lib_deinit_rsp *rsp_buf;
964
965 if (!handle || !handle->qseecom_handle ||
966 !handle->qseecom_handle->sbuf) {
967 pr_err("invalid handle\n");
968 rc = -EINVAL;
969 goto exit;
970 }
971
972 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
973 pr_err("library not loaded\n");
974 return rc;
975 }
976
977 /* unloading app by sending hdcp_lib_deinit cmd */
978 req_buf = (struct hdcp_lib_deinit_req *)handle->qseecom_handle->sbuf;
979 req_buf->commandid = HDCP_LIB_DEINIT;
980 rsp_buf = (struct hdcp_lib_deinit_rsp *)
981 (handle->qseecom_handle->sbuf +
982 QSEECOM_ALIGN(sizeof(struct hdcp_lib_deinit_req)));
983
984 rc = qseecom_send_command(handle->qseecom_handle,
985 req_buf,
986 QSEECOM_ALIGN(sizeof
987 (struct hdcp_lib_deinit_req)),
988 rsp_buf,
989 QSEECOM_ALIGN(sizeof
990 (struct hdcp_lib_deinit_rsp)));
991
992 if (rc < 0) {
993 pr_err("qseecom cmd failed err = %d\n", rc);
994 goto exit;
995 }
996
997 /* deallocate the resources for qseecom handle */
998 rc = qseecom_shutdown_app(&handle->qseecom_handle);
999 if (rc) {
1000 pr_err("qseecom_shutdown_app failed err: %d\n", rc);
1001 goto exit;
1002 }
1003
1004 handle->hdcp_state &= ~HDCP_STATE_APP_LOADED;
1005 pr_debug("success\n");
1006exit:
1007 return rc;
1008}
1009
1010static int hdcp_lib_session_init(struct hdcp_lib_handle *handle)
1011{
1012 int rc = 0;
1013 struct hdcp_lib_session_init_req *req_buf;
1014 struct hdcp_lib_session_init_rsp *rsp_buf;
1015
1016 if (!handle || !handle->qseecom_handle ||
1017 !handle->qseecom_handle->sbuf) {
1018 pr_err("invalid handle\n");
1019 rc = -EINVAL;
1020 goto exit;
1021 }
1022
1023 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
1024 pr_err("app not loaded\n");
1025 goto exit;
1026 }
1027
1028 if (handle->hdcp_state & HDCP_STATE_SESSION_INIT) {
1029 pr_err("session already initialized\n");
1030 goto exit;
1031 }
1032
1033 /* send HDCP_Session_Init command to TZ */
1034 req_buf =
1035 (struct hdcp_lib_session_init_req *)handle->qseecom_handle->sbuf;
1036 req_buf->commandid = HDCP_SESSION_INIT;
1037 req_buf->deviceid = handle->device_type;
1038 rsp_buf = (struct hdcp_lib_session_init_rsp *)
1039 (handle->qseecom_handle->sbuf +
1040 QSEECOM_ALIGN(sizeof(struct hdcp_lib_session_init_req)));
1041
1042 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
1043 QSEECOM_ALIGN(sizeof
1044 (struct
1045 hdcp_lib_session_init_req)),
1046 rsp_buf,
1047 QSEECOM_ALIGN(sizeof
1048 (struct
1049 hdcp_lib_session_init_rsp)));
1050
1051 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS) ||
1052 (rsp_buf->commandid != HDCP_SESSION_INIT)) {
1053 pr_err("qseecom cmd failed with err = %d, status = %d\n",
1054 rc, rsp_buf->status);
1055 rc = -EINVAL;
1056 goto exit;
1057 }
1058
1059 pr_debug("session id %d\n", rsp_buf->sessionid);
1060
1061 handle->session_id = rsp_buf->sessionid;
1062 handle->hdcp_state |= HDCP_STATE_SESSION_INIT;
1063
1064 pr_debug("success\n");
1065exit:
1066 return rc;
1067}
1068
1069static int hdcp_lib_session_deinit(struct hdcp_lib_handle *handle)
1070{
1071 int rc = 0;
1072 struct hdcp_lib_session_deinit_req *req_buf;
1073 struct hdcp_lib_session_deinit_rsp *rsp_buf;
1074
1075 if (!handle || !handle->qseecom_handle ||
1076 !handle->qseecom_handle->sbuf) {
1077 pr_err("invalid handle\n");
1078 rc = -EINVAL;
1079 goto exit;
1080 }
1081
1082 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
1083 pr_err("app not loaded\n");
1084 goto exit;
1085 }
1086
1087 if (!(handle->hdcp_state & HDCP_STATE_SESSION_INIT)) {
1088 /* unload library here */
1089 pr_err("session not initialized\n");
1090 goto exit;
1091 }
1092
1093 /* send command to TZ */
1094 req_buf =
1095 (struct hdcp_lib_session_deinit_req *)handle->qseecom_handle->sbuf;
1096 req_buf->commandid = HDCP_SESSION_DEINIT;
1097 req_buf->sessionid = handle->session_id;
1098 rsp_buf = (struct hdcp_lib_session_deinit_rsp *)
1099 (handle->qseecom_handle->sbuf +
1100 QSEECOM_ALIGN(sizeof(struct hdcp_lib_session_deinit_req)));
1101
1102 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
1103 QSEECOM_ALIGN(sizeof
1104 (struct
1105 hdcp_lib_session_deinit_req)),
1106 rsp_buf,
1107 QSEECOM_ALIGN(sizeof
1108 (struct
1109 hdcp_lib_session_deinit_rsp)));
1110
Tatenda Chipeperekwa8a77c8a2018-01-30 14:50:11 -08001111 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS) ||
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07001112 (rsp_buf->commandid != HDCP_SESSION_DEINIT)) {
1113 pr_err("qseecom cmd failed with err = %d status = %d\n",
1114 rc, rsp_buf->status);
1115 rc = -EINVAL;
1116 goto exit;
1117 }
1118
1119 handle->hdcp_state &= ~HDCP_STATE_SESSION_INIT;
1120 pr_debug("success\n");
1121exit:
1122 return rc;
1123}
1124
1125static int hdcp_lib_txmtr_init(struct hdcp_lib_handle *handle)
1126{
1127 int rc = 0;
1128 struct hdcp_tx_init_req *req_buf;
1129 struct hdcp_tx_init_rsp *rsp_buf;
1130
1131 if (!handle || !handle->qseecom_handle ||
1132 !handle->qseecom_handle->sbuf) {
1133 pr_err("invalid handle\n");
1134 rc = -EINVAL;
1135 goto exit;
1136 }
1137
1138 if (!(handle->hdcp_state & HDCP_STATE_SESSION_INIT)) {
1139 pr_err("session not initialized\n");
1140 goto exit;
1141 }
1142
1143 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
1144 pr_err("library not loaded\n");
1145 goto exit;
1146 }
1147
1148 /* send HDCP_Txmtr_Init command to TZ */
1149 req_buf = (struct hdcp_tx_init_req *)handle->qseecom_handle->sbuf;
1150 req_buf->commandid = HDCP_TXMTR_INIT;
1151 req_buf->sessionid = handle->session_id;
1152 rsp_buf = (struct hdcp_tx_init_rsp *)
1153 (handle->qseecom_handle->sbuf +
1154 QSEECOM_ALIGN(sizeof(struct hdcp_tx_init_req)));
1155
1156 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
1157 QSEECOM_ALIGN(sizeof
1158 (struct hdcp_tx_init_req)),
1159 rsp_buf,
1160 QSEECOM_ALIGN(sizeof
1161 (struct hdcp_tx_init_rsp)));
1162
1163 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS) ||
1164 (rsp_buf->commandid != HDCP_TXMTR_INIT)) {
1165 pr_err("qseecom cmd failed with err = %d, status = %d\n",
1166 rc, rsp_buf->status);
1167 rc = -EINVAL;
1168 goto exit;
1169 }
1170
1171 handle->tz_ctxhandle = rsp_buf->ctxhandle;
1172 handle->hdcp_state |= HDCP_STATE_TXMTR_INIT;
1173
1174 pr_debug("success\n");
1175exit:
1176 return rc;
1177}
1178
1179static int hdcp_lib_txmtr_deinit(struct hdcp_lib_handle *handle)
1180{
1181 int rc = 0;
1182 struct hdcp_deinit_req *req_buf;
1183 struct hdcp_deinit_rsp *rsp_buf;
1184
1185 if (!handle || !handle->qseecom_handle ||
1186 !handle->qseecom_handle->sbuf) {
1187 pr_err("invalid handle\n");
1188 rc = -EINVAL;
1189 goto exit;
1190 }
1191
1192 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
1193 pr_err("app not loaded\n");
1194 goto exit;
1195 }
1196
1197 if (!(handle->hdcp_state & HDCP_STATE_TXMTR_INIT)) {
1198 /* unload library here */
1199 pr_err("txmtr not initialized\n");
1200 goto exit;
1201 }
1202
1203 /* send command to TZ */
1204 req_buf = (struct hdcp_deinit_req *)handle->qseecom_handle->sbuf;
1205 req_buf->commandid = HDCP_TXMTR_DEINIT;
1206 req_buf->ctxhandle = handle->tz_ctxhandle;
1207 rsp_buf = (struct hdcp_deinit_rsp *)
1208 (handle->qseecom_handle->sbuf +
1209 QSEECOM_ALIGN(sizeof(struct hdcp_deinit_req)));
1210
1211 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
1212 QSEECOM_ALIGN(sizeof(struct hdcp_deinit_req)),
1213 rsp_buf,
1214 QSEECOM_ALIGN(sizeof
1215 (struct hdcp_deinit_rsp)));
1216
Tatenda Chipeperekwa8a77c8a2018-01-30 14:50:11 -08001217 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS) ||
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07001218 (rsp_buf->commandid != HDCP_TXMTR_DEINIT)) {
1219 pr_err("qseecom cmd failed with err = %d status = %d\n",
1220 rc, rsp_buf->status);
1221 rc = -EINVAL;
1222 goto exit;
1223 }
1224
1225 handle->hdcp_state &= ~HDCP_STATE_TXMTR_INIT;
1226 pr_debug("success\n");
1227exit:
1228 return rc;
1229}
1230
1231static int hdcp_lib_start_auth(struct hdcp_lib_handle *handle)
1232{
1233 int rc = 0;
1234 struct hdcp_start_auth_req *req_buf;
1235 struct hdcp_start_auth_rsp *rsp_buf;
1236
1237 if (!handle || !handle->qseecom_handle ||
1238 !handle->qseecom_handle->sbuf) {
1239 pr_err("invalid handle\n");
1240 rc = -EINVAL;
1241 goto exit;
1242 }
1243
1244 if (!(handle->hdcp_state & HDCP_STATE_SESSION_INIT)) {
1245 pr_err("session not initialized\n");
1246 goto exit;
1247 }
1248
1249 if (!(handle->hdcp_state & HDCP_STATE_TXMTR_INIT)) {
1250 pr_err("txmtr not initialized\n");
1251 goto exit;
1252 }
1253
1254 /* send HDCP_Txmtr_Start_Auth command to TZ */
1255 req_buf = (struct hdcp_start_auth_req *)handle->qseecom_handle->sbuf;
1256 req_buf->commandid = HDCP_TXMTR_START_AUTHENTICATE;
1257 req_buf->ctxHandle = handle->tz_ctxhandle;
1258 rsp_buf = (struct hdcp_start_auth_rsp *)
1259 (handle->qseecom_handle->sbuf +
1260 QSEECOM_ALIGN(sizeof(struct hdcp_start_auth_req)));
1261
1262 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
1263 QSEECOM_ALIGN(sizeof
1264 (struct hdcp_start_auth_req)),
1265 rsp_buf,
1266 QSEECOM_ALIGN(sizeof
1267 (struct hdcp_start_auth_rsp)));
1268
1269 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS) ||
1270 (rsp_buf->commandid != HDCP_TXMTR_START_AUTHENTICATE) ||
Tatenda Chipeperekwa8a77c8a2018-01-30 14:50:11 -08001271 (rsp_buf->msglen == 0) || (rsp_buf->message == NULL)) {
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07001272 pr_err("qseecom cmd failed with err = %d, status = %d\n",
1273 rc, rsp_buf->status);
1274 rc = -EINVAL;
1275 goto exit;
1276 }
1277
1278 pr_debug("recvd %s from TZ at %dms\n",
1279 hdcp_lib_message_name((int)rsp_buf->message[0]),
1280 jiffies_to_msecs(jiffies));
1281
1282 handle->last_msg = (int)rsp_buf->message[0];
1283
1284 /* send the response to HDMI driver */
1285 memset(handle->listener_buf, 0, MAX_TX_MESSAGE_SIZE);
1286 memcpy(handle->listener_buf, (unsigned char *)rsp_buf->message,
1287 rsp_buf->msglen);
1288 handle->msglen = rsp_buf->msglen;
1289 handle->hdcp_timeout = rsp_buf->timeout;
1290
1291 handle->tz_ctxhandle = rsp_buf->ctxhandle;
1292
1293 pr_debug("success\n");
1294exit:
1295 return rc;
1296}
1297
1298static void hdcp_lib_stream(struct hdcp_lib_handle *handle)
1299{
1300 int rc = 0;
1301 struct hdcp_query_stream_type_req *req_buf;
1302 struct hdcp_query_stream_type_rsp *rsp_buf;
1303
1304 if (!handle || !handle->qseecom_handle ||
1305 !handle->qseecom_handle->sbuf) {
1306 pr_err("invalid handle\n");
1307 return;
1308 }
1309
1310 if (atomic_read(&handle->hdcp_off)) {
1311 pr_debug("invalid state, hdcp off\n");
1312 return;
1313 }
1314
1315 if (!handle->repeater_flag) {
1316 pr_debug("invalid state, not a repeater\n");
1317 return;
1318 }
1319
1320 /* send command to TZ */
1321 req_buf =
1322 (struct hdcp_query_stream_type_req *)handle->qseecom_handle->sbuf;
1323 req_buf->commandid = HDCP_TXMTR_QUERY_STREAM_TYPE;
1324 req_buf->ctxhandle = handle->tz_ctxhandle;
1325 rsp_buf = (struct hdcp_query_stream_type_rsp *)
1326 (handle->qseecom_handle->sbuf +
1327 QSEECOM_ALIGN(sizeof(struct hdcp_query_stream_type_req)));
1328
1329 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
1330 QSEECOM_ALIGN(sizeof
1331 (struct
1332 hdcp_query_stream_type_req)),
1333 rsp_buf,
1334 QSEECOM_ALIGN(sizeof
1335 (struct
1336 hdcp_query_stream_type_rsp)));
1337
Tatenda Chipeperekwa8a77c8a2018-01-30 14:50:11 -08001338 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS) ||
1339 (rsp_buf->msglen == 0) ||
1340 (rsp_buf->commandid != HDCP_TXMTR_QUERY_STREAM_TYPE) ||
1341 (rsp_buf->msg == NULL)) {
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07001342 pr_err("qseecom cmd failed with err=%d status=%d\n",
1343 rc, rsp_buf->status);
1344 rc = -EINVAL;
1345 goto exit;
1346 }
1347
1348 pr_debug("message received from TZ: %s\n",
1349 hdcp_lib_message_name((int)rsp_buf->msg[0]));
1350
1351 handle->last_msg = (int)rsp_buf->msg[0];
1352
1353 memset(handle->listener_buf, 0, MAX_TX_MESSAGE_SIZE);
1354 memcpy(handle->listener_buf, (unsigned char *)rsp_buf->msg,
1355 rsp_buf->msglen);
1356 handle->hdcp_timeout = rsp_buf->timeout;
1357 handle->msglen = rsp_buf->msglen;
1358exit:
1359 if (!rc && !atomic_read(&handle->hdcp_off))
1360 hdcp_lib_send_message(handle);
1361}
1362
1363static void hdcp_lib_query_stream_work(struct kthread_work *work)
1364{
1365 struct hdcp_lib_handle *handle = container_of(work,
1366 struct hdcp_lib_handle,
1367 wk_stream);
1368
1369 hdcp_lib_stream(handle);
1370}
1371
1372static bool hdcp_lib_client_feature_supported(void *phdcpcontext)
1373{
1374 int rc = 0;
1375 bool supported = false;
1376 struct hdcp_lib_handle *handle = phdcpcontext;
1377
1378 if (!handle) {
1379 pr_err("invalid input\n");
1380 goto exit;
1381 }
1382
1383 if (handle->feature_supported) {
1384 supported = true;
1385 goto exit;
1386 }
1387
1388 rc = hdcp_lib_library_load(handle);
1389 if (!rc) {
1390 if (!hdcp_lib_verify_keys(handle)) {
1391 pr_debug("HDCP2p2 supported\n");
1392 handle->feature_supported = true;
1393 supported = true;
1394 }
1395 hdcp_lib_library_unload(handle);
1396 }
1397exit:
1398 return supported;
1399}
1400
1401static void hdcp_lib_check_worker_status(struct hdcp_lib_handle *handle)
1402{
1403 if (!list_empty(&handle->wk_init.node))
1404 pr_debug("init work queued\n");
1405
1406 if (handle->worker.current_work == &handle->wk_init)
1407 pr_debug("init work executing\n");
1408
1409 if (!list_empty(&handle->wk_msg_sent.node))
1410 pr_debug("msg_sent work queued\n");
1411
1412 if (handle->worker.current_work == &handle->wk_msg_sent)
1413 pr_debug("msg_sent work executing\n");
1414
1415 if (!list_empty(&handle->wk_msg_recvd.node))
1416 pr_debug("msg_recvd work queued\n");
1417
1418 if (handle->worker.current_work == &handle->wk_msg_recvd)
1419 pr_debug("msg_recvd work executing\n");
1420
1421 if (!list_empty(&handle->wk_timeout.node))
1422 pr_debug("timeout work queued\n");
1423
1424 if (handle->worker.current_work == &handle->wk_timeout)
1425 pr_debug("timeout work executing\n");
1426
1427 if (!list_empty(&handle->wk_clean.node))
1428 pr_debug("clean work queued\n");
1429
1430 if (handle->worker.current_work == &handle->wk_clean)
1431 pr_debug("clean work executing\n");
1432
1433 if (!list_empty(&handle->wk_wait.node))
1434 pr_debug("wait work queued\n");
1435
1436 if (handle->worker.current_work == &handle->wk_wait)
1437 pr_debug("wait work executing\n");
1438
1439 if (!list_empty(&handle->wk_stream.node))
1440 pr_debug("stream work queued\n");
1441
1442 if (handle->worker.current_work == &handle->wk_stream)
1443 pr_debug("stream work executing\n");
1444}
1445
1446static int hdcp_lib_check_valid_state(struct hdcp_lib_handle *handle)
1447{
1448 int rc = 0;
1449
1450 if (!list_empty(&handle->worker.work_list))
1451 hdcp_lib_check_worker_status(handle);
1452
1453 if (handle->wakeup_cmd == HDCP_LIB_WKUP_CMD_START) {
1454 if (!list_empty(&handle->worker.work_list)) {
1455 pr_debug("error: queue not empty\n");
1456 rc = -EBUSY;
1457 goto exit;
1458 }
1459
1460 if (handle->hdcp_state & HDCP_STATE_APP_LOADED) {
1461 pr_debug("library already loaded\n");
1462 rc = -EBUSY;
1463 goto exit;
1464 }
1465 } else {
1466 if (atomic_read(&handle->hdcp_off)) {
1467 pr_debug("hdcp2.2 session tearing down\n");
1468 goto exit;
1469 }
1470
1471 if (!(handle->hdcp_state & HDCP_STATE_APP_LOADED)) {
1472 pr_debug("hdcp 2.2 app not loaded\n");
1473 goto exit;
1474 }
1475 }
1476exit:
1477 return rc;
1478}
1479
1480static int hdcp_lib_wakeup_thread(struct hdcp_lib_wakeup_data *data)
1481{
1482 struct hdcp_lib_handle *handle;
1483 int rc = 0;
1484
1485 if (!data)
1486 return -EINVAL;
1487
1488 handle = data->context;
1489 if (!handle)
1490 return -EINVAL;
1491
1492 mutex_lock(&handle->wakeup_mutex);
1493
1494 handle->wakeup_cmd = data->cmd;
1495 handle->timeout_left = data->timeout;
1496
1497 pr_debug("client->lib: %s (%s)\n",
1498 hdcp_lib_cmd_to_str(data->cmd),
1499 hdcp_lib_message_name(handle->last_msg));
1500
1501 rc = hdcp_lib_check_valid_state(handle);
1502 if (rc)
1503 goto exit;
1504
1505 mutex_lock(&handle->msg_lock);
1506 if (data->recvd_msg_len) {
1507 kzfree(handle->last_msg_recvd_buf);
1508
1509 handle->last_msg_recvd_len = data->recvd_msg_len;
1510 handle->last_msg_recvd_buf = kzalloc(data->recvd_msg_len,
1511 GFP_KERNEL);
1512 if (!handle->last_msg_recvd_buf) {
1513 rc = -ENOMEM;
1514 mutex_unlock(&handle->msg_lock);
1515 goto exit;
1516 }
1517
1518 memcpy(handle->last_msg_recvd_buf, data->recvd_msg_buf,
1519 data->recvd_msg_len);
1520 }
1521 mutex_unlock(&handle->msg_lock);
1522
1523 if (!completion_done(&handle->poll_wait))
1524 complete_all(&handle->poll_wait);
1525
1526 switch (handle->wakeup_cmd) {
1527 case HDCP_LIB_WKUP_CMD_START:
1528 handle->no_stored_km_flag = 0;
1529 handle->repeater_flag = false;
1530 handle->update_stream = false;
1531 handle->last_msg_sent = 0;
1532 handle->last_msg = INVALID_MESSAGE_ID;
1533 handle->hdcp_timeout = 0;
1534 handle->timeout_left = 0;
1535 atomic_set(&handle->hdcp_off, 0);
1536 handle->hdcp_state = HDCP_STATE_INIT;
1537
1538 HDCP_LIB_EXECUTE(init);
1539 break;
1540 case HDCP_LIB_WKUP_CMD_STOP:
1541 atomic_set(&handle->hdcp_off, 1);
1542
1543 HDCP_LIB_EXECUTE(clean);
1544 break;
1545 case HDCP_LIB_WKUP_CMD_MSG_SEND_SUCCESS:
1546 handle->last_msg_sent = handle->listener_buf[0];
1547
1548 HDCP_LIB_EXECUTE(msg_sent);
1549 break;
1550 case HDCP_LIB_WKUP_CMD_MSG_SEND_FAILED:
1551 case HDCP_LIB_WKUP_CMD_MSG_RECV_FAILED:
1552 case HDCP_LIB_WKUP_CMD_LINK_FAILED:
1553 handle->hdcp_state |= HDCP_STATE_ERROR;
1554 HDCP_LIB_EXECUTE(clean);
1555 break;
1556 case HDCP_LIB_WKUP_CMD_MSG_RECV_SUCCESS:
1557 HDCP_LIB_EXECUTE(msg_recvd);
1558 break;
1559 case HDCP_LIB_WKUP_CMD_MSG_RECV_TIMEOUT:
1560 HDCP_LIB_EXECUTE(timeout);
1561 break;
1562 case HDCP_LIB_WKUP_CMD_QUERY_STREAM_TYPE:
1563 HDCP_LIB_EXECUTE(stream);
1564 break;
1565 default:
1566 pr_err("invalid wakeup command %d\n", handle->wakeup_cmd);
1567 }
1568exit:
1569 mutex_unlock(&handle->wakeup_mutex);
1570
1571 return rc;
1572}
1573
1574static void hdcp_lib_msg_sent(struct hdcp_lib_handle *handle)
1575{
1576 struct hdcp_wakeup_data cdata = { HDCP_WKUP_CMD_INVALID };
1577
1578 if (!handle) {
1579 pr_err("invalid handle\n");
1580 return;
1581 }
1582
1583 cdata.context = handle->client_ctx;
1584
1585 switch (handle->last_msg_sent) {
1586 case SKE_SEND_TYPE_ID:
1587 if (!hdcp_lib_enable_encryption(handle)) {
1588 handle->authenticated = true;
1589
1590 cdata.cmd = HDCP_WKUP_CMD_STATUS_SUCCESS;
1591 hdcp_lib_wakeup_client(handle, &cdata);
1592 }
1593
1594 /* poll for link check */
1595 cdata.cmd = HDCP_WKUP_CMD_LINK_POLL;
1596 break;
1597 case SKE_SEND_EKS_MESSAGE_ID:
1598 if (handle->repeater_flag) {
1599 /* poll for link check */
1600 cdata.cmd = HDCP_WKUP_CMD_LINK_POLL;
1601 } else {
1602 memset(handle->listener_buf, 0, MAX_TX_MESSAGE_SIZE);
1603 handle->listener_buf[0] = SKE_SEND_TYPE_ID;
1604 handle->msglen = 2;
1605 cdata.cmd = HDCP_WKUP_CMD_SEND_MESSAGE;
1606 cdata.send_msg_buf = handle->listener_buf;
1607 cdata.send_msg_len = handle->msglen;
1608 handle->last_msg = hdcp_lib_get_next_message(handle,
1609 &cdata);
1610 }
1611 break;
1612 case REPEATER_AUTH_SEND_ACK_MESSAGE_ID:
1613 pr_debug("Repeater authentication successful\n");
1614
1615 if (handle->update_stream) {
1616 HDCP_LIB_EXECUTE(stream);
1617 handle->update_stream = false;
1618 } else {
1619 cdata.cmd = HDCP_WKUP_CMD_LINK_POLL;
1620 }
1621 break;
1622 default:
1623 cdata.cmd = HDCP_WKUP_CMD_RECV_MESSAGE;
1624 cdata.timeout = handle->timeout_left;
1625 }
1626
1627 hdcp_lib_wakeup_client(handle, &cdata);
1628}
1629
1630static void hdcp_lib_msg_sent_work(struct kthread_work *work)
1631{
1632 struct hdcp_lib_handle *handle = container_of(work,
1633 struct hdcp_lib_handle,
1634 wk_msg_sent);
1635
1636 if (handle->wakeup_cmd != HDCP_LIB_WKUP_CMD_MSG_SEND_SUCCESS) {
1637 pr_err("invalid wakeup command %d\n", handle->wakeup_cmd);
1638 return;
1639 }
1640
1641 hdcp_lib_msg_sent(handle);
1642}
1643
1644static void hdcp_lib_init(struct hdcp_lib_handle *handle)
1645{
1646 int rc = 0;
1647
1648 if (!handle) {
1649 pr_err("invalid handle\n");
1650 return;
1651 }
1652
1653 if (handle->wakeup_cmd != HDCP_LIB_WKUP_CMD_START) {
1654 pr_err("invalid wakeup command %d\n", handle->wakeup_cmd);
1655 return;
1656 }
1657
1658 rc = hdcp_lib_library_load(handle);
1659 if (rc)
1660 goto exit;
1661
1662 rc = hdcp_lib_session_init(handle);
1663 if (rc)
1664 goto exit;
1665
1666 if (handle->hdcp_txmtr_init == NULL) {
1667 pr_err("invalid txmtr init function pointer\n");
1668 return;
1669 }
1670
1671 rc = handle->hdcp_txmtr_init(handle);
1672 if (rc)
1673 goto exit;
1674
1675 rc = hdcp_lib_start_auth(handle);
1676 if (rc)
1677 goto exit;
1678
1679 hdcp_lib_send_message(handle);
1680
1681 return;
1682exit:
1683 HDCP_LIB_EXECUTE(clean);
1684}
1685
1686static void hdcp_lib_init_work(struct kthread_work *work)
1687{
1688 struct hdcp_lib_handle *handle = container_of(work,
1689 struct hdcp_lib_handle,
1690 wk_init);
1691
1692 hdcp_lib_init(handle);
1693}
1694
1695static void hdcp_lib_timeout(struct hdcp_lib_handle *handle)
1696{
1697 int rc = 0;
1698 struct hdcp_send_timeout_req *req_buf;
1699 struct hdcp_send_timeout_rsp *rsp_buf;
1700
1701 if (!handle || !handle->qseecom_handle ||
1702 !handle->qseecom_handle->sbuf) {
1703 pr_debug("invalid handle\n");
1704 return;
1705 }
1706
1707 if (atomic_read(&handle->hdcp_off)) {
1708 pr_debug("invalid state, hdcp off\n");
1709 return;
1710 }
1711
1712 req_buf = (struct hdcp_send_timeout_req *)
1713 (handle->qseecom_handle->sbuf);
1714 req_buf->commandid = HDCP_TXMTR_SEND_MESSAGE_TIMEOUT;
1715 req_buf->ctxhandle = handle->tz_ctxhandle;
1716
1717 rsp_buf = (struct hdcp_send_timeout_rsp *)
1718 (handle->qseecom_handle->sbuf +
1719 QSEECOM_ALIGN(sizeof(struct hdcp_send_timeout_req)));
1720
1721 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
1722 QSEECOM_ALIGN(sizeof
1723 (struct hdcp_send_timeout_req)),
1724 rsp_buf,
1725 QSEECOM_ALIGN(sizeof
1726 (struct
1727 hdcp_send_timeout_rsp)));
1728
1729 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS)) {
1730 pr_err("qseecom cmd failed for with err = %d status = %d\n",
1731 rc, rsp_buf->status);
1732 rc = -EINVAL;
1733 goto error;
1734 }
1735
1736 if (rsp_buf->commandid == HDCP_TXMTR_SEND_MESSAGE_TIMEOUT) {
1737 pr_err("HDCP_TXMTR_SEND_MESSAGE_TIMEOUT\n");
1738 rc = -EINVAL;
1739 goto error;
1740 }
1741
1742 /*
1743 * if the response contains LC_Init message
1744 * send the message again to TZ
1745 */
1746 if ((rsp_buf->commandid == HDCP_TXMTR_PROCESS_RECEIVED_MESSAGE) &&
1747 ((int)rsp_buf->message[0] == LC_INIT_MESSAGE_ID) &&
1748 (rsp_buf->msglen == LC_INIT_MESSAGE_SIZE)) {
1749 if (!atomic_read(&handle->hdcp_off)) {
1750 /* keep local copy of TZ response */
1751 memset(handle->listener_buf, 0, MAX_TX_MESSAGE_SIZE);
1752 memcpy(handle->listener_buf,
1753 (unsigned char *)rsp_buf->message,
1754 rsp_buf->msglen);
1755 handle->hdcp_timeout = rsp_buf->timeout;
1756 handle->msglen = rsp_buf->msglen;
1757
1758 hdcp_lib_send_message(handle);
1759 }
1760 }
1761
1762 return;
1763error:
1764 if (!atomic_read(&handle->hdcp_off))
1765 HDCP_LIB_EXECUTE(clean);
1766}
1767
1768static void hdcp_lib_manage_timeout_work(struct kthread_work *work)
1769{
1770 struct hdcp_lib_handle *handle = container_of(work,
1771 struct hdcp_lib_handle,
1772 wk_timeout);
1773
1774 hdcp_lib_timeout(handle);
1775}
1776
1777static void hdcp_lib_clean(struct hdcp_lib_handle *handle)
1778{
1779 struct hdcp_wakeup_data cdata = { HDCP_WKUP_CMD_INVALID };
1780
1781 if (!handle) {
1782 pr_err("invalid input\n");
1783 return;
1784 }
1785
1786 handle->authenticated = false;
1787
1788 hdcp_lib_txmtr_deinit(handle);
1789 hdcp_lib_session_deinit(handle);
1790 hdcp_lib_library_unload(handle);
1791
1792 cdata.context = handle->client_ctx;
1793 cdata.cmd = HDCP_WKUP_CMD_STATUS_FAILED;
1794
1795 if (!atomic_read(&handle->hdcp_off))
1796 hdcp_lib_wakeup_client(handle, &cdata);
1797
1798 atomic_set(&handle->hdcp_off, 1);
1799}
1800
1801static void hdcp_lib_cleanup_work(struct kthread_work *work)
1802{
1803
1804 struct hdcp_lib_handle *handle = container_of(work,
1805 struct hdcp_lib_handle,
1806 wk_clean);
1807
1808 hdcp_lib_clean(handle);
1809}
1810
1811static void hdcp_lib_msg_recvd(struct hdcp_lib_handle *handle)
1812{
1813 int rc = 0;
1814 struct hdcp_wakeup_data cdata = { HDCP_WKUP_CMD_INVALID };
1815 struct hdcp_rcvd_msg_req *req_buf;
1816 struct hdcp_rcvd_msg_rsp *rsp_buf;
1817 uint32_t msglen;
1818 char *msg = NULL;
1819 char msg_name[50];
1820 uint32_t message_id_bytes = 0;
1821
1822 if (!handle || !handle->qseecom_handle ||
1823 !handle->qseecom_handle->sbuf) {
1824 pr_err("invalid handle\n");
1825 return;
1826 }
1827
1828 if (atomic_read(&handle->hdcp_off)) {
1829 pr_debug("invalid state, hdcp off\n");
1830 return;
1831 }
1832
1833 cdata.context = handle->client_ctx;
1834
1835 mutex_lock(&handle->msg_lock);
1836 msglen = handle->last_msg_recvd_len;
1837
Tatenda Chipeperekwa8a77c8a2018-01-30 14:50:11 -08001838 if (msglen == 0) {
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07001839 pr_err("invalid msg len\n");
1840 mutex_unlock(&handle->msg_lock);
1841 rc = -EINVAL;
1842 goto exit;
1843 }
1844
1845 /* If the client is DP then allocate extra byte for message ID. */
1846 if (handle->device_type == HDCP_TXMTR_DP)
1847 message_id_bytes = 1;
1848
1849 msglen += message_id_bytes;
1850
1851 msg = kzalloc(msglen, GFP_KERNEL);
1852 if (!msg) {
1853 mutex_unlock(&handle->msg_lock);
1854 rc = -ENOMEM;
1855 goto exit;
1856 }
1857
1858 /* copy the message id if needed */
1859 if (message_id_bytes)
1860 memcpy(msg, &handle->last_msg, message_id_bytes);
1861
1862 memcpy(msg + message_id_bytes,
1863 handle->last_msg_recvd_buf,
1864 handle->last_msg_recvd_len);
1865
1866 mutex_unlock(&handle->msg_lock);
1867
1868 snprintf(msg_name, sizeof(msg_name), "%s: ",
1869 hdcp_lib_message_name((int)msg[0]));
1870
1871 print_hex_dump(KERN_DEBUG, msg_name,
1872 DUMP_PREFIX_NONE, 16, 1, msg, msglen, false);
1873
1874 /* send the message to QSEECOM */
1875 req_buf = (struct hdcp_rcvd_msg_req *)(handle->qseecom_handle->sbuf);
1876 req_buf->commandid = HDCP_TXMTR_PROCESS_RECEIVED_MESSAGE;
1877 memcpy(req_buf->msg, msg, msglen);
1878 req_buf->msglen = msglen;
1879 req_buf->ctxhandle = handle->tz_ctxhandle;
1880
1881 rsp_buf =
1882 (struct hdcp_rcvd_msg_rsp *)(handle->qseecom_handle->sbuf +
1883 QSEECOM_ALIGN(sizeof
1884 (struct
1885 hdcp_rcvd_msg_req)));
1886
1887 pr_debug("writing %s to TZ at %dms\n",
1888 hdcp_lib_message_name((int)msg[0]), jiffies_to_msecs(jiffies));
1889
1890 rc = qseecom_send_command(handle->qseecom_handle, req_buf,
1891 QSEECOM_ALIGN(sizeof
1892 (struct hdcp_rcvd_msg_req)),
1893 rsp_buf,
1894 QSEECOM_ALIGN(sizeof
1895 (struct hdcp_rcvd_msg_rsp)));
1896
1897 /* get next message from sink if we receive H PRIME on no store km */
1898 if ((msg[0] == AKE_SEND_H_PRIME_MESSAGE_ID) &&
1899 handle->no_stored_km_flag) {
1900 handle->hdcp_timeout = rsp_buf->timeout;
1901
1902 cdata.cmd = HDCP_WKUP_CMD_RECV_MESSAGE;
1903 cdata.timeout = handle->hdcp_timeout;
1904
1905 goto exit;
1906 }
1907
1908 if ((msg[0] == REPEATER_AUTH_STREAM_READY_MESSAGE_ID) &&
1909 (rc == 0) && (rsp_buf->status == 0)) {
1910 pr_debug("Got Auth_Stream_Ready, nothing sent to rx\n");
1911
1912 if (!handle->authenticated &&
1913 !hdcp_lib_enable_encryption(handle)) {
1914 handle->authenticated = true;
1915
1916 cdata.cmd = HDCP_WKUP_CMD_STATUS_SUCCESS;
1917 hdcp_lib_wakeup_client(handle, &cdata);
1918 }
1919
1920 cdata.cmd = HDCP_WKUP_CMD_LINK_POLL;
1921 goto exit;
1922 }
1923
Tatenda Chipeperekwa8a77c8a2018-01-30 14:50:11 -08001924 if ((rc < 0) || (rsp_buf->status != HDCP_SUCCESS) ||
1925 (rsp_buf->msglen == 0) ||
1926 (rsp_buf->commandid != HDCP_TXMTR_PROCESS_RECEIVED_MESSAGE) ||
1927 (rsp_buf->msg == NULL)) {
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07001928 pr_err("qseecom cmd failed with err=%d status=%d\n",
1929 rc, rsp_buf->status);
1930 rc = -EINVAL;
1931 goto exit;
1932 }
1933
1934 pr_debug("recvd %s from TZ at %dms\n",
1935 hdcp_lib_message_name((int)rsp_buf->msg[0]),
1936 jiffies_to_msecs(jiffies));
1937
1938 handle->last_msg = (int)rsp_buf->msg[0];
1939
1940 /* set the flag if response is AKE_No_Stored_km */
1941 if (((int)rsp_buf->msg[0] == AKE_NO_STORED_KM_MESSAGE_ID)) {
1942 pr_debug("Setting no_stored_km_flag\n");
1943 handle->no_stored_km_flag = 1;
1944 } else {
1945 handle->no_stored_km_flag = 0;
1946 }
1947
1948 /* check if it's a repeater */
1949 if ((rsp_buf->msg[0] == SKE_SEND_EKS_MESSAGE_ID) &&
1950 (rsp_buf->msglen == SKE_SEND_EKS_MESSAGE_SIZE)) {
1951 if ((rsp_buf->flag ==
1952 HDCP_TXMTR_SUBSTATE_WAITING_FOR_RECIEVERID_LIST) &&
1953 (rsp_buf->timeout > 0))
1954 handle->repeater_flag = true;
1955 handle->update_stream = true;
1956 }
1957
1958 memset(handle->listener_buf, 0, MAX_TX_MESSAGE_SIZE);
1959 memcpy(handle->listener_buf, (unsigned char *)rsp_buf->msg,
1960 rsp_buf->msglen);
1961 handle->hdcp_timeout = rsp_buf->timeout;
1962 handle->msglen = rsp_buf->msglen;
1963
1964 if (!atomic_read(&handle->hdcp_off))
1965 hdcp_lib_send_message(handle);
1966exit:
1967 kzfree(msg);
1968
1969 hdcp_lib_wakeup_client(handle, &cdata);
1970
1971 if (rc && !atomic_read(&handle->hdcp_off))
1972 HDCP_LIB_EXECUTE(clean);
1973}
1974
1975static void hdcp_lib_msg_recvd_work(struct kthread_work *work)
1976{
1977 struct hdcp_lib_handle *handle = container_of(work,
1978 struct hdcp_lib_handle,
1979 wk_msg_recvd);
1980
1981 hdcp_lib_msg_recvd(handle);
1982}
1983
1984static void hdcp_lib_wait_work(struct kthread_work *work)
1985{
1986 u32 timeout;
1987 struct hdcp_lib_handle *handle = container_of(work,
1988 struct hdcp_lib_handle, wk_wait);
1989
1990 if (!handle) {
1991 pr_err("invalid input\n");
1992 return;
1993 }
1994
1995 if (atomic_read(&handle->hdcp_off)) {
1996 pr_debug("invalid state: hdcp off\n");
1997 return;
1998 }
1999
2000 if (handle->hdcp_state & HDCP_STATE_ERROR) {
2001 pr_debug("invalid state: hdcp error\n");
2002 return;
2003 }
2004
2005 reinit_completion(&handle->poll_wait);
2006 timeout = wait_for_completion_timeout(&handle->poll_wait,
2007 handle->wait_timeout);
2008 if (!timeout) {
2009 pr_err("wait timeout\n");
2010
2011 if (!atomic_read(&handle->hdcp_off))
2012 HDCP_LIB_EXECUTE(clean);
2013 }
2014
2015 handle->wait_timeout = 0;
2016}
2017
2018bool hdcp1_check_if_supported_load_app(void)
2019{
2020 int rc = 0;
2021
2022 /* start hdcp1 app */
2023 if (hdcp1_supported && !hdcp1_handle) {
2024 rc = qseecom_start_app(&hdcp1_handle, HDCP1_APP_NAME,
2025 QSEECOM_SBUFF_SIZE);
2026 if (rc) {
2027 pr_err("qseecom_start_app failed %d\n", rc);
2028 hdcp1_supported = false;
2029 } else {
2030 mutex_init(&hdcp1_ta_cmd_lock);
2031 }
2032 }
2033
2034 pr_debug("hdcp1 app %s loaded\n",
2035 hdcp1_supported ? "successfully" : "not");
2036
2037 return hdcp1_supported;
2038}
2039
Sankeerth Billakanti37886d92019-01-24 18:01:28 +05302040void hdcp1_unload_app(void)
2041{
2042 int rc = 0;
2043
2044 if (!hdcp1_supported) {
2045 pr_debug("hdcp1 is not supported\n");
2046 return;
2047 }
2048
2049 if (!hdcp1_handle) {
2050 pr_debug("invalid hdcp1 handle\n");
2051 return;
2052 }
2053
2054 rc = qseecom_shutdown_app(&hdcp1_handle);
2055 if (rc) {
2056 pr_debug("qseecom_shutdown_app failed with ERR = %d\n", rc);
2057 return;
2058 }
2059
2060 hdcp1_handle = NULL;
2061 pr_debug("hdcp1 app unloaded\n");
2062}
2063
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07002064/* APIs exposed to all clients */
2065int hdcp1_set_keys(uint32_t *aksv_msb, uint32_t *aksv_lsb)
2066{
2067 int rc = 0;
2068 struct hdcp1_key_set_req *key_set_req;
2069 struct hdcp1_key_set_rsp *key_set_rsp;
2070
2071 if (aksv_msb == NULL || aksv_lsb == NULL)
2072 return -EINVAL;
2073
2074 if (!hdcp1_supported || !hdcp1_handle)
2075 return -EINVAL;
2076
2077 /* set keys and request aksv */
2078 key_set_req = (struct hdcp1_key_set_req *)hdcp1_handle->sbuf;
2079 key_set_req->commandid = HDCP1_SET_KEY_MESSAGE_ID;
2080 key_set_rsp = (struct hdcp1_key_set_rsp *)(hdcp1_handle->sbuf +
2081 QSEECOM_ALIGN(sizeof(struct hdcp1_key_set_req)));
2082 rc = qseecom_send_command(hdcp1_handle, key_set_req,
2083 QSEECOM_ALIGN(sizeof
2084 (struct hdcp1_key_set_req)),
2085 key_set_rsp,
2086 QSEECOM_ALIGN(sizeof
2087 (struct hdcp1_key_set_rsp)));
2088
2089 if (rc < 0) {
2090 pr_err("qseecom cmd failed err=%d\n", rc);
2091 return -ENOKEY;
2092 }
2093
2094 rc = key_set_rsp->ret;
2095 if (rc) {
2096 pr_err("set key cmd failed, rsp=%d\n", key_set_rsp->ret);
2097 return -ENOKEY;
2098 }
2099
2100 /* copy bytes into msb and lsb */
Tatenda Chipeperekwa8a77c8a2018-01-30 14:50:11 -08002101 *aksv_msb = key_set_rsp->ksv[0] << 24 | key_set_rsp->ksv[1] << 16 |
2102 key_set_rsp->ksv[2] << 8 | key_set_rsp->ksv[3];
2103 *aksv_lsb = key_set_rsp->ksv[4] << 24 | key_set_rsp->ksv[5] << 16 |
2104 key_set_rsp->ksv[6] << 8 | key_set_rsp->ksv[7];
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07002105
2106 return 0;
2107}
2108
2109int hdcp1_set_enc(bool enable)
2110{
2111 int rc = 0;
2112 struct hdcp1_set_enc_req *set_enc_req;
2113 struct hdcp1_set_enc_rsp *set_enc_rsp;
2114
2115 mutex_lock(&hdcp1_ta_cmd_lock);
2116
2117 if (!hdcp1_supported || !hdcp1_handle) {
2118 rc = -EINVAL;
2119 goto end;
2120 }
2121
2122 if (hdcp1_enc_enabled == enable) {
2123 pr_info("already %s\n", enable ? "enabled" : "disabled");
2124 goto end;
2125 }
2126
2127 /* set keys and request aksv */
2128 set_enc_req = (struct hdcp1_set_enc_req *)hdcp1_handle->sbuf;
2129 set_enc_req->commandid = HDCP1_SET_ENC_MESSAGE_ID;
2130 set_enc_req->enable = enable;
2131 set_enc_rsp = (struct hdcp1_set_enc_rsp *)(hdcp1_handle->sbuf +
2132 QSEECOM_ALIGN(sizeof(struct hdcp1_set_enc_req)));
2133 rc = qseecom_send_command(hdcp1_handle, set_enc_req,
2134 QSEECOM_ALIGN(sizeof
2135 (struct hdcp1_set_enc_req)),
2136 set_enc_rsp,
2137 QSEECOM_ALIGN(sizeof
2138 (struct hdcp1_set_enc_rsp)));
2139
2140 if (rc < 0) {
2141 pr_err("qseecom cmd failed err=%d\n", rc);
2142 goto end;
2143 }
2144
2145 rc = set_enc_rsp->ret;
2146 if (rc) {
2147 pr_err("enc cmd failed, rsp=%d\n", set_enc_rsp->ret);
2148 rc = -EINVAL;
2149 goto end;
2150 }
2151
2152 hdcp1_enc_enabled = enable;
2153 pr_info("%s success\n", enable ? "enable" : "disable");
2154end:
2155 mutex_unlock(&hdcp1_ta_cmd_lock);
2156 return rc;
2157}
2158
2159int hdcp_library_register(struct hdcp_register_data *data)
2160{
2161 int rc = 0;
2162 struct hdcp_lib_handle *handle = NULL;
2163
2164 if (!data) {
2165 pr_err("invalid input\n");
2166 return -EINVAL;
2167 }
2168
2169 if (!data->txmtr_ops) {
2170 pr_err("invalid input: txmtr context\n");
2171 return -EINVAL;
2172 }
2173
2174 if (!data->client_ops) {
2175 pr_err("invalid input: client_ops\n");
2176 return -EINVAL;
2177 }
2178
2179 if (!data->hdcp_ctx) {
2180 pr_err("invalid input: hdcp_ctx\n");
2181 return -EINVAL;
2182 }
2183
2184 /* populate ops to be called by client */
2185 data->txmtr_ops->feature_supported = hdcp_lib_client_feature_supported;
2186 data->txmtr_ops->wakeup = hdcp_lib_wakeup_thread;
2187
2188 handle = kzalloc(sizeof(*handle), GFP_KERNEL);
2189 if (!handle) {
2190 rc = -ENOMEM;
2191 goto unlock;
2192 }
2193
2194 handle->client_ctx = data->client_ctx;
2195 handle->client_ops = data->client_ops;
2196 handle->hdcp_app_init = NULL;
2197 handle->hdcp_txmtr_init = NULL;
2198 handle->device_type = data->device_type;
2199
2200 atomic_set(&handle->hdcp_off, 0);
2201
2202 mutex_init(&handle->msg_lock);
2203 mutex_init(&handle->wakeup_mutex);
2204
2205 kthread_init_worker(&handle->worker);
2206
2207 kthread_init_work(&handle->wk_init, hdcp_lib_init_work);
2208 kthread_init_work(&handle->wk_msg_sent, hdcp_lib_msg_sent_work);
2209 kthread_init_work(&handle->wk_msg_recvd, hdcp_lib_msg_recvd_work);
2210 kthread_init_work(&handle->wk_timeout, hdcp_lib_manage_timeout_work);
2211 kthread_init_work(&handle->wk_clean, hdcp_lib_cleanup_work);
2212 kthread_init_work(&handle->wk_wait, hdcp_lib_wait_work);
2213 kthread_init_work(&handle->wk_stream, hdcp_lib_query_stream_work);
2214
2215 init_completion(&handle->poll_wait);
2216
2217 handle->listener_buf = kzalloc(MAX_TX_MESSAGE_SIZE, GFP_KERNEL);
2218 if (!(handle->listener_buf)) {
2219 rc = -ENOMEM;
2220 goto error;
2221 }
2222
2223 *data->hdcp_ctx = handle;
Abhinav Kumar3f0e1c02018-01-08 22:04:13 -08002224
Tatenda Chipeperekwa65935362017-06-07 13:44:11 -07002225 handle->thread = kthread_run(kthread_worker_fn,
2226 &handle->worker, "hdcp_tz_lib");
2227
2228 if (IS_ERR(handle->thread)) {
2229 pr_err("unable to start lib thread\n");
2230 rc = PTR_ERR(handle->thread);
2231 handle->thread = NULL;
2232 goto error;
2233 }
2234
2235 return 0;
2236error:
2237 kzfree(handle->listener_buf);
2238 handle->listener_buf = NULL;
2239 kzfree(handle);
2240 handle = NULL;
2241unlock:
2242 return rc;
2243}
2244EXPORT_SYMBOL(hdcp_library_register);
2245
2246void hdcp_library_deregister(void *phdcpcontext)
2247{
2248 struct hdcp_lib_handle *handle = phdcpcontext;
2249
2250 if (!handle)
2251 return;
2252
2253 kthread_stop(handle->thread);
2254
2255 kzfree(handle->qseecom_handle);
2256 kzfree(handle->last_msg_recvd_buf);
2257
2258 mutex_destroy(&handle->wakeup_mutex);
2259
2260 kzfree(handle->listener_buf);
2261 kzfree(handle);
2262}
2263EXPORT_SYMBOL(hdcp_library_deregister);
2264