source: svn/trunk/newcon3bcm2_21bu/magnum/portinginterface/hdm/7552/bhdm_hdcp.c

Last change on this file was 2, checked in by phkim, 11 years ago

1.phkim

  1. revision copy newcon3sk r27
  • Property svn:executable set to *
File size: 101.6 KB
Line 
1/***************************************************************************
2 *     Copyright (c) 2003-2012, Broadcom Corporation
3 *     All Rights Reserved
4 *     Confidential Property of Broadcom Corporation
5 *
6 *  THIS SOFTWARE MAY ONLY BE USED SUBJECT TO AN EXECUTED SOFTWARE LICENSE
7 *  AGREEMENT  BETWEEN THE USER AND BROADCOM.  YOU HAVE NO RIGHT TO USE OR
8 *  EXPLOIT THIS MATERIAL EXCEPT SUBJECT TO THE TERMS OF SUCH AN AGREEMENT.
9 *
10 * $brcm_Workfile: bhdm_hdcp.c $
11 * $brcm_Revision: Hydra_Software_Devel/100 $
12 * $brcm_Date: 1/3/12 3:27p $
13 *
14 * Module Description:
15 * This module implements HDCP functionality contained in the HDCP Spec
16 * Version 1.1 (www.digital-cp.com) for HDMI/DVI transmiters and
17 * receivers. 
18 *
19 * Revision History:
20 *
21 * $brcm_Log: /magnum/portinginterface/hdm/7038/bhdm_hdcp.c $
22 *
23 * Hydra_Software_Devel/100   1/3/12 3:27p vle
24 * SW7358-203: Merged to mainline.
25 *
26 * Hydra_Software_Devel/bdvd_v4.0/2   12/19/11 1:52p rbshah
27 * SWBLURAY-26245:[ see Broadcom Issue Tracking JIRA for more info ]
28 *
29 * Hydra_Software_Devel/99   11/14/11 2:15p rgreen
30 * SW7425-1710: Update BHDM_CONFIG macro usage.  Describe specific
31 * functionality vs chip process
32 *
33 * Hydra_Software_Devel/98   10/23/11 12:22p rgreen
34 * SW7425-1583:  Add debug warning if a Test Key Set is used for
35 * authentication
36 *
37 * Hydra_Software_Devel/97   10/11/11 4:50p vle
38 * SW7429-5: Add support for 7429.
39 *
40 * Hydra_Software_Devel/96   9/30/11 6:21p vle
41 * SW7408-296: Fix coverity issue
42 *
43 * Hydra_Software_Devel/95   9/2/11 4:56p vle
44 * SW7403-932: Change default values of Ri4SecsAgo and Ri6SecsAgo to avoid
45 * rare case where Ri event is never fired when R0 = 0x01
46 *
47 * Hydra_Software_Devel/94   6/24/11 11:59a vle
48 * SW7422-457: Merged bdvd updates to mainline.
49 *
50 * Hydra_Software_Devel/bdvd_v3.0/bdvd_v4.0/3   6/17/11 3:23p rbshah
51 * SWBLURAY-26245:[ see Broadcom Issue Tracking JIRA for more info ]
52 *
53 * Hydra_Software_Devel/93   11/24/10 3:28p calvinho
54 * SW7401-4468: Update HDCP version definition
55 *
56 * Hydra_Software_Devel/92   11/11/10 4:07p calvinho
57 * SW7401-4370: Separate BHDM_HDCP_RX_AINFO write into a separate function
58 *
59 * Hydra_Software_Devel/91   9/22/10 10:42a vle
60 * SW7335-837: Be sure to always validate RxBksv
61 *
62 * Hydra_Software_Devel/90   4/29/10 11:56a vle
63 * SW7342-110: Fix HDCP compliance test issue (test with repeater) for
64 * 7340/7342 and other big endian system
65 *
66 * Hydra_Software_Devel/89   4/7/10 3:54p vle
67 * SW7208-20, SW7342-110: fix DRIFT_FIFO underflow/overflow errors for
68 * HDCP compliance test 1A-07.
69 *
70 * Hydra_Software_Devel/88   3/24/10 11:47a vle
71 * SW7601-171: Add BI2C_P_SetupHdmiHwAccess to set up I2C for HDMI HDCP
72 * auto Ri/Pj link integrity check feature
73 *
74 * Hydra_Software_Devel/SW7601-171/2   3/10/10 6:39p vle
75 * SW7400-2713: Fix coverity issue
76 *
77 * Hydra_Software_Devel/SW7601-171/1   3/9/10 3:22p vle
78 * SW7601-171: Add BI2C_P_SetupHdmiHwAccess to set up I2C for HDMI HDCP
79 * auto Ri/Pj link integrity check feature
80 *
81 * Hydra_Software_Devel/87   2/26/10 5:18p vle
82 * SW7405-3016: Remove software i2c settings from HDM PI. This mode is
83 * configure in I2C module
84 *
85 * Hydra_Software_Devel/86   2/22/10 5:10p vle
86 * SW7335-669: add BHDM_HDCP_RX_BKSV_I2C_READ_ERROR and
87 * BHDM_HDCP_TX_AKSV_I2C_WRITE_ERROR errors constant.
88 *
89 * Hydra_Software_Devel/85   12/21/09 4:43p vle
90 * SW7405-3559: Disable Pj checking by default.
91 *
92 * Hydra_Software_Devel/84   11/16/09 2:50p rgreen
93 * SW7405-3409: Fix kernel mode compilation warnings
94 *
95 * Hydra_Software_Devel/83   11/13/09 3:47p jrubio
96 * SW7342-76: Make HMDI info functions DEBUG only
97 *
98 * Hydra_Software_Devel/82   9/28/09 4:29p vle
99 * SW7601-167: Merge fixes from bdvd_v3.0 branch to main branch.
100 * Fix build issue for platforms without auto Ri/Pj checking feature.
101 *
102 * Hydra_Software_Devel/81   9/24/09 6:04p vle
103 * SW7601-167: Merge fixes from bdvd_v3.0 branch to main branch.
104 * Fix build issue from an incorrect check in.
105 *
106 * Hydra_Software_Devel/80   9/24/09 4:53p vle
107 * SW7601-167: Merge fixes from bdvd_v3.0 branch to main branch.
108 *
109 * Hydra_Software_Devel/bdvd_v3.0/3   9/8/09 3:18p rbshah
110 * PR16468[DVD]:[ see HiDef-DVD bug tracking system for more info ].  Fix
111 * merge issue with HDCP not coming up on AVRs. Also allow Auto HW Pj
112 * checking to be enabled if so desired by the application.
113 *
114 * Hydra_Software_Devel/bdvd_v3.0/2   9/2/09 3:31p rbshah
115 * PR16468[DVD]:[ see HiDef-DVD bug tracking system for more info ].
116 * Merged with the latest portinginterface/hdm and syslib/hdcplib files.
117 *
118 * Hydra_Software_Devel/bdvd_v2.0/bdvd_v2.1/1   7/14/09 1:30p rbshah
119 * PR_15413[DVD]:[ see HiDef-DVD bug tracking system for more info ].
120 * Merge work from the HDMI certification branch. Also addresses PR15437
121 * and PR15220 (merged from v2.0). Plus coverity PR15782.
122 *
123 * Hydra_Software_Devel/bdvd_v2.0/bdvd_hdmi_cert_v2.1/2   7/9/09 9:42p rbshah
124 * Don't retry R0 I2C read -- Simplay hack
125 *
126 * Hydra_Software_Devel/bdvd_v2.0/bdvd_hdmi_cert_v2.1/1   7/8/09 12:18p rbshah
127 * Various fixes for Auto Hardware Ri,Pj checking. I2C changes are
128 * temporary. Switch from software to hardware Ri checking by default.
129 *
130 * Hydra_Software_Devel/79   7/17/09 7:47a vle
131 * PR56896: Fix build issue involving BHDM_HDCP_P_CheckForValidVideo
132 *
133 * Hydra_Software_Devel/78   7/14/09 11:28a rgreen
134 * PR56776: Prevent HDCP An Timeout; Reduce debug messages
135 *
136 * Hydra_Software_Devel/77   6/24/09 5:04p vle
137 * PR56341: Fix coverity issue
138 *
139 * Hydra_Software_Devel/76   5/12/09 2:11a vle
140 * PR 54851: Make sure to disable HDCP 1.1 only when the Pj link failures
141 * occur consecutively.
142 *
143 * Hydra_Software_Devel/75   5/5/09 5:14p vle
144 * PR 54851: Implement a dynamic mode in the PI where HDCP 1.1 feature
145 * will be disabled when a pre-define occurance of Pj Link Failures is
146 * met.
147 *
148 * Hydra_Software_Devel/74   3/3/09 8:23p vle
149 * PR50569: Add HW Ri/Pj checking feature. Merged from bdvd branch after
150 * Rajul's testing effort.
151 *
152 * Hydra_Software_Devel/73   2/24/09 8:29p vle
153 * PR51272: Merge to main branch
154 *
155 * Hydra_Software_Devel/PR51272/1   1/30/09 3:49p vle
156 * PR51272: Make sure to asset I_AUTH_REQUEST after each frame while An is
157 * not ready. This will help prevent An generation timeout issue.
158 * 
159 * Hydra_Software_Devel/bdvd_v2.0/2   1/23/09 10:13a rbshah
160 * PR_10346 [ see HiDef-DVD bug tracking system for more info ].  Checkin
161 * code drop from Anthony Le for Auto Ri,Pj feature in the
162 * 7601B0 (Digital Video PR50569).
163 *
164 * This is disabled by default and will be turned on once it has
165 * been tested and soaked.
166 *
167 * Did verify the A0 build!
168 *
169 * Hydra_Software_Devel/72   12/18/08 6:03p vle
170 * PR48987: HDCP errors should be considered as error and warning messages
171 *
172 * Hydra_Software_Devel/71   12/5/08 2:27p vle
173 * PR 48987: Change variable name for better description
174 *
175 * Hydra_Software_Devel/70   12/2/08 8:01p vle
176 * PR48987: Merge to main branch - add run time option to enable I2C bit
177 * bang mode.
178 *
179 * Hydra_Software_Devel/HDMI_TX_Plugfest11_200811/1   11/13/08 7:33p vle
180 * PR 48987: Add run time option to enable I2C bit bang mode.
181 *
182 * Hydra_Software_Devel/69   10/22/08 6:01p rgreen
183 * PR48233: Fix Coverity Issue evaluation order
184 *
185 * Hydra_Software_Devel/68   10/10/08 10:38a rgreen
186 * PR47781:Fix erroneous abort message for Authentications after hot plug
187 *
188 * Hydra_Software_Devel/67   9/10/08 11:56a vle
189 * PR 45988: ENC_EN/ENC_DIS signal can be generated by hardware on 7400E0
190 *
191 * Hydra_Software_Devel/66   8/1/08 5:07p vle
192 * PR 44758: fix compiler warning for kernel mode build.
193 *
194 * Hydra_Software_Devel/65   2/26/08 5:01p rgreen
195 * PR39995: Fix for HDCP Compliance Test 1B-03; check if HDCP has been
196 * aborted due to hot plug
197 *
198 * Hydra_Software_Devel/64   12/18/07 9:18p rgreen
199 * PR38235: Remove code to clear RDB_AUTHENTICATED bit.  Either ENC_EN or
200 * ENC_DIS should always be transmitted.  Remove redundant code to
201 * SET_RDB_AUTHENTICATED bit.  Add comments
202 *
203 * Hydra_Software_Devel/63   11/8/07 12:56a vle
204 * PR 36796: Increase the time out for generating An values from 10ms to 6
205 * frames (16ms each frames).
206 *
207 * Hydra_Software_Devel/62   11/7/07 4:14p rgreen
208 * PR36718: Clear I_ALWAYS_REKEY_ON_VSYNC when using HDCP 1.0
209 *
210 * Hydra_Software_Devel/61   10/20/07 8:44p rgreen
211 * PR36200: Fixes to support HDCP Compliance Testing.  Set Core
212 * Authenticaed after An generation
213 *
214 * Hydra_Software_Devel/60   10/17/07 6:25p rgreen
215 * PR36200: Add fixes to support HDCP Compliance Testing
216 *
217 * Hydra_Software_Devel/59   10/11/07 4:52p rgreen
218 * PR36035:  Add BHDM_CONFIG_HDCP_RI_SHORT_READ to enable Fast or Short
219 * I2C reads for HDMI Rx Ri' reads.  Default is standard I2C reads
220 *
221 * Hydra_Software_Devel/58   10/10/07 11:05a rgreen
222 * PR35874:
223 * Report error if TxCore does not complete V Calculation
224 * Move the reading of the V Calculation from BHDM_HDCP_WriteTxKsvFifo
225 * to BHDM_HDCP_RepeaterAuthenticateLink since Repeater Authentication can
226 * occur  with no Ksvs (no downstream devices)
227 *
228 * Hydra_Software_Devel/57   9/6/07 5:01p rgreen
229 * PR34668: add code to support HDCP 1.1 Pj Checking
230 *
231 * Hydra_Software_Devel/56   5/23/07 11:31p rgreen
232 * PR31560:Remove excess delay in reading HDCP R0 value from receiver
233 *
234 * Hydra_Software_Devel/55   9/15/06 5:38p rgreen
235 * PR24304:  Add test features for Plugfest
236 *
237 * Hydra_Software_Devel/54   6/26/06 12:04p rgreen
238 * PR22342: Detect three successive HDCP Pj failures prior to forcing an
239 * un-Authenticated link
240 *
241 * Hydra_Software_Devel/53   6/2/06 3:25p rgreen
242 * PR20866: Add option to disable Pj checking; default is on
243 * Add BHDM_HDCP_Get/SetOptions
244 * Modify LIC return codes to report specific Ri or Pj link failure
245 *
246 * Hydra_Software_Devel/52   5/1/06 2:53p rgreen
247 * PR8896: Debug cleanup.  Remove second instance of r0 generated from the
248 * Ri interrupt.
249 *
250 * Hydra_Software_Devel/51   2/8/06 4:37p rgreen
251 * PR19552: Retry i2c read due to error up to four times during HDCP LIC
252 *
253 * Hydra_Software_Devel/50   2/3/06 4:36p rgreen
254 * PR8896: Remove depracated functions
255 *
256 * Hydra_Software_Devel/49   10/21/05 5:44p rgreen
257 * PR17750:
258 * Move HDCP version banner from BKsv read to when HDCP An value is
259 * generated; reduces debug messages
260 * Clear HDCP abort flag after loading HDCP keys
261 * Allow return of  new BHDM_HDCP_AUTH_ABORTED  value
262 * Add debug config flag for HDMI Rx BCaps register.
263 *
264 * Hydra_Software_Devel/48   10/3/05 4:20p rgreen
265 * PR17428: Force re-read of Bcaps register at all times. remove mode used
266 * to prevent redundant i2c reads
267 *
268 * Hydra_Software_Devel/47   7/14/05 5:13p rgreen
269 * PR16287: Fix incorrectly reported HDCP Link Success when I2C Read
270 * failure occurs (monitor power down).  Should be reported as a failure.
271 *
272 * Hydra_Software_Devel/46   6/27/05 6:21p rgreen
273 * PR15217: Add Auth Support for HDCP Repeaters with Device Count 0;
274 * Use bhdm_config.h configuration option.
275 * Add option for Repeater Simulation Test
276 *
277 * Hydra_Software_Devel/45   4/21/05 7:42p rgreen
278 * PR14622: Add HDMI API to return KSV values
279 * Add functions
280 * BHDM_HDCP_GetRxKsv
281 * BHDM_HDCP_GetRepeaterKsvFifo
282 *
283 * Hydra_Software_Devel/44   3/8/05 5:46p rgreen
284 * PR9474: HDCP 1.1 Support
285 * Explicitly set HDCP Version 1.0 support when reading BCaps register
286 *
287 * Hydra_Software_Devel/43   3/3/05 5:21p rgreen
288 * PR9474: HDCP 1.1 Support
289 * BHDM_HDCP_SetVersion is now depracated;
290 * HDCP Version set automatically when BCaps read
291 * (See BHDM_HDCP_ReadRxBksv & BHDM_HDCP_GetRxCaps)
292 *
293 * Hydra_Software_Devel/42   3/1/05 5:07p rgreen
294 * PR8896:
295 * Eliminate redundant I2C reads of Rx BCaps register
296 *
297 * Hydra_Software_Devel/41   2/24/05 3:46p rgreen
298 * PR14230: Add HDCP bond status detection to chip interface
299 *
300 * Hydra_Software_Devel/40   2/23/05 10:37a rgreen
301 * PR8896: Fix Pj debug message; turn on BCaps messages
302 *
303 * Hydra_Software_Devel/39   2/18/05 1:34p rgreen
304 * PR14181: HDCP Auth Failure after repeated hotplugs / on/off cycles
305 * Increase the wait time for HDCP authentication from 10ms to 50ms.
306 * Authentication should not take more than 1 field ~16ms
307 *
308 * Hydra_Software_Devel/38   2/4/05 1:48p rgreen
309 * PR9474: HDCP 1.1 Support; add runtime identifier for file/revision
310 *
311 * Hydra_Software_Devel/37   2/4/05 1:04p rgreen
312 * PR9474: HDCP 1.1 Support
313 * Remove depracated   BHDM_HDCP_Version eHdcpVersion from
314 * BHDM_XmitEncrypted.  Already part of hdmi handle.
315 *
316 * Hydra_Software_Devel/36   2/4/05 10:36a rgreen
317 * PR9474: HDCP 1.1 Support
318 * Add Pj Link Integrity Check
319 *
320 * Hydra_Software_Devel/35   1/3/05 12:56p rgreen
321 * PR8896: HDCP Bug Fixes
322 * Fix bit shifting when checking repeater depth in BStatus register
323 * Add timeouts when waiting for TxRepeater calculations
324 * Fix loading of SHA-1 Rx value to Tx Repeater Core for big endian
325 * environments
326 * Fix InitializeRepeaterAuthentication for big endian environment
327 * Add debug messages for debugging big endian environment
328 *
329 * Hydra_Software_Devel/34   12/9/04 2:38p rgreen
330 * PR8896: Change BHDM_HDCP_AuthenticateRepeater argument
331 * RepeaterAuthenticated from bool to uint8_t.
332 *
333 * Clean up debug messages
334 *
335 * Hydra_Software_Devel/33   12/9/04 1:25p rgreen
336 * PR8896: Fix bug with HDCP Repeater Authentication;
337 * Restore writing BCaps value to Tx HDCP core... not needed for
338 * Rx Authentication, but needed for Repeater Authentication
339 *
340 * Make sure  HDCP Spec TestAn values not generated in RandomAn Mode;
341 * generate new RandomAn if TestAn generated.
342 *
343 * Hydra_Software_Devel/32   11/12/04 4:35p rgreen
344 * PR8896:  Fix HDCP Authentication errors in big endian environments
345 *
346 * Hydra_Software_Devel/31   10/21/04 6:26p rgreen
347 * PR8896: Remove HDCP Key functions used for debug purposes.
348 *
349 * Hydra_Software_Devel/30   10/18/04 11:58a rgreen
350 * PR9474: Add HDCP 1.1 Support
351 * HDCP 1.1 not fully implemented
352 * Replace private BHDM_HDCP_P_SetVersion with new API call
353 * BHDM_HDCP_SetVersion
354 * Remove writing BCaps value to Tx HDCP core... un-neccessary
355 * BHDM_HDCP_XmitEncrypted no longer uses HDCP Version; HdcpVersion set by
356 * BHDM_HDCP_SetVersion
357 * argument left for legacy reasons.
358 * Modified BHDM_HDCP_GetRxStatus API call (RxStatus is uint16_t not
359 * uint8_t)
360 * Add debug messages for HDCP Rx BCaps (cabailities)
361 * Add debug messages for HDCP Rx BStatus
362 * Remove BHDM_HDCP_EnableDviEESS... handled by BHDM_HDCP_SetVersion
363 *
364 * Hydra_Software_Devel/29   9/24/04 6:21p rgreen
365 * PR9474:  Fix HDCP KSV FIFO reading
366 *
367 * Hydra_Software_Devel/28   9/23/04 8:44p rgreen
368 * PR12728: fix compiler warnings
369 * PR8896: Fix Pj output message
370 *
371 * Hydra_Software_Devel/27   9/15/04 10:56a rgreen
372 * PR8896:
373 * Remove BHDM_HDCP_VerifyLink function; no longer used
374 *
375 * Hydra_Software_Devel/26   8/18/04 6:52p rgreen
376 * PR 12116: Add HDCP Key Loading Support
377 * Warn RDB_KeyLoad function to be removed
378 *
379 * Hydra_Software_Devel/25   8/18/04 6:19p rgreen
380 * PR12116: Add HDCP Key Loading Support
381 * Fix DEBUG messages
382 *
383 * Hydra_Software_Devel/24   6/4/04 2:01p rgreen
384 * PR9474: HDMI API Development / Test
385 * Fix HDCP BStatus write to the HDCP core
386 *
387 * Hydra_Software_Devel/23   5/13/04 4:25p rgreen
388 * PR 10273: HDMI / HDCP Revocation/renewability support requirement
389 *
390 * Enable Repeater authetntication support.
391 *
392 * Hydra_Software_Devel/22   4/29/04 12:23p rgreen
393 * PR8896: HDMI Development
394 * Re-insert HDCP_VerifyLink to support B0 compilation
395 *
396 * Hydra_Software_Devel/22   4/29/04 12:15p rgreen
397 * PR8896: HDMI Development
398 * Re-insert HDCP_VerifyLink to support B0 compilation
399 *
400 * Hydra_Software_Devel/21   4/28/04 11:00a rgreen
401 * PR8896: HDMI Development
402 * Removed code for BHDM_HDCP_VerifyLink; use
403 * BHDM_HDCP_RiLinkIntegrityCheck instead
404 * Use one 8 byte I2C Write to the Rx for the HDCP An value vs 2 4 byte
405 * writes
406 * Delay 100ms for the Rx to complete HDCP calculations once the Aksv is
407 * written
408 * Reset Ri counter when authentication is cleared.
409 * Remove toggling of the MUX_VSYNC bit when activating encrypted
410 * transmission
411 * Get Pj value for RiLinkIntegrityCheck
412 *
413 * Hydra_Software_Devel/20   4/5/04 1:18p rgreen
414 * PR8896: HDMI API Development/Test
415 * Clear AUTH_REQUEST bit immediately after setting; reather than after An
416 * value is generated.  Clear additional bits in the HDCP_CTL register in
417 * the same manner.
418 *
419 * Verify all Tx Core components (HDCP + Scheduler)  are authenticated
420 * before setting the link as authenticated.
421 *
422 * Hydra_Software_Devel/19   3/20/04 5:13p rgreen
423 * PR8896: HDMI API Development/Test
424 * Add timeouts for HDCP Ri and An  calculations
425 *
426 * Hydra_Software_Devel/18   2/16/04 5:10p rgreen
427 * PR8896: HDMI API Development/Test
428 * Change BHDM_IsRxDeviceAttached to BHDM_RxDeviceAttacde.
429 * return code indicates function success/failure;use function
430 * argument for DeviceAttached status
431 *
432 * Hydra_Software_Devel/17   2/14/04 1:50p rgreen
433 * PR8896: HDMI API Development/Test
434 * Modify Debug Module Name
435 * Fix compilation errors/warnings
436 *
437 * Hydra_Software_Devel/16   2/13/04 7:53p rgreen
438 * PR8896: HDMI API Development/Test
439 * Add code for HDCP Repeater Support
440 * Change BHDM_HDCP_ReadReapeaterKsvFIFO to
441 * BHDM_HDCP_ReadRxRepeaterKsvFIFO
442 * Add BHDM_HDCP_WriteTxKsvFIFO
443 * Add checkForRepeater function
444 *
445 * Use BHDM_CONFIG_REPEATER_SIMULATION_TEST to generate Tx verifications values contained in
446 * the HDCP 1.1 Spec
447 *
448 * Hydra_Software_Devel/15   1/27/04 1:03p rgreen
449 * PR8896: HDMI API Development/Test
450 * Move AuthenticateRepeater function to BHDMlib; needs access to XPT
451 * handle for authentication with HDCP Repeater
452 *
453 * Hydra_Software_Devel/14   1/26/04 11:38a rgreen
454 * PR9474: Add HDCP 1.1 functionality
455 * Add BHDM_HDCP_Version enumeration for HDCP Version unused/1_0/1_1
456 *
457 * Replace BHDM_HDCP_XmitEncrypted bool argument with BHDM_HDCP_Version
458 * enumeration.
459 * Caller can decide which version of HDCP to used based on Rx Capability
460 *
461 * Add BHDM_HDCP_RiLinkIntegrityCheck to replace BHDM_HDCP_VerifyLink...
462 * VerifyLink will be eventually removed
463 *
464 * Add BHDM_HDCP_PjLinkIntegrityCheck stub for HDCP 1.1 functionality
465 *
466 * Add toggle to AUTH_REQUEST bit for GenerateAn
467 *
468 * Enable Always Rekey on VSync functionality (HDCP 1.1) to the
469 * XmitEncryprpted function
470 *
471 * Hydra_Software_Devel/13   1/20/04 7:04p rgreen
472 * PR8896: HDMI API Development/Test
473 * Add flag to BHDM_XmitEncrypted to enable HDCP 1.1 Features
474 *
475 * Hydra_Software_Devel/12   1/12/04 3:25p rgreen
476 * PR8896: HDMI API Development
477 * Add appropriate endian macros for i2c <--> register values
478 *
479 * Hydra_Software_Devel/11   12/15/03 5:08p rgreen
480 * PR8896:
481 * Change BHDM_IsHdmiRxAttached to BHDM_IsRxDeviceAttached...
482 * Disable non implemented functions (stubs) that give compiler warnings
483 *
484 * Hydra_Software_Devel/10   12/10/03 3:35p rgreen
485 * PR8727:
486 * Fix Compilation Warnings
487 *
488 * Hydra_Software_Devel/9   12/10/03 3:32p rgreen
489 * PR8727:
490 * Fix Compilation Warnings
491 *
492 * Hydra_Software_Devel/8   12/10/03 10:20a rgreen
493 * PR8727:
494 * Fix compilation warnings
495 *
496 * Hydra_Software_Devel/7   11/24/03 3:04p rgreen
497 * Expose BHDM_HDCP_ReadRxBksv,
498 *       BHDM_HDCP_GenerateAn, and
499 *       BHDM_HDCP_AuthenticateLink as public functions to be used in
500 * higher level libraries/apps.
501 * Add supporting functions BHDM_HDCP_WriteTxAksvToRx and
502 * BHDM_HDCP_EnableSerialKeyLoad
503 * for use in authenticating receivers in higher level libraries/apps.
504 *
505 * Remove AuthenticateReceiver from Porting Interface
506 * Use status registers to check for completion of HDCP calculations
507 *
508 * Add debug function BHDM_HDCP_DEBUGTEST_RdbLoadTxKeys to support
509 * testing.
510 *
511 * Hydra_Software_Devel/6   11/7/03 5:33p rgreen
512 * Clear I_AUTH_REQUEST bit to enable advancing Ri authentication  values.
513 *
514 * Hydra_Software_Devel/5   11/5/03 4:51p rgreen
515 * Add BHDM_HDCP_IsLinkAuthenticated function which can be used to check
516 * authentication status of the link.
517 * Add missing BDBG_ENTER / LEAVE macros for some functions
518 * Turn off AN_INFLUENCE bits when generating test An values
519 * Display entire generated An value in one debug message
520 * Fix error writing Aksv to the Receiver
521 * Configure for loading keys through register vs serial key loader
522 * Fix error loading HDCP Keys
523 * Add Return Codes (rc) to VerifyLink
524 * Fix debug statements in AuthenticateRepeater function (not implemented
525 * yet)
526 *
527 * Hydra_Software_Devel/4   10/24/03 7:13p rgreen
528 * Remove NOT_IMPLEMENTED return values for newly implemented functions
529 *
530 * Hydra_Software_Devel/3   10/23/03 6:22p rgreen
531 * Fix unreferenced variable compilation warnings
532 *
533 * Hydra_Software_Devel/2   10/23/03 5:27p rgreen
534 * Use KNI memory functions
535 *
536 * Hydra_Software_Devel/1   10/22/03 6:19p rgreen
537 * Initial Version
538 *
539 ***************************************************************************/
540#include "bstd.h"
541#include "breg_endian.h"
542
543#include "bhdm_config.h"
544#include "bhdm.h"
545#include "bhdm_priv.h"
546#include "bhdm_hdcp.h"
547
548BDBG_MODULE(BHDM_HDCP) ;
549
550#define BHDM_CHECK_RC( rc, func )                     \
551do                                                \
552{                                                                                         \
553        if( (rc = BERR_TRACE(func)) != BERR_SUCCESS ) \
554        {                                                                                     \
555                goto done;                                                            \
556        }                                                                                     \
557} while(0)
558
559
560static unsigned int BHDM_HDCP_P_NumberOfSetBits(const unsigned char *bytes, int nbytes) ;
561
562static BERR_Code BHDM_HDCP_P_CheckRevokedKsvList(
563        const uint8_t *pRevokedKsvList, 
564        const uint16_t uiRevokedKsvCount, 
565        uint8_t *pRxKsvList, 
566        uint16_t uiRxDeviceCount, 
567        bool *bRevoked) ;
568
569
570#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
571static BERR_Code BHDM_HDCP_P_AutoRiLinkIntegrityCheck( 
572        BHDM_Handle hHDMI     /* [in] HDMI handle */
573) ;
574
575static BERR_Code BHDM_HDCP_P_AutoPjLinkIntegrityCheck(
576   BHDM_Handle hHDMI              /* [in] HDMI handle */
577) ;
578
579static BERR_Code BHDM_HDCP_P_ConfigureAutoRi(
580        BHDM_Handle hHDMI     /* [in] HDMI handle */
581) ;
582
583static BERR_Code BHDM_HDCP_P_ConfigureAutoPj(
584        BHDM_Handle hHDMI     /* [in] HDMI handle */
585) ;
586
587static BERR_Code BHDM_HDCP_P_EnableAutoRiPjChecking (
588        BHDM_Handle hHDMI,      /* [in] HDMI handle */
589        uint8_t uiPjChecking
590) ;
591
592static BERR_Code BHDM_HDCP_P_DisableAutoRiPjChecking (
593        BHDM_Handle hHDMI               /* [in] HDMI handle */
594) ;
595#endif
596
597static BERR_Code BHDM_HDCP_P_CheckForValidVideo(
598        BHDM_Handle hHDMI              /* [in] HDMI handle */
599) ;
600
601
602/******************************************************************************
603unsigned int BHDM_HDCP_P_NumberOfSetBits
604Summary: Get the number of Set Bits
605*******************************************************************************/
606static unsigned int BHDM_HDCP_P_NumberOfSetBits(const unsigned char *bytes, int nbytes)
607{
608        int i, j ;
609        int bit ;
610        int count = 0 ;
611        uint8_t byteToCheck;
612
613        count = 0 ;
614        for (i = 0; i < nbytes; i++)
615        {
616                bit = 1 ;
617                byteToCheck = bytes[i];
618                for (j = 0; j < 8 ; j++)
619                {
620                        if (bit & byteToCheck)
621                                count++ ;
622                        bit = bit << 1 ;
623                }
624        }
625        return count ;
626} /* end BHDM_HDCP_P_NumberOfSetBits */
627
628
629/******************************************************************************
630BERR_Code BHDM_HDCP_P_CheckRevokedKsvList
631Summary: Check if retrieved Ksv(s) are on the list of revoked Ksvs
632*******************************************************************************/
633BERR_Code BHDM_HDCP_P_CheckRevokedKsvList(
634        const uint8_t *pRevokedKsvList, 
635        const uint16_t uiRevokedKsvCount, 
636        uint8_t *pRxKsvList, 
637        uint16_t uiRxDeviceCount,
638        bool *bRevokedKsv) 
639{       
640        uint16_t i, j ;
641        uint16_t uiRxKsvIndex ;
642        uint16_t uiRevokedKsvIndex ;
643       
644        uint8_t k ;
645       
646        *bRevokedKsv = false ;
647       
648        /* check each retrieved KSV against the Revoked KSV List */
649        for (i = 0 ; i < uiRxDeviceCount ; i++)                  /* for each RxKsv */
650        {
651                uiRxKsvIndex = i * BHDM_HDCP_KSV_LENGTH ;
652               
653                /* display each KSV to check debugging */
654                BDBG_MSG(("Checking RxBksv (Device %d): %02x %02x %02x %02x %02x", 
655                        i, pRxKsvList[uiRxKsvIndex + 4], 
656                        pRxKsvList[uiRxKsvIndex + 3], pRxKsvList[uiRxKsvIndex + 2], 
657                        pRxKsvList[uiRxKsvIndex + 1], pRxKsvList[uiRxKsvIndex + 0]));
658                       
659                for (j = 0 ; j < uiRevokedKsvCount; j++)        /* for each Revoked Ksv */
660                {
661                        /*
662                        * SRM messages, which contain the Revoked Keys are stored in big endian
663                        * format, therefore the comparison must be reveresed for the retrieved
664                        * Ksvs which are in little endian format
665                        */
666                               
667                        /* set the Revoked Ksv byte index to the end of the stored key
668                        * i.e. at the LSB
669                        */
670                        uiRevokedKsvIndex = j * BHDM_HDCP_KSV_LENGTH + BHDM_HDCP_KSV_LENGTH - 1 ;
671                       
672                        for (k = 0 ; k < BHDM_HDCP_KSV_LENGTH; k++) /* for each Ksv Byte */
673                        {
674#if 0                           
675                                /* debug KSV revocation */
676                                BDBG_MSG(("Compare Ksv LSB %d: %02x - %02x", k,
677                                        pRxKsvList[uiRxKsvIndex + k],               /* little endian */
678                                        pRevokedKsvList[uiRevokedKsvIndex - k])) ;  /* big endian */
679#endif                                 
680                               
681                                if (pRxKsvList[uiRxKsvIndex + k] != pRevokedKsvList[uiRevokedKsvIndex - k])
682                                        break ;  /* no match; go to next Revoked Key */
683
684                                /* all bytes matched */                                 
685                                if (k + 1 == BHDM_HDCP_KSV_LENGTH)
686                                {
687                                        BDBG_WRN(("RxBksv appears in revoked list")) ;
688                                        *bRevokedKsv = true ;
689                                        goto done ;
690                                }
691                        }
692                }
693        }
694               
695done:
696        return BERR_SUCCESS ;           
697}
698
699
700/******************************************************************************
701BERR_Code BHDM_HDCP_ReadRxBksv
702Summary: Read the HDCP Bksv value from the receiver
703*******************************************************************************/
704BERR_Code BHDM_HDCP_ReadRxBksv(
705   BHDM_Handle hHDMI,              /* [in] HDMI handle */
706   const uint8_t *pRevokedKsvList, /* [in] pointer to Revoked KSV List */
707   const uint16_t uiRevokedKsvCount /* [in] number of KSVs in Revoked Ksv List */
708)
709{
710        BERR_Code   rc = BERR_SUCCESS;
711
712        uint32_t    Register ;
713        uint32_t    BksvRegisterValue ;
714        unsigned char   RxBksv[] = { 0x00, 0x01, 0x02, 0x03, 0x04 }; /* LSB...MSB */
715        /*
716        **      FYI B1 Bksv Test Value from HDCP Specification
717        **     RxBksv[] = { 0xcd, 0x1a, 0xf2, 0x1e, 0x51 };
718        */
719        uint8_t BCaps ;
720        uint8_t RxDeviceAttached ;
721        bool bRevoked ;
722               
723        BDBG_ENTER(BHDM_HDCP_ReadRxBksv) ;
724
725
726        /* make sure HDMI Cable is connected to something... */
727        BHDM_CHECK_RC(rc, BHDM_RxDeviceAttached(hHDMI, &RxDeviceAttached));
728        if (!RxDeviceAttached)
729        {
730                rc = BHDM_NO_RX_DEVICE ;
731                BDBG_WRN(("No DVI/HDMI Device Found")) ;
732                goto done ;
733        }
734
735        /* read the BCaps first */
736        BCaps = 0 ;
737        BHDM_CHECK_RC(rc, BHDM_HDCP_GetRxCaps(hHDMI, &BCaps)) ;
738       
739       
740#if BHDM_CONFIG_REPEATER_SIMULATION_TEST       
741        BCaps |= BHDM_HDCP_RxCaps_eHdcpRepeater ; 
742#endif
743
744
745        /* We can't access I2C if control has been handed over to HW */
746        if (hHDMI->bAutoRiPjCheckingEnabled)
747        {
748                BKNI_Memcpy(RxBksv, hHDMI->HDCP_RxKsv, BHDM_HDCP_KSV_LENGTH) ;
749        }
750        else
751        {
752                /* try to read the RxBksv */
753                rc = BREG_I2C_Read(hHDMI->hI2cRegHandle, 
754                        BHDM_HDCP_RX_I2C_ADDR,  BHDM_HDCP_RX_BKSV0, RxBksv, BHDM_HDCP_KSV_LENGTH ) ;   
755                if (rc != BERR_SUCCESS)
756                {
757                        BDBG_ERR(("Bksw I2C read error"));     
758                        rc = BHDM_HDCP_RX_BKSV_I2C_READ_ERROR;
759                        goto done;
760                }
761        }
762
763        /* Verify RxBksv has 20 zeros & 20 ones */
764        if (BHDM_HDCP_P_NumberOfSetBits(RxBksv, BHDM_HDCP_KSV_LENGTH) != 20) 
765        {
766                BDBG_ERR(("Valid RxBksv contain 20 1s and 20 0s")) ;
767                rc = BHDM_HDCP_RX_BKSV_ERROR ;
768                goto done ;
769        }
770       
771        /* display changes in KSV for debugging */
772        if (BKNI_Memcmp(RxBksv, hHDMI->HDCP_RxKsv, BHDM_HDCP_KSV_LENGTH))
773        {
774                BDBG_MSG(("RxBksv = %02x %02x %02x %02x %02x", 
775                                RxBksv[4], RxBksv[3], RxBksv[2], RxBksv[1], RxBksv[0]));
776        }
777       
778
779        BKNI_Memcpy(hHDMI->HDCP_RxKsv, RxBksv, BHDM_HDCP_KSV_LENGTH) ;
780       
781       
782        /* check the retrieved KSV against the Revoked KSV List */
783        if (uiRevokedKsvCount)
784        {
785                BHDM_HDCP_P_CheckRevokedKsvList(
786                        (uint8_t *) pRevokedKsvList, uiRevokedKsvCount, RxBksv, 1, &bRevoked) ;
787               
788                if (bRevoked)
789                {
790                        rc = BHDM_HDCP_RX_BKSV_REVOKED ;
791                        goto done ;
792                }
793        }
794       
795        /* write the 4 LSBs RxBksv to the transmitter... */
796        BksvRegisterValue =
797                  RxBksv[0]
798                | RxBksv[1] <<  8
799                | RxBksv[2] << 16
800                | RxBksv[3] << 24 ;
801               
802        Register = BCHP_FIELD_DATA(HDMI_BKSV0, I_BKSV_31_0, BksvRegisterValue) ;
803        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_BKSV0, Register) ;
804#if 0   
805        BDBG_MSG(("BKSV0 Register: 0x%08X", Register)) ;
806#endif 
807
808
809        /*
810        -- write the 1 MSB RxBksv to the transmitter...
811        -- also check if we are authenticating with a repeater
812        */
813        BksvRegisterValue = RxBksv[4];
814        Register = BCHP_FIELD_DATA(HDMI_BKSV1, I_BKSV_39_32, BksvRegisterValue)
815                |  BCHP_FIELD_DATA(HDMI_BKSV1, BCAPS_7_0, BCaps) ;
816#if 0
817        BDBG_MSG(("BKSV1 Register Value: 0x%08X", Register)) ;
818#endif 
819        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_BKSV1, Register) ;
820
821done:
822        BDBG_LEAVE(BHDM_HDCP_ReadRxBksv) ;
823        return rc ;
824} /* end BHDM_HDCP_ReadRxBksv */
825
826
827static BERR_Code BHDM_HDCP_P_CheckForValidVideo(
828        BHDM_Handle hHDMI              /* [in] HDMI handle */
829)
830{
831        BERR_Code rc = BERR_SUCCESS ;
832        BREG_Handle hRegister ;
833        uint32_t Register ;
834        bool bUnderFlow, bOverFlow, bMasterMode;
835        uint8_t uRdAddr , uWrAddr ;
836        uint8_t uPrevRdAddr , uPrevWrAddr ;
837
838        hRegister = hHDMI->hRegister ;
839
840        /* make sure PLL is up/running */
841#if BHDM_CONFIG_65NM_SUPPORT
842        {
843                bool bPllPoweredDown ;
844       
845                /* check if pll is powered on */
846                Register = BREG_Read32(hRegister, BCHP_HDMI_TX_PHY_HDMI_TX_PHY_RESET_CTL) ;
847
848                /* use bUnderFlow variable to check pll pwrdn status */
849                bPllPoweredDown = BCHP_GET_FIELD_DATA(Register, HDMI_TX_PHY_HDMI_TX_PHY_RESET_CTL, PLL_PWRDN) ;
850                if (bPllPoweredDown)
851                {
852                        BDBG_ERR(("PLL is powered down; HDCP Authentication cannot proceed")) ;
853                        rc = BHDM_HDCP_PLL_PWRDN ;
854                        goto done ;
855                }
856               
857                BDBG_MSG(("PLL power... OK")) ;
858        }
859#endif
860
861        /* Check Drift FIFO, but do so only if we're in Slave mode */
862        rc = BHDM_GetHdmiDataTransferMode(hHDMI, &bMasterMode);
863
864        if (rc == BERR_SUCCESS && !bMasterMode)
865        {
866                /* capture FIFO pointers */
867                Register = BREG_Read32(hRegister , BCHP_HDMI_FIFO_CTL) ;
868                Register &= ~ BCHP_MASK(HDMI_FIFO_CTL, CAPTURE_POINTERS) ;
869                BREG_Write32(hRegister, BCHP_HDMI_FIFO_CTL, Register) ;
870               
871                Register |= BCHP_MASK(HDMI_FIFO_CTL, CAPTURE_POINTERS) ;
872                BREG_Write32(hRegister, BCHP_HDMI_FIFO_CTL, Register) ;
873
874                /* check for over/underflow */
875                Register = BREG_Read32(hRegister, BCHP_HDMI_READ_POINTERS) ;
876                bOverFlow = BCHP_GET_FIELD_DATA(Register, HDMI_READ_POINTERS, DRIFT_OVERFLOW) ;
877                bUnderFlow = BCHP_GET_FIELD_DATA(Register, HDMI_READ_POINTERS, DRIFT_UNDERFLOW) ;
878
879                if (bUnderFlow)
880                {
881                        BDBG_ERR(("DRIFT FIFO Under Flow; HDCP Authentication cannot proceed")) ;
882                        rc = BHDM_HDCP_FIFO_UNDERFLOW ;
883                        BHDM_InitializeDriftFIFO(hHDMI);
884                        goto done ;
885                }
886                else if (bOverFlow)
887                {
888                        BDBG_ERR(("DRIFT FIFO Over Flow; HDCP Authentication cannot proceed")) ;
889                        rc = BHDM_HDCP_FIFO_OVERFLOW ;
890                        BHDM_InitializeDriftFIFO(hHDMI);
891                        goto done ;
892                }
893        }
894
895        /* save current pointers */
896        Register = BREG_Read32(hRegister, BCHP_HDMI_READ_POINTERS) ;
897
898        uPrevRdAddr = BCHP_GET_FIELD_DATA(Register, HDMI_READ_POINTERS, DRIFT_RD_ADDR_7_0) ;
899        uPrevWrAddr = BCHP_GET_FIELD_DATA(Register, HDMI_READ_POINTERS, DRIFT_WR_ADDR_7_0) ;
900       
901        /* capture FIFO pointers again */
902        Register = BREG_Read32(hRegister , BCHP_HDMI_FIFO_CTL) ;
903        Register &= ~ BCHP_MASK(HDMI_FIFO_CTL, CAPTURE_POINTERS) ;
904        BREG_Write32(hRegister, BCHP_HDMI_FIFO_CTL, Register) ;
905       
906        Register |= BCHP_MASK(HDMI_FIFO_CTL, CAPTURE_POINTERS) ;
907        BREG_Write32(hRegister, BCHP_HDMI_FIFO_CTL, Register) ;
908
909        /* read compare FIFO pointers */       
910        Register = BREG_Read32(hRegister, BCHP_HDMI_READ_POINTERS) ;
911        uRdAddr = BCHP_GET_FIELD_DATA(Register, HDMI_READ_POINTERS, DRIFT_RD_ADDR_7_0) ;
912        uWrAddr = BCHP_GET_FIELD_DATA(Register, HDMI_READ_POINTERS, DRIFT_WR_ADDR_7_0) ;
913        BDBG_MSG(("Previous: Read  Pointer= %3d Write Pointer= %3d",  uPrevRdAddr, uPrevWrAddr)) ;
914        BDBG_MSG((" Current: Read  Pointer= %3d Write Pointer= %3d",  uRdAddr, uWrAddr)) ;
915
916        if ((uRdAddr == uPrevRdAddr) || (uWrAddr == uPrevWrAddr))
917        {
918                BDBG_ERR(("Video to HDMI Core is stalled...")) ;
919                rc = BHDM_UNSUPPORTED_VIDEO_FORMAT ;
920                goto done ;
921        }
922
923        BDBG_MSG(("Video data to HDMI Core... OK")) ;
924               
925
926done:
927        return rc ;
928               
929}
930
931
932/******************************************************************************
933BERR_Code BHDM_HDCP_GenerateAn
934Summary: Generate the HDCP An value for HDCP calculations
935*******************************************************************************/
936BERR_Code BHDM_HDCP_GenerateAn(
937        BHDM_Handle hHDMI,              /* [in] HDMI handle */
938        BHDM_HDCP_AnSelect AnSelection) /* [in] HDCP An type value to use */
939{
940        BERR_Code   rc = BERR_SUCCESS;
941        BREG_Handle hRegister ;
942        uint32_t    Register ;
943        uint32_t        AnMsb, AnLsb ;
944        uint8_t i ;
945        uint8_t timeoutFrames ;
946        uint8_t AnReady ;
947        uint8_t AnValue[BHDM_HDCP_AN_LENGTH] ;
948        bool    bTestAnGenerated = false ;
949        bool bHdcpCapable ;
950
951#define NUM_TEST_AN_VALUES 4
952static const uint8_t ucHdcpSpecTestAnValues[NUM_TEST_AN_VALUES][BHDM_HDCP_AN_LENGTH] =
953        {
954                { 0x03, 0x04, 0x07, 0x0c, 0x13, 0x1c, 0x27, 0x34},  /* A1/B1 */
955                { 0xe5, 0x0f, 0xd1, 0x3a, 0xa5, 0x62, 0x5e, 0x44},  /* A1/B2 */
956                { 0x07, 0x6e, 0xc6, 0x01, 0xbb, 0xc2, 0xbe, 0x83},  /* A2/B1 */
957                { 0x4d, 0xa7, 0x06, 0x54, 0x17, 0xf7, 0x51, 0x03}   /* A2/B2 */
958        } ;
959       
960
961        BDBG_ENTER(BHDM_HDCP_GenerateAn) ;
962
963        if (hHDMI->bHdcpAnRequest)
964        {
965                BDBG_ERR(("HDCP An value already requested")) ;
966                return BHDM_HDCP_MULTIPLE_AN_REQUEST ;
967        }
968
969        /* new authentication attempt */
970        BDBG_WRN(("HDCP Authentication Request")) ;
971        BDBG_MSG(("*****************************************")) ;
972        BDBG_MSG(("$brcm_Workfile: bhdm_hdcp.c $")) ;
973        BDBG_MSG(("$brcm_Revision: Hydra_Software_Devel/100 $")) ;
974        BDBG_MSG(("$brcm_Date: 1/3/12 3:27p $")) ;
975        BDBG_MSG(("*****************************************")) ;
976
977        hRegister = hHDMI->hRegister ;
978
979#if BHDM_CONFIG_DEBUG_PJ_CHECKING
980        BDBG_WRN(("!!!!! Pj Check Test... video will be solid green or magenta color !!!!! ")) ;
981        BDBG_WRN(("!!!!! Ri Sequence should be consistent on every authentication  !!!!! ")) ;
982        Register = BREG_Read32(hRegister,  BCHP_HDMI_CP_TST) ;
983        Register &= 
984                ~(BCHP_MASK(HDMI_CP_TST, I_TST_FORCE_VIDEO_ALL_ONES) 
985                | BCHP_MASK(HDMI_CP_TST, I_TST_FORCE_VIDEO_ALL_ZEROS)) ;
986
987        Register |= BCHP_FIELD_DATA(HDMI_CP_TST,  I_TST_FORCE_VIDEO_ALL_ZEROS, 1) ;
988               
989        BREG_Write32(hRegister, BCHP_HDMI_CP_TST, Register) ;
990        AnSelection = BHDM_HDCP_AnSelect_eTestA1B1An ;
991#endif 
992
993       
994        bHdcpCapable = false ;
995        BHDM_CHECK_RC(rc, BCHP_GetFeature(hHDMI->hChip, BCHP_Feature_eHdcpCapable, &bHdcpCapable)) ;
996        if (!bHdcpCapable)
997        {
998                BDBG_ERR(("#############################")) ;
999                BDBG_ERR(("HDCP is DISABLED on this part")) ;
1000                BDBG_ERR(("#############################")) ;
1001                rc = BERR_NOT_SUPPORTED ;
1002                goto done ;
1003        } 
1004
1005        /* clear previously received values; for debug reporting */
1006        BKNI_Memset(hHDMI->HDCP_RxKsv, 0, BHDM_HDCP_KSV_LENGTH) ;
1007        hHDMI->RxBCaps = 0 ;
1008
1009        /* make sure video is flowing from BVN before starting */
1010        BHDM_CHECK_RC(rc, BHDM_HDCP_P_CheckForValidVideo(       hHDMI)) ;
1011
1012        Register = BREG_Read32(hRegister, BCHP_HDMI_SCHEDULER_CONTROL) ;
1013        Register &= ~BCHP_MASK(HDMI_SCHEDULER_CONTROL, ALWAYS_VERT_KEEP_OUT) ;
1014
1015        Register |= BCHP_FIELD_DATA(HDMI_SCHEDULER_CONTROL, ALWAYS_VERT_KEEP_OUT, 1) ;
1016        BREG_Write32(hRegister, BCHP_HDMI_SCHEDULER_CONTROL, Register) ;
1017       
1018        hHDMI->bHdcpAnRequest = true ;
1019        do
1020        {
1021                /* set up for Test An values if requested */
1022                if (AnSelection != BHDM_HDCP_AnSelect_eRandomAn) 
1023                {
1024                        /* for HDCP Test An values, make sure the influence bits are off */
1025                        Register = BREG_Read32(hRegister, BCHP_HDMI_CP_CONFIG) ;
1026                        Register &= ~BCHP_MASK(HDMI_CP_CONFIG, AN_INFLUENCE_MODE) ;
1027                        Register |= BCHP_FIELD_DATA(HDMI_CP_CONFIG, AN_INFLUENCE_MODE, 0) ;
1028                        BREG_Write32(hRegister, BCHP_HDMI_CP_CONFIG, Register) ;
1029                       
1030                        /* Set An Selection and TestAn Enable */
1031                        Register = BREG_Read32(hRegister, BCHP_HDMI_CP_TST) ;
1032                        Register &= 
1033                                ~( BCHP_MASK(HDMI_CP_TST, I_TST_AN_SEL_1_0) 
1034                                 | BCHP_MASK(HDMI_CP_TST, I_TST_MODE_AN_ENABLE)) ;
1035                        Register |= 
1036                                  BCHP_FIELD_DATA(HDMI_CP_TST, I_TST_AN_SEL_1_0, AnSelection) 
1037                                | BCHP_FIELD_DATA(HDMI_CP_TST, I_TST_MODE_AN_ENABLE, 1) ;
1038                        BREG_Write32(hRegister, BCHP_HDMI_CP_TST, Register) ;
1039                }
1040
1041                /* Check for completion of the generated HDCP An Value */
1042                /* should complete within 1-2 frames */
1043                timeoutFrames = 6 ;
1044                do                       
1045                {
1046                        /* request the authentication values */
1047                        /* Set AUTH_REQUEST_BIT only - all other bits must be zero */
1048                        Register = BCHP_FIELD_DATA(HDMI_HDCP_CTL, I_AUTH_REQUEST, 1) ;
1049                        BREG_Write32(hRegister, BCHP_HDMI_HDCP_CTL, Register) ;
1050
1051                        /* HDCP An value *should* be generated after one frame;  */
1052                        /* Wait up to  3+ frames */
1053                        /* NOTE: Video flow from BVN to HDMI must be stable when generating An value */
1054                        BHDM_CHECK_RC(rc, BKNI_WaitForEvent(hHDMI->BHDM_EventHDCP, BHDM_HDCP_CONFIG_AN_TIMEOUT_MS)) ;
1055
1056                        Register = BREG_Read32(hRegister, BCHP_HDMI_CP_STATUS) ;
1057                        AnReady = BCHP_GET_FIELD_DATA(Register, HDMI_CP_STATUS, O_AN_READY) ;
1058                        if (AnReady)
1059                                break ;
1060       
1061                        BDBG_WRN(("Waitng for HDCP An Value")) ;
1062                } while ( timeoutFrames-- ) ;
1063       
1064                if (!AnReady)
1065                {
1066                        BDBG_ERR(("Timeout Error waiting for HDCP An Value")) ;
1067
1068                        /* check for valid video */
1069                        BHDM_CHECK_RC(rc, BHDM_HDCP_P_CheckForValidVideo(hHDMI)) ;
1070                       
1071                        rc = BERR_TIMEOUT ;
1072                        goto done ;
1073                }
1074               
1075
1076                /* read the generated HDCP An value / write to the HDCP Rx */
1077                AnMsb = BREG_Read32(hRegister, BCHP_HDMI_AN1) ; /* 32 MSB */
1078                AnLsb = BREG_Read32(hRegister, BCHP_HDMI_AN0) ; /* 32 LSB */
1079               
1080                /* copy the AnValue to a uint8_t string for single I2C write to the Rx */
1081                AnValue[0] =  AnLsb        & 0xFF ;
1082                AnValue[1] = (AnLsb >>  8) & 0xFF ; 
1083                AnValue[2] = (AnLsb >> 16) & 0xFF ; 
1084                AnValue[3] = (AnLsb >> 24) & 0xFF ; 
1085               
1086                AnValue[4] =  AnMsb        & 0xFF ;
1087                AnValue[5] = (AnMsb >>  8) & 0xFF ; 
1088                AnValue[6] = (AnMsb >> 16) & 0xFF ; 
1089                AnValue[7] = (AnMsb >> 24) & 0xFF ; 
1090               
1091                /* verify the generated An value is not one of the test values if we are generating random numbers */
1092                if (AnSelection == BHDM_HDCP_AnSelect_eRandomAn)  /* for Test An Values */
1093                {
1094                        for (i = 0 ; i < NUM_TEST_AN_VALUES ; i++)
1095                        {
1096#if 0                           
1097                                BDBG_MSG(("Compare generated RandomAn to TestAn %02x%02x%02x%02x%02x%02x%02x%02x ",
1098                                        ucHdcpSpecTestAnValues[i][7], ucHdcpSpecTestAnValues[i][6],     
1099                                        ucHdcpSpecTestAnValues[i][5], ucHdcpSpecTestAnValues[i][4],     
1100                                        ucHdcpSpecTestAnValues[i][3], ucHdcpSpecTestAnValues[i][2],     
1101                                        ucHdcpSpecTestAnValues[i][1], ucHdcpSpecTestAnValues[i][0])) ;
1102#endif
1103                                if (!BKNI_Memcmp(AnValue, ucHdcpSpecTestAnValues[i], BHDM_HDCP_AN_LENGTH))
1104                                {
1105                                        bTestAnGenerated = true ;
1106                                        break ;
1107                                }
1108                        }
1109                }
1110               
1111                BDBG_MSG(("AnValue = %02x%02x%02x%02x%02x%02x%02x%02x ", 
1112                        AnValue[7], AnValue[6], AnValue[5], AnValue[4], 
1113                        AnValue[3], AnValue[2], AnValue[1], AnValue[0])) ;
1114        } while ((AnSelection == BHDM_HDCP_AnSelect_eRandomAn) && (bTestAnGenerated)) ;
1115
1116
1117#if BHDM_CONFIG_HDCP_FORCE_ENC_SIGNAL
1118        /*
1119            For HDCP Compliance Test ...
1120            make sure the RDB Auth is set so at least the ENC_DIS signal is always sent
1121            when MUX_VSYNC is enabled after authentication, ENC_EN will be transmitted
1122          */
1123         
1124        /* Set SET_RDB_AUTHENTICATED_BIT only - all other bits must be zero */
1125        Register = BCHP_FIELD_DATA(HDMI_HDCP_CTL, I_SET_RDB_AUTHENTICATED, 1) ;
1126        BREG_Write32(hRegister, BCHP_HDMI_HDCP_CTL, Register) ; 
1127#endif 
1128
1129        /* write the generate An value to the Receiver */
1130        BHDM_CHECK_RC(rc, BREG_I2C_Write(hHDMI->hI2cRegHandle,
1131                        BHDM_HDCP_RX_I2C_ADDR,  BHDM_HDCP_RX_AN0, (uint8_t *) AnValue, BHDM_HDCP_AN_LENGTH)) ;
1132       
1133done:
1134        hHDMI->bHdcpAnRequest = false ; 
1135        BDBG_LEAVE(BHDM_HDCP_GenerateAn) ;
1136        return rc ;
1137} /* end BHDM_HDCP_GenerateAn */
1138
1139
1140/******************************************************************************
1141BERR_Code BHDM_HDCP_WriteTxAksvToRx
1142Summary: Write the HDCP Aksv value to the receiver
1143*******************************************************************************/
1144BERR_Code BHDM_HDCP_WriteTxAksvToRx(
1145   BHDM_Handle hHDMI,           /* [in] HDMI handle */
1146   const uint8_t *pTxAksv       /* [in] pointer HDCP Key Set Aksv Value */
1147) 
1148{
1149        static uint8_t HdcpSpecTestSet1Aksv[BHDM_HDCP_KSV_LENGTH] =
1150                {0x14, 0xF7, 0x61, 0x03, 0xB7} ;
1151
1152        BERR_Code   rc = BERR_SUCCESS;
1153        uint8_t RxCaps;
1154        uint8_t AinfoByte;
1155   
1156        BDBG_ENTER(BHDM_HDCP_WriteTxAksvToRx) ;
1157
1158        /* Verify TxAksv has 20 zeros & 20 ones */
1159       
1160        /* display KSV for debugging */
1161        BDBG_MSG(("TxAksv = %02x %02x %02x %02x %02x", 
1162                        pTxAksv[4], pTxAksv[3], pTxAksv[2], pTxAksv[1], pTxAksv[0]));
1163
1164        /* check for valid KSV */
1165        if (BHDM_HDCP_P_NumberOfSetBits((uint8_t *) pTxAksv, BHDM_HDCP_KSV_LENGTH) != 20) 
1166        {
1167                BDBG_ERR(("Valid TxAksv contain 20 1s and 20 0s")) ;
1168                rc = BHDM_HDCP_TX_AKSV_ERROR ;
1169                goto done ;
1170        }
1171
1172        /* make sure KSV is not from the Test Key Set*/ 
1173        if (!BKNI_Memcmp(HdcpSpecTestSet1Aksv, pTxAksv, BHDM_HDCP_KSV_LENGTH))
1174        {
1175                BDBG_WRN(("\n\n\n")) ;
1176                BDBG_WRN(("******************************")) ;
1177                BDBG_WRN(("TxAksv = %02x %02x %02x %02x %02x", 
1178                                pTxAksv[4], pTxAksv[3], pTxAksv[2], pTxAksv[1], pTxAksv[0]));
1179                BDBG_WRN(("TkAksv is part of the HDCP Spec Test Key Set")) ;
1180                BDBG_WRN(("Production Key Set required for use with a Production Receiver")) ;
1181                BDBG_WRN(("******************************")) ;
1182                rc = BHDM_HDCP_TX_AKSV_ERROR ;
1183                goto done ;
1184        }
1185
1186       
1187        /* Write the AInfo value */
1188        BHDM_CHECK_RC(rc, BHDM_HDCP_GetRxCaps(hHDMI, &RxCaps)) ;
1189       
1190    if ((RxCaps & BHDM_HDCP_RxCaps_eHDCP_1_1_Features) 
1191        && (hHDMI->HdcpOptions.PjChecking)
1192        && (hHDMI->HdcpOptions.numPjFailures <= BHDM_HDCP_MAX_PJ_LINK_FAILURES_BEFORE_DISABLE_HDCP_1_1))   
1193        {
1194                AinfoByte = BHDM_HDCP_RX_ENABLE_1_1_FEATURES ;
1195
1196#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
1197                if (!hHDMI->bAutoRiPjCheckingEnabled) {
1198                        BHDM_CHECK_RC(rc, BREG_I2C_Write(hHDMI->hI2cRegHandle,
1199                                BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_AINFO, (uint8_t *) &AinfoByte, 1)) ;
1200                }
1201#else
1202                BHDM_CHECK_RC(rc, BREG_I2C_Write(hHDMI->hI2cRegHandle,
1203                        BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_AINFO, (uint8_t *) &AinfoByte, 1)) ;
1204#endif
1205
1206        }   
1207
1208        /* Write the TxAksv value to the HDCP Rx */
1209        rc = BREG_I2C_Write(hHDMI->hI2cRegHandle, BHDM_HDCP_RX_I2C_ADDR, 
1210                BHDM_HDCP_RX_AKSV0, (uint8_t *) pTxAksv, BHDM_HDCP_KSV_LENGTH) ;
1211
1212        if (rc != BERR_SUCCESS)
1213        {
1214                BDBG_ERR(("Aksv I2C write error"));
1215                rc = BHDM_HDCP_TX_AKSV_I2C_WRITE_ERROR;
1216                goto done;
1217        }
1218
1219        /*
1220        consider the authentication request started once the TxAksv
1221        is written to the Rx; clear the authenticated link bit
1222        */
1223        hHDMI->AbortHdcpAuthRequest = 0 ;
1224       
1225        /* clear AuthenticatedLink Variable */
1226        hHDMI->HDCP_AuthenticatedLink = 0 ;
1227       
1228
1229done : 
1230        BDBG_LEAVE(BHDM_HDCP_WriteTxAksvToRx) ;
1231        return rc ;
1232}
1233
1234
1235/******************************************************************************
1236BERR_Code BHDM_HDCP_EnableSerialKeyLoad(
1237Summary: Enable HDMI transmitter core to receive the HDCP Keys serially.
1238*******************************************************************************/
1239BERR_Code BHDM_HDCP_EnableSerialKeyLoad(
1240   BHDM_Handle hHDMI              /* [in] HDMI handle */
1241)
1242{
1243        BERR_Code   rc = BERR_SUCCESS;
1244        uint32_t    Register ;
1245
1246        BDBG_ENTER(BHDM_HDCP_EnableSerialKeyLoad) ;
1247
1248        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG) ;
1249        Register &= ~BCHP_MASK(HDMI_CP_CONFIG, I_ENABLE_RDB_KEY_LOAD) ;
1250        Register |= BCHP_FIELD_DATA(HDMI_CP_CONFIG, I_ENABLE_RDB_KEY_LOAD, 0x0) ;
1251        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG, Register) ;
1252
1253
1254        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG) ;
1255        Register &= ~BCHP_MASK(HDMI_CP_CONFIG, I_KEY_BASE_ADDRESS_9_0) ;
1256        Register |= BCHP_FIELD_DATA(HDMI_CP_CONFIG, I_KEY_BASE_ADDRESS_9_0, 0x80) ;
1257        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG, Register) ;
1258               
1259        hHDMI->AbortHdcpAuthRequest = 0 ;       
1260       
1261        BDBG_LEAVE(BHDM_HDCP_EnableSerialKeyLoad) ;
1262        return rc ;
1263}
1264
1265
1266
1267
1268/******************************************************************************
1269BERR_Code BHDM_HDCP_AuthenticateLink
1270Summary: Authenticate the HDCP Link; verify TxR0 and RxR0 values are equal
1271*******************************************************************************/
1272BERR_Code BHDM_HDCP_AuthenticateLink
1273(
1274        BHDM_Handle hHDMI              /* [in] HDMI handle */
1275)
1276{
1277        BERR_Code   rc = BERR_SUCCESS;
1278        uint32_t    Register ;
1279        uint8_t     timeoutMs ;
1280
1281        uint8_t
1282                RdbAuthenticated ,
1283                SchedulerAuthenticated,
1284                CoreAuthenticated ;
1285
1286
1287        /* Before checking Authentication... */
1288        /* Reset Ri counter and previous Ri Values */
1289        hHDMI->HDCP_RiCount = 0 ;
1290
1291        hHDMI->HDCP_Ri2SecsAgo = 0x01 ;
1292        hHDMI->HDCP_Ri4SecsAgo = 0x01 ;
1293        hHDMI->HDCP_Ri6SecsAgo = 0x01 ;
1294
1295        hHDMI->HDCP_AuthenticatedLink = 0 ;
1296
1297#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
1298        hHDMI->bAutoRiPjCheckingEnabled = false;
1299#endif
1300
1301        if ((rc = BHDM_HDCP_RiLinkIntegrityCheck(hHDMI)) != BERR_SUCCESS) 
1302        {
1303                BDBG_ERR(("HDCP Authentication Failed"));
1304                goto done ;
1305        }
1306
1307
1308        /* SET_RDB_AUTHENTICATED must be asserted to ensure ENC_EN/ENC_DIS
1309        signal is sent either via MUX_VSYNC or by the HW */
1310       
1311        /* Set SET_RDB_AUTHENTICATED_BIT only - all other bits must be zero */
1312        Register = BCHP_FIELD_DATA(HDMI_HDCP_CTL, I_SET_RDB_AUTHENTICATED, 1) ;
1313        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_HDCP_CTL, Register) ;
1314
1315
1316        /* wait up to 50ms for the core to authenticate; should authenticate within 1 field */
1317        timeoutMs = 5 ;
1318        do                       
1319        {
1320                /* make sure HDCP request is still active... hotplug will abort request  */
1321                if (hHDMI->AbortHdcpAuthRequest)
1322                {
1323                        BDBG_WRN(("HDCP Authentication Request Aborted....")) ;
1324                        rc = BHDM_HDCP_AUTH_ABORTED ;
1325                        goto done ;
1326                }
1327               
1328                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_STATUS) ;
1329
1330                RdbAuthenticated = BCHP_GET_FIELD_DATA(Register, HDMI_CP_STATUS, RDB_AUTHENTICATED) ;
1331                SchedulerAuthenticated = BCHP_GET_FIELD_DATA(Register, HDMI_CP_STATUS, AUTHENTICATED_OK) ;
1332                CoreAuthenticated = BCHP_GET_FIELD_DATA(Register, HDMI_CP_STATUS, CORE_AUTHENTICATED) ;
1333
1334                if (RdbAuthenticated
1335                &&  SchedulerAuthenticated
1336                &&  CoreAuthenticated)
1337                        break ;
1338                       
1339                BDBG_WRN(("Waiting for TxCore to Authenticate %d %d %d",
1340                        RdbAuthenticated, SchedulerAuthenticated, CoreAuthenticated)) ;
1341
1342                BKNI_Sleep(10) ;
1343        } while ( timeoutMs-- ) ;
1344
1345        if (!RdbAuthenticated)
1346        {
1347                BDBG_WRN(("HDCP Tx RDB not authenticated")) ;
1348                rc = BHDM_HDCP_AUTHENTICATE_ERROR ;
1349                goto done ;
1350        }
1351        else if (!SchedulerAuthenticated)
1352        {
1353                BDBG_WRN(("HDCP Tx Scheduler not authenticated")) ;
1354                rc = BHDM_HDCP_AUTHENTICATE_ERROR ;
1355                goto done ;
1356        }
1357        else if (!CoreAuthenticated)
1358        {
1359                BDBG_WRN(("HDCP Tx Core not authenticated")) ;
1360                rc = BHDM_HDCP_AUTHENTICATE_ERROR ;
1361                goto done ;
1362        }
1363
1364
1365        hHDMI->HDCP_AuthenticatedLink = 1 ;
1366        BDBG_MSG(("Receiver AUTHENTICATED")) ;
1367       
1368
1369        /* Reset the Ri values again so when Video transmission begins */
1370        /* HDCP doesn't think Ri is not advancing */
1371        hHDMI->HDCP_Ri2SecsAgo = 0x0102 ;
1372        hHDMI->HDCP_Ri4SecsAgo = 0x0203 ;
1373        hHDMI->HDCP_Ri6SecsAgo = 0x0304 ;
1374
1375#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
1376        if (hHDMI->DeviceSettings.bEnableAutoRiPjChecking)
1377        {
1378                /* Configure/setup auto Ri */
1379                BHDM_HDCP_P_ConfigureAutoRi(hHDMI);
1380
1381                /* Configure/setup auto Pj */
1382                if (hHDMI->HdcpOptions.PjChecking)
1383                        BHDM_HDCP_P_ConfigureAutoPj(hHDMI);
1384
1385                /* Cache RxBCaps and RxKSV before we switch over to auto HW checking. */
1386                BHDM_CHECK_RC(rc, BHDM_HDCP_GetRxCaps(hHDMI, &hHDMI->RxBCaps)) ;
1387                BHDM_CHECK_RC(rc, BHDM_HDCP_GetRxKsv(hHDMI, &hHDMI->HDCP_RxKsv[0])) ; 
1388
1389                /* If non-repeater, switch over from software to auto HW checking now. */
1390                if ((hHDMI->RxBCaps & BHDM_HDCP_RxCaps_eHdcpRepeater) == 0)
1391                {
1392                        BHDM_HDCP_P_EnableAutoRiPjChecking(hHDMI, hHDMI->HdcpOptions.PjChecking) ;
1393                }
1394        }
1395#endif
1396
1397done:   
1398        return rc ;
1399} /* end BHDM_HDCP_AuthenticateLink */
1400
1401
1402
1403
1404/******************************************************************************
1405BERR_Code BHDM_HDCP_ClearAuthentication(
1406Summary: Clear the Authenticated link between the Transmitter and the Receiver.
1407*******************************************************************************/
1408BERR_Code BHDM_HDCP_ClearAuthentication(
1409   BHDM_Handle hHDMI              /* [in] HDMI handle */
1410) 
1411{
1412        BERR_Code   rc = BERR_SUCCESS;
1413        uint32_t    Register ;
1414
1415        BDBG_ENTER(BHDM_HDCP_ClearAuthentication) ;
1416        BDBG_ASSERT( hHDMI );
1417
1418        /* Clear the MuxVsync Bit First (eliminate momentary snow at the Rx) */
1419        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG) ;
1420        Register &= ~BCHP_MASK(HDMI_CP_CONFIG, I_MUX_VSYNC) ;
1421        Register |= BCHP_FIELD_DATA(HDMI_CP_CONFIG, I_MUX_VSYNC, 0) ;
1422        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG, Register) ;
1423
1424        /* Wait long enough for the current frame to complete... */
1425        BKNI_Sleep(20) ;  /* wait */
1426                       
1427
1428#if BHDM_CONFIG_HDCP_FORCE_ENC_SIGNAL
1429        /*
1430        Clearing the I_CLEAR_RDB_AUTHENTICATED_BIT has been removed to fix HDCP
1431        Compliance Test Issue... the CLEAR_RDB_AUTHENTICATED should never asserted
1432       
1433        The Compliance Test checks to make sure either ENC_DIS or ENC_EN
1434        is always transmitted.  Setting  the core as always authenticated will
1435        allow the MUX_VSYNC to control the ENC_DIS/ENC_EN signal
1436        */
1437
1438#else
1439        /* Set the Tx Authentication Cleared Bit */
1440
1441        /* Set CLEAR_RDB_AUTHENTICATED BIT only - all other bits must be zero */
1442        Register = BCHP_FIELD_DATA(HDMI_HDCP_CTL, I_CLEAR_RDB_AUTHENTICATED, 1) ;
1443        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_HDCP_CTL, Register) ;
1444       
1445        Register = BCHP_FIELD_DATA(HDMI_HDCP_CTL, I_CLEAR_RDB_AUTHENTICATED, 0) ;
1446        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_HDCP_CTL, Register) ;
1447       
1448#endif                 
1449
1450#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
1451        BHDM_HDCP_P_DisableAutoRiPjChecking (hHDMI);
1452#endif
1453        /* clear AuthenticatedLink Variable */
1454        hHDMI->HDCP_AuthenticatedLink = 0 ;
1455       
1456        /* Reset Ri counter */
1457        hHDMI->HDCP_RiCount = 0 ;
1458
1459        BDBG_LEAVE(BHDM_HDCP_ClearAuthentication) ;
1460        return rc ;
1461       
1462} /* end BHDM_HDCP_ClearAuthentication */
1463
1464
1465
1466
1467/******************************************************************************
1468BERR_Code BHDM_HDCP_XmitEncrypted
1469Summary:Start transmitting video encrypted with HDCP.
1470*******************************************************************************/
1471BERR_Code BHDM_HDCP_XmitEncrypted(
1472   BHDM_Handle hHDMI              /* [in] HDMI handle */
1473) 
1474{
1475        BERR_Code   rc = BERR_SUCCESS;
1476        uint32_t    Register ;
1477        uint16_t JRate ;
1478
1479        BDBG_ENTER(BHDM_HDCP_XmitEncrypted) ;
1480        BDBG_ASSERT( hHDMI );
1481
1482        if ((hHDMI->HdcpVersion == BHDM_HDCP_Version_e1_1) /* same as hHDMI->HdcpVersion == BHDM_HDCP_Version_e1_0*/ 
1483        ||      (hHDMI->HdcpVersion == BHDM_HDCP_Version_eUnused))
1484        {
1485                BDBG_MSG(("Using HDCP 1.1 Features")) ;
1486               
1487                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CFG) ;
1488                Register &= ~BCHP_MASK(HDMI_CP_INTEGRITY_CFG, I_ALWAYS_REKEY_ON_VSYNC) ;
1489                BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CFG, Register) ;
1490        }
1491        else                                                                           
1492        {
1493                BDBG_MSG(("Using HDCP 1.1 with Optional Features")) ;
1494               
1495                /* enable ReKey on Vsync for HDCP 1.1 Receivers */ 
1496                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CFG) ;
1497                JRate = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY_CFG, J_RATE_7_0) ;
1498                BDBG_MSG(("Pj Rate: %d frames", JRate)) ;
1499
1500                Register &= ~BCHP_MASK(HDMI_CP_INTEGRITY_CFG, I_ALWAYS_REKEY_ON_VSYNC) ;
1501                Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CFG, I_ALWAYS_REKEY_ON_VSYNC, 1) ;
1502                BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CFG, Register) ;
1503        }
1504
1505
1506        /* enable (toggle) the Vsync for encryption */
1507        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG) ;
1508        Register &= ~BCHP_MASK(HDMI_CP_CONFIG, I_MUX_VSYNC) ;
1509       
1510        Register |= BCHP_FIELD_DATA(HDMI_CP_CONFIG, I_MUX_VSYNC, 1) ;
1511        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG, Register) ;
1512
1513        BDBG_LEAVE(BHDM_HDCP_XmitEncrypted) ;
1514        return rc ;
1515} /* end BHDM_HDCP_XmitEncrypted */
1516
1517
1518
1519
1520/******************************************************************************
1521BERR_Code BHDM_HDCP_XmitClear
1522Summary: Start transmitting video without HDCP.
1523*******************************************************************************/
1524BERR_Code BHDM_HDCP_XmitClear(
1525   BHDM_Handle hHDMI              /* [in] HDMI handle */
1526)
1527{
1528        BERR_Code   rc = BERR_SUCCESS;
1529        uint32_t    Register ;
1530
1531        BDBG_ENTER(BHDM_HDCP_XmitClear) ;
1532        BDBG_ASSERT( hHDMI );
1533
1534        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG) ;
1535        Register &= ~BCHP_MASK(HDMI_CP_CONFIG, I_MUX_VSYNC) ;
1536        Register |= BCHP_FIELD_DATA(HDMI_CP_CONFIG, I_MUX_VSYNC, 0) ;
1537        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_CONFIG, Register) ;
1538       
1539        BDBG_LEAVE(BHDM_HDCP_XmitClear) ;
1540        return rc ;
1541} /* end BHDM_HDCP_XmitClear */
1542
1543
1544#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
1545/******************************************************************************
1546BERR_Code BHDM_HDCP_P_AutoRiLinkIntegrityCheck
1547Summary: Use hardware Ri checking to verify the protected link is still valid.
1548*******************************************************************************/
1549BERR_Code BHDM_HDCP_P_AutoRiLinkIntegrityCheck(
1550   BHDM_Handle hHDMI              /* [in] HDMI handle */
1551) 
1552{
1553        BERR_Code       rc = BERR_SUCCESS;
1554
1555        uint32_t        Register ;
1556        uint16_t        Ri ;
1557#if BHDM_CONFIG_DEBUG_PJ_CHECKING       
1558        uint8_t  Pj ;
1559#endif
1560       
1561        BDBG_ENTER(BHDM_HDCP_P_AutoRiLinkIntegrityCheck) ;
1562        BDBG_ASSERT( hHDMI );
1563
1564        /* Request to abort authentication */
1565        if (hHDMI->AbortHdcpAuthRequest)
1566        {
1567                BDBG_WRN(("HDCP Authentication Request Aborted....")) ;
1568                rc = BHDM_HDCP_AUTH_ABORTED ;
1569                goto done ;
1570        }
1571
1572        /* Ri mismatch interrupt(s) fired. Either on the 127th frame (A) or the 0th frame (B) */
1573        if (hHDMI->HDCP_AutoRiMismatch_A || hHDMI->HDCP_AutoRiMismatch_B)
1574        {
1575                if (hHDMI->HDCP_AutoRiMismatch_A)
1576                {
1577                        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_STATUS_2) ;
1578                        Ri = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY_CHK_STATUS_2, O_RI_A_SOURCE) ;
1579                        BKNI_Memcpy(&hHDMI->HDCP_TxRi, &Ri, 2) ;
1580
1581                        Ri = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY_CHK_STATUS_2, O_RI_A_SINK) ;
1582                        BKNI_Memcpy(&hHDMI->HDCP_RxRi, &Ri, 2) ;                       
1583               
1584                        BDBG_WRN(("HDCP Ri Failure. Sink update Ri' too early"));
1585                        BDBG_WRN(("LIC: Frame 127th: TxRi= %04x <> RxRi= %04x             R%d !=",
1586                                hHDMI->HDCP_TxRi, hHDMI->HDCP_RxRi, hHDMI->HDCP_RiCount)) ;
1587                        hHDMI->HDCP_AutoRiMismatch_A = false;
1588                }
1589
1590                if (hHDMI->HDCP_AutoRiMismatch_B)
1591                {
1592                        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_STATUS_3) ;
1593                        Ri = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY_CHK_STATUS_3, O_RI_B_SOURCE) ;
1594                        BKNI_Memcpy(&hHDMI->HDCP_TxRi, &Ri, 2) ;
1595
1596                        Ri = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY_CHK_STATUS_3, O_RI_B_SINK) ;
1597                        BKNI_Memcpy(&hHDMI->HDCP_RxRi, &Ri, 2) ;                       
1598               
1599                        BDBG_WRN(("HDCP Ri Failure. Sink update Ri' too late"));
1600                        BDBG_WRN(("LIC: Frame 0th: TxRi= %04x <> RxRi= %04x             R%d !=",
1601                                hHDMI->HDCP_TxRi, hHDMI->HDCP_RxRi, hHDMI->HDCP_RiCount)) ;
1602                        hHDMI->HDCP_AutoRiMismatch_B = false;
1603                }                       
1604
1605                /* Clear/Disable the HDCP Authentication */
1606                BHDM_HDCP_ClearAuthentication(hHDMI) ;
1607                                       
1608                rc = BHDM_HDCP_LINK_RI_FAILURE ;
1609                goto done;
1610        }
1611
1612        /* No Ri mismatch interrupt was fired. Update Ri values */
1613        else
1614        {
1615                /* Read TxRi at the 0th frame. This is the start of the next 128 frames period, thus the updated Ri value */
1616                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY) ;
1617                Ri = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY, O_RI_15_0) ;
1618
1619                BKNI_Memcpy(&hHDMI->HDCP_TxRi, &Ri, 2) ;
1620
1621                if (! BKNI_Memcmp(&hHDMI->HDCP_TxRi, &hHDMI->HDCP_Ri2SecsAgo, 2))       /* No Ri change from 2secs ago */
1622                {
1623                        /*
1624                        ** The TxRi has not changed, so there is no need to read the RxRi.
1625                        ** just verify the TxRi value has changed in the last 6 seconds
1626                        */
1627
1628                        if (BKNI_Memcmp(&hHDMI->HDCP_TxRi, &hHDMI->HDCP_Ri4SecsAgo, 2)) /* Ri changed from 4secs ago */
1629                        {
1630                                BKNI_Memcpy(&hHDMI->HDCP_Ri4SecsAgo, &hHDMI->HDCP_Ri2SecsAgo, 2) ;
1631                                rc = BERR_SUCCESS ;
1632                                goto done ;
1633                        }
1634
1635                        if (BKNI_Memcmp(&hHDMI->HDCP_TxRi, &hHDMI->HDCP_Ri6SecsAgo, 2)) /* Ri changed from 6secs ago */
1636                        {
1637                                BKNI_Memcpy(&hHDMI->HDCP_Ri6SecsAgo, &hHDMI->HDCP_Ri4SecsAgo, 2) ;
1638                                rc = BERR_SUCCESS ;
1639                                goto done ;
1640                        }         
1641
1642                        /*
1643                        ** Ri hasn't changed for six seconds
1644                        ** Clear the Authentication and return a LINK FAILURE
1645                        */
1646                        BDBG_WRN(("Ri HDCP Link Integrity (Ri) values are not changing")) ;
1647                        BDBG_WRN(("HDCP Link will shutdown")) ;
1648
1649                        /* Clear/Disable the HDCP Authentication */
1650                        BHDM_HDCP_ClearAuthentication(hHDMI) ;
1651
1652                        rc = BHDM_HDCP_LINK_RI_FAILURE  ; 
1653                        goto done ;
1654                }
1655
1656
1657                if      ((hHDMI->HDCP_TxRi == hHDMI->HDCP_Ri2SecsAgo)  /* No Ri change in 2secs */ 
1658                && (hHDMI->HDCP_TxRi == hHDMI->HDCP_Ri4SecsAgo)  /* No Ri change in 4secs */
1659                && (hHDMI->HDCP_TxRi == hHDMI->HDCP_Ri6SecsAgo)) /* No Ri change in 6secs */
1660                {
1661                        /*
1662                        ** if Ri has not changed in 6 seconds  (3 Consecutive Ri reads)
1663                        ** the HDCP link is no longer valid
1664                        */
1665                        rc = BHDM_HDCP_LINK_RI_FAILURE  ; 
1666                        goto done ;
1667                }
1668
1669                /* Print the Ri value at the last frame of the previous 128 frames period for debug information */
1670                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_STATUS_2) ;
1671                Ri = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY_CHK_STATUS_2, O_RI_A_SOURCE) ; 
1672
1673                BDBG_MSG(("LIC: At 127th frame:  Tx/Rx Ri= %04x                 R%d",                           
1674                        Ri, hHDMI->HDCP_RiCount-1)) ;           
1675                BDBG_MSG(("LIC: At 0th frame:  Tx/Rx Ri= %04x                   R%d",                           
1676                        hHDMI->HDCP_TxRi, hHDMI->HDCP_RiCount)) ;
1677
1678#if BHDM_CONFIG_DEBUG_PJ_CHECKING
1679                /* Pj values at  Ri updates should equal the LSB of the Ri value */
1680                /* Note the video pixel must be zero for this test */
1681                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY) ;
1682                Pj = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY, O_PJ_7_0) ;
1683
1684                BDBG_MSG(("                       %04x", Pj)) ;
1685#endif
1686                /*      increment  the RiCount only if Ri Changed in the last 2 secs */
1687                if (hHDMI->HDCP_TxRi != hHDMI->HDCP_Ri2SecsAgo)   
1688                        hHDMI->HDCP_RiCount++ ;
1689
1690                /*
1691                ** RiNSecsAgo values are initialized 
1692                ** in BHDM_HDCP_AuthenticateLink
1693                */
1694                hHDMI->HDCP_Ri6SecsAgo = hHDMI->HDCP_Ri4SecsAgo ;
1695                hHDMI->HDCP_Ri4SecsAgo = hHDMI->HDCP_Ri2SecsAgo ;
1696                hHDMI->HDCP_Ri2SecsAgo = hHDMI->HDCP_TxRi ;
1697
1698                /* Return Link is Valid */
1699                rc = BERR_SUCCESS ;
1700                goto done ;
1701
1702        }
1703
1704done:   
1705        BDBG_LEAVE(BHDM_HDCP_P_AutoRiLinkIntegrityCheck) ;
1706        return rc ;
1707
1708}
1709
1710
1711/******************************************************************************
1712BERR_Code BHDM_HDCP_P_AutoPjLinkIntegrityCheck
1713Summary: Use hardware Pj checking to verify the protected link is still valid.
1714*******************************************************************************/
1715BERR_Code BHDM_HDCP_P_AutoPjLinkIntegrityCheck(
1716   BHDM_Handle hHDMI              /* [in] HDMI handle */
1717) 
1718{
1719        BERR_Code   rc = BERR_SUCCESS;
1720        uint32_t    Register ;
1721        uint8_t         Pj ;
1722       
1723        BDBG_ENTER(BHDM_HDCP_P_AutoPjLinkIntegrityCheck) ;
1724        BDBG_ASSERT( hHDMI );
1725
1726#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
1727
1728        /* Request to abort authentication */
1729        if (hHDMI->AbortHdcpAuthRequest)
1730        {
1731                BDBG_WRN(("HDCP Authentication Request Aborted....")) ;
1732                rc = BHDM_HDCP_AUTH_ABORTED ;
1733                goto done ;
1734        }
1735
1736        /* Read Tx Pj updated value */
1737        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_STATUS_1) ;
1738        Pj = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY_CHK_STATUS_1, O_PJ_SOURCE) ;
1739        BKNI_Memcpy(&hHDMI->HDCP_TxPj, &Pj, 1) ;
1740
1741        /* Pj values mismatched */
1742        if (hHDMI->HDCP_AutoPjMismatch)
1743        {
1744                Pj = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY_CHK_STATUS_1, O_PJ_SINK) ;
1745                BKNI_Memcpy(&hHDMI->HDCP_RxPj, &Pj, 1) ;
1746
1747                BDBG_WRN(("Pj LIC: TxPj= %02x <> RxPj= %02x !=",
1748                        hHDMI->HDCP_TxPj, hHDMI->HDCP_RxPj)) ;
1749
1750                /* could be a pixel transmission error; ignore if errs < MAX MisMatch */
1751                if (++hHDMI->HDCP_PjMismatchCount < BHDM_HDCP_MAX_PJ_MISMATCH)
1752                {
1753                        BDBG_WRN(("Pixel Transmission Error?? Pj Mis-match Count %d", 
1754                                hHDMI->HDCP_PjMismatchCount)) ;
1755                }
1756                else   /* otherwise fail the link */
1757                {
1758                        rc = BHDM_HDCP_LINK_PJ_FAILURE ;
1759                       
1760                        /* Clear/Disable the HDCP Authentication */
1761                        BHDM_HDCP_ClearAuthentication(hHDMI) ;
1762                        goto done;
1763                }       
1764        }
1765
1766       
1767        /* Pjs match... */
1768        BDBG_MSG(("Pj LIC: Tx/Rx Pj: %02x", Pj)) ;
1769        hHDMI->HDCP_PjMismatchCount = 0 ;
1770       
1771        /* Return Link is Valid */
1772        rc = BERR_SUCCESS ;;
1773       
1774#endif
1775               
1776done:
1777        BDBG_LEAVE(BHDM_HDCP_P_AutoPjLinkIntegrityCheck) ;
1778        return rc ;
1779
1780}
1781#endif
1782
1783/******************************************************************************
1784BERR_Code BHDM_HDCP_RiLinkIntegrityCheck
1785Summary: Use the HDCP Ri values to verify the protected link is still valid.
1786*******************************************************************************/
1787BERR_Code BHDM_HDCP_RiLinkIntegrityCheck(
1788   BHDM_Handle hHDMI              /* [in] HDMI handle */
1789) 
1790{
1791        BERR_Code   rc = BERR_SUCCESS;
1792
1793        uint32_t    Register ;
1794        uint16_t    Ri ;
1795#if BHDM_CONFIG_DEBUG_PJ_CHECKING       
1796        uint8_t  Pj ;
1797#endif
1798        uint8_t RetryCount = 0;
1799       
1800        BDBG_ENTER(BHDM_HDCP_RiLinkIntegrityCheck) ;
1801        BDBG_ASSERT( hHDMI );
1802
1803#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
1804        /* Enable auto Ri checking */
1805        if (hHDMI->DeviceSettings.bEnableAutoRiPjChecking && hHDMI->bAutoRiPjCheckingEnabled)
1806        {
1807                rc = BHDM_HDCP_P_AutoRiLinkIntegrityCheck(hHDMI);
1808                goto done;
1809        }
1810#endif
1811
1812#if 0
1813        /* TE for SimplayHD Test 7-11 appears to get confused if we attempt to read R0
1814         * more than once. So don't retry if this LIC is for R0.
1815         *
1816         * Discovered that the new Quantum Data PS-980 has an internal problem with the
1817         * 1st (short-form) access to R0 but the 2nd attempt works fine. This is a
1818         * good thing to have in general, anyway.
1819         */
1820         
1821        if (hHDMI->HDCP_RiCount == 0)
1822                        RetryCount = BHDM_HDCP_MAX_I2C_RETRY;
1823#endif
1824
1825        /* No Auto Ri/Pj checking is disabled or not supported */
1826        do
1827        {
1828                RetryCount++;
1829               
1830                if (hHDMI->AbortHdcpAuthRequest)
1831                {
1832                        BDBG_WRN(("HDCP Authentication Request Aborted....")) ;
1833                        rc = BHDM_HDCP_AUTH_ABORTED ;
1834                        goto done ;
1835                }
1836
1837                /* Read the Tx Ri value contained in the upper 16 bits of the Register */
1838                /* also get the Pj value */
1839                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY) ;
1840                Ri = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY, O_RI_15_0) ;
1841
1842               
1843                BKNI_Memcpy(&hHDMI->HDCP_TxRi, &Ri, 2) ;
1844
1845                if (! BKNI_Memcmp(&hHDMI->HDCP_TxRi, &hHDMI->HDCP_Ri2SecsAgo, 2))   /* No Ri change from 2secs ago */
1846                {
1847                        /*
1848                        ** The TxRi has not changed, so there is no need to read the RxRi.
1849                        ** just verify the TxRi value has changed in the last 6 seconds
1850                        */
1851
1852                        if (BKNI_Memcmp(&hHDMI->HDCP_TxRi, &hHDMI->HDCP_Ri4SecsAgo, 2)) /* Ri changed from 4secs ago */
1853                        {
1854                                BKNI_Memcpy(&hHDMI->HDCP_Ri4SecsAgo, &hHDMI->HDCP_Ri2SecsAgo, 2) ;
1855                                rc = BERR_SUCCESS ;
1856                                goto done ;
1857                        }
1858
1859                        if (BKNI_Memcmp(&hHDMI->HDCP_TxRi, &hHDMI->HDCP_Ri6SecsAgo, 2)) /* Ri changed from 6secs ago */
1860                        {
1861                                BKNI_Memcpy(&hHDMI->HDCP_Ri6SecsAgo, &hHDMI->HDCP_Ri4SecsAgo, 2) ;
1862                                rc = BERR_SUCCESS ;
1863                                goto done ;
1864                        }         
1865
1866                        /*
1867                        ** Ri hasn't changed for six seconds
1868                        ** Clear the Authentication and return a LINK FAILURE
1869                        */
1870                        BDBG_WRN(("Ri HDCP Link Integrity (Ri) values are not changing")) ;
1871                        BDBG_WRN(("HDCP Link will shutdown")) ;
1872
1873                        /* Clear/Disable the HDCP Authentication */
1874                        BHDM_HDCP_ClearAuthentication(hHDMI) ;
1875
1876                        rc = BHDM_HDCP_LINK_RI_FAILURE  ; 
1877                        goto done ;
1878                }
1879
1880#if BHDM_CONFIG_REPEATER_SIMULATION_TEST
1881                hHDMI->HDCP_RxRi = hHDMI->HDCP_TxRi ;
1882                BDBG_MSG(("LIC: Tx/Rx Ri= %04x  %8d",
1883                        hHDMI->HDCP_TxRi, hHDMI->HDCP_RiCount++)) ;
1884                return BERR_SUCCESS ;
1885#endif
1886
1887
1888/*
1889** All HDCP Rx are required to support Short or Fast Read Configuration
1890** where a read without an offset indicates the default I2C offset of the
1891** device should be used.   In the case of the HDCP Rx this is offset
1892** 0x08 (Ri).  Some early DVI receivers did not properly implement the
1893** Short Read resulting in Authentication errors
1894**
1895** Enable the following macro in bhdm_config.h to enable the HDCP Ri Short Read
1896** and eliminate compliance test reports of long Ri reads.
1897*/
1898#if BHDM_CONFIG_HDCP_RI_SHORT_READ
1899                rc = BREG_I2C_ReadNoAddr(hHDMI->hI2cRegHandle, 
1900                                BHDM_HDCP_RX_I2C_ADDR, (uint8_t *) &hHDMI->HDCP_RxRi, 2) ;
1901#else
1902                rc = BREG_I2C_Read(hHDMI->hI2cRegHandle, 
1903                                BHDM_HDCP_RX_I2C_ADDR,  BHDM_HDCP_RX_RI0, (uint8_t *) &hHDMI->HDCP_RxRi, 2) ;
1904#endif
1905
1906                if (rc != BERR_SUCCESS)
1907                {
1908                        BDBG_ERR(("Ri LIC: RxRi I2C read failure %x", rc)) ;
1909                        continue ;
1910                }
1911               
1912                /* little endian number */             
1913                BREG_LE16(hHDMI->HDCP_RxRi) ;
1914
1915
1916                /* if RIs match... */
1917                if  (hHDMI->HDCP_TxRi == hHDMI->HDCP_RxRi)
1918                {
1919                        /* make sure the Ri values are changing...*/
1920                       
1921                        if  ((hHDMI->HDCP_TxRi == hHDMI->HDCP_Ri2SecsAgo)  /* No Ri change in 2secs */ 
1922                        && (hHDMI->HDCP_TxRi == hHDMI->HDCP_Ri4SecsAgo)  /* No Ri change in 4secs */
1923                        && (hHDMI->HDCP_TxRi == hHDMI->HDCP_Ri6SecsAgo)) /* No Ri change in 6secs */
1924                        {
1925                                /*
1926                                ** if Ri has not changed in 6 seconds  (3 Consecutive Ri reads)
1927                                ** the HDCP link is no longer valid
1928                                */
1929                                rc = BHDM_HDCP_LINK_RI_FAILURE  ; 
1930                                goto done ;
1931                        }
1932
1933                        BDBG_MSG(("LIC: Tx/Rx Ri= %04x          R%d",
1934                                hHDMI->HDCP_TxRi, hHDMI->HDCP_RiCount)) ;
1935
1936                       
1937#if BHDM_CONFIG_DEBUG_PJ_CHECKING       
1938                        /* read the Integrity register a 2nd time to ensure Pj value has updated */
1939                        /* Pj values at  Ri updates should equal the LSB of the Ri value */
1940                        /* Note the video pixel must be zero for this test */
1941                        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY) ;
1942                        Pj = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY, O_PJ_7_0) ;
1943               
1944                        BDBG_MSG(("               %04x", Pj)) ;
1945#endif
1946                        /*  increment  the RiCount only if Ri Changed in the last 2 secs */
1947                        if (hHDMI->HDCP_TxRi != hHDMI->HDCP_Ri2SecsAgo)   
1948                                hHDMI->HDCP_RiCount++ ;
1949                       
1950                        /*
1951                        ** RiNSecsAgo values are initialized 
1952                        ** in BHDM_HDCP_AuthenticateLink
1953                        */
1954                        hHDMI->HDCP_Ri6SecsAgo = hHDMI->HDCP_Ri4SecsAgo ;
1955                        hHDMI->HDCP_Ri4SecsAgo = hHDMI->HDCP_Ri2SecsAgo ;
1956                        hHDMI->HDCP_Ri2SecsAgo = hHDMI->HDCP_TxRi ;
1957                       
1958
1959                        /* Return Link is Valid */
1960                        rc = BERR_SUCCESS ;
1961                        goto done ;
1962                }
1963
1964                /* Ri values don't match; try reading again up to 4 times */
1965
1966                /*
1967                ** BDBG_MSG Display the different Ri Values read
1968                ** Add a pattern "!=" to the display message so differences can
1969                ** be easily found in any generated logs.
1970                **
1971                ** Most of the time this will be a transition from one Ri
1972                ** value to the next;
1973                ** the next Ris read should result in equal Ri values
1974                */
1975                BDBG_WRN(("LIC: TxRi= %04x <> RxRi= %04x         R%d !=",
1976                        hHDMI->HDCP_TxRi, hHDMI->HDCP_RxRi, hHDMI->HDCP_RiCount)) ;
1977
1978                rc = BHDM_HDCP_LINK_RI_FAILURE ;
1979        } while (RetryCount < BHDM_HDCP_MAX_I2C_RETRY) ;
1980
1981        /* Clear/Disable the HDCP Authentication */
1982        BHDM_HDCP_ClearAuthentication(hHDMI) ;
1983       
1984done:   
1985        BDBG_LEAVE(BHDM_HDCP_RiLinkIntegrityCheck) ;
1986        return rc ;
1987}
1988
1989
1990/******************************************************************************
1991BERR_Code BHDM_HDCP_PjLinkIntegrityCheck
1992Summary: Use the HDCP Ri values to verify the protected link is still valid.
1993*******************************************************************************/
1994BERR_Code BHDM_HDCP_PjLinkIntegrityCheck(
1995   BHDM_Handle hHDMI              /* [in] HDMI handle */
1996) 
1997{
1998        BERR_Code   rc = BERR_SUCCESS;
1999
2000        uint32_t    Register ;
2001        uint8_t         Pj ;
2002        uint8_t RetryCount = 0;
2003       
2004        BDBG_ENTER(BHDM_HDCP_PjLinkIntegrityCheck) ;
2005        BDBG_ASSERT( hHDMI );
2006
2007#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
2008        if (hHDMI->DeviceSettings.bEnableAutoRiPjChecking && hHDMI->bAutoRiPjCheckingEnabled)
2009        {
2010                rc = BHDM_HDCP_P_AutoPjLinkIntegrityCheck(hHDMI);
2011                goto done;
2012        }
2013#endif
2014
2015        do
2016        {
2017                RetryCount++;
2018
2019                /* Read the Tx Ri value contained in the upper 16 bits of the Register */
2020                /* also get the Pj value */
2021                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY) ;
2022                Pj = BCHP_GET_FIELD_DATA(Register, HDMI_CP_INTEGRITY, O_PJ_7_0) ;
2023
2024                /*
2025                ** There is no guarantee the connected Rx supports the HDCP I2C Short
2026                ** Read format, therefore use a standard I2C read for the Receiver
2027                */
2028                rc = BREG_I2C_Read(hHDMI->hI2cRegHandle, 
2029                                BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_PJ, (uint8_t *) &hHDMI->HDCP_RxPj, 1) ;
2030                if (rc != BERR_SUCCESS)
2031                {
2032                        BDBG_ERR(("Pj LIC: Rx Pj I2C read failure %d", rc));
2033                        continue  ;
2034                }
2035
2036                /* Pjs match... */
2037                if  (hHDMI->HDCP_RxPj == Pj)
2038                {
2039                        BDBG_MSG(("Pj LIC: Tx/Rx Pj: %02x", Pj)) ;
2040                        hHDMI->HDCP_PjMismatchCount = 0 ;
2041                        hHDMI->HdcpOptions.numPjFailures = 0;
2042                       
2043                        /* Return Link is Valid */
2044                        rc = BERR_SUCCESS ;
2045                        goto done ;
2046                }
2047
2048
2049                /* Pj values don't match; try reading again up to MAX_I2C_RETRY times */
2050
2051                /*
2052                ** BDBG_MSG Display the different Pj Values read
2053                ** Add a pattern "!=" to the display message so differences can
2054                ** be easily found in any generated logs.
2055                **
2056                ** Most of the time this will be a transition from one Pj
2057                ** value to the next;
2058                ** the next Pjs read should result in equal Pj values
2059                */
2060                BDBG_WRN(("Pj LIC: TxPj= %02x <> RxPj= %02x %d !=",
2061                        Pj, hHDMI->HDCP_RxPj, RetryCount)) ;
2062        } while (RetryCount < BHDM_HDCP_MAX_I2C_RETRY) ;
2063
2064        /* could be a pixel transmission error; ignore if errs < MAX MisMatch */
2065        if (++hHDMI->HDCP_PjMismatchCount < BHDM_HDCP_MAX_PJ_MISMATCH)
2066        {
2067                BDBG_WRN(("Pixel Transmission Error?? Pj Mis-match Count %d", 
2068                        hHDMI->HDCP_PjMismatchCount)) ;
2069        }
2070        else   /* otherwise fail the link */
2071        {
2072                rc = BHDM_HDCP_LINK_PJ_FAILURE ;
2073                hHDMI->HdcpOptions.numPjFailures++;
2074                BDBG_MSG(("%d consecutive Pj link failures", hHDMI->HdcpOptions.numPjFailures));
2075
2076                /* Clear/Disable the HDCP Authentication */
2077                BHDM_HDCP_ClearAuthentication(hHDMI) ;
2078        }
2079
2080
2081done:
2082        BDBG_LEAVE(BHDM_HDCP_PjLinkIntegrityCheck) ;
2083        return rc ;
2084}
2085
2086
2087/******************************************************************************
2088BERR_Code BHDM_HDCP_GetRxCaps
2089Summary: Retrieve the Rx Capabilities.
2090*******************************************************************************/
2091BERR_Code BHDM_HDCP_GetRxCaps(
2092   BHDM_Handle hHDMI,         /* [in] HDMI handle */
2093   uint8_t *pRxCapsReg     /* [out] HDCP Rx Capability */
2094) 
2095{
2096        BERR_Code   rc = BERR_SUCCESS;
2097
2098        BDBG_ENTER(BHDM_HDCP_GetRxCaps) ;
2099        BDBG_ASSERT( hHDMI ) ;
2100
2101        /* if get RxCaps is being used to determine if the KSV FIFO is ready */
2102        /* return an HDCP Abort if a HP has occurred while waiting for KsvFifoRdy bit */
2103        if ((hHDMI->AbortHdcpAuthRequest) && (hHDMI->HDCP_AuthenticatedLink))
2104        {
2105                BDBG_WRN(("HDCP Authentication Request Aborted....")) ;
2106                rc = BHDM_HDCP_AUTH_ABORTED ;
2107                hHDMI->AbortHdcpAuthRequest = 0 ;
2108                goto done ;
2109        }
2110
2111#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
2112        /* We can't access I2C if control has been handed over to HW */
2113        if (hHDMI->bAutoRiPjCheckingEnabled)
2114        {
2115                *pRxCapsReg = hHDMI->RxBCaps;
2116        }
2117        else
2118        {       
2119                BHDM_CHECK_RC(rc, BREG_I2C_Read(hHDMI->hI2cRegHandle, 
2120                        BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_BCAPS, pRxCapsReg, 1)) ;
2121        }
2122#else
2123                BHDM_CHECK_RC(rc, BREG_I2C_Read(hHDMI->hI2cRegHandle, 
2124                        BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_BCAPS, pRxCapsReg, 1)) ;
2125#endif
2126
2127
2128#if 0
2129        /* debug to force Pj values */
2130        /* if Rx does not support Pj auth errors will occur */
2131        *pRxCapsReg     |= BHDM_HDCP_RxCaps_eHDCP_1_1_Features ;
2132#endif
2133
2134#if BHDM_CONFIG_REPEATER_SIMULATION_TEST
2135        *pRxCapsReg |=BHDM_HDCP_RxCaps_eHdcpRepeater ;
2136#endif 
2137
2138        /* update settings only if RxCaps has changed */
2139        if (hHDMI->RxBCaps == *pRxCapsReg)
2140                goto done ;
2141
2142#if BDBG_DEBUG_BUILD
2143        if ( *pRxCapsReg & BHDM_HDCP_RxCaps_eHdcpRepeater) {
2144                BDBG_MSG(("Repeater Bcaps (0x40): %#x", *pRxCapsReg)) ;
2145        } else {
2146                BDBG_MSG(("Receiver Bcaps (0x40): %#x", *pRxCapsReg)) ;
2147        }
2148#endif 
2149               
2150#if BHDM_CONFIG_DEBUG_HDCP_BCAPS
2151        BDBG_MSG(("-----------------------")) ;
2152        BDBG_MSG(("HDMI Rsvd(7):  %d", 
2153                *pRxCapsReg & BHDM_HDCP_RxCaps_eHdmiCapable ? 1 : 0)) ;
2154        BDBG_MSG(("Repeater(6):   %d", 
2155                *pRxCapsReg & BHDM_HDCP_RxCaps_eHdcpRepeater ? 1 : 0)) ;
2156        if (*pRxCapsReg & BHDM_HDCP_RxCaps_eHdcpRepeater)
2157                BDBG_MSG(("   KSV FIFO Rdy (5): %d", 
2158                        *pRxCapsReg & BHDM_HDCP_RxCaps_eKsvFifoReady ? 1 : 0)) ;
2159        BDBG_MSG(("Fast I2C(4):   %d", 
2160                *pRxCapsReg & BHDM_HDCP_RxCaps_eI2c400KhzSupport ? 1 : 0)) ;
2161        BDBG_MSG(("HDCP 1.1 with Optional Features(1):   %d", 
2162                *pRxCapsReg & BHDM_HDCP_RxCaps_eHDCP_1_1_Features ? 1 : 0)) ;
2163        BDBG_MSG(("FastReauth(0): %d", 
2164                *pRxCapsReg & BHDM_HDCP_RxCaps_eFastReauth ? 1 : 0)) ;
2165#endif         
2166
2167        /* If attached Rx supports HDCP 1.1 with optional features, option Pj checking desired and
2168        the number of Pj link failures <= the max failures allow, enable HDCP 1.1 with optional features */
2169        if ((*pRxCapsReg & BHDM_HDCP_RxCaps_eHDCP_1_1_Features) 
2170        && (hHDMI->HdcpOptions.PjChecking)
2171        && (hHDMI->HdcpOptions.numPjFailures <= BHDM_HDCP_MAX_PJ_LINK_FAILURES_BEFORE_DISABLE_HDCP_1_1))   
2172        {
2173                /* tell the Rx the our HDMI core supports HDCP 1.1 with optional features as well */
2174                hHDMI->HdcpVersion = BHDM_HDCP_Version_e1_1_Optional_Features ;
2175
2176                /* turn on the callbacks for Pj interrupts */
2177                BHDM_CHECK_RC(rc, BINT_EnableCallback( hHDMI->hCallback[MAKE_INTR_ENUM(HDCP_PJ)] )) ;
2178
2179#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
2180                BHDM_CHECK_RC(rc, BINT_EnableCallback( hHDMI->hCallback[MAKE_INTR_ENUM(HDCP_PJ_MISMATCH)] )) ;
2181#endif
2182
2183        }
2184        else
2185        {
2186                hHDMI->HdcpVersion = BHDM_HDCP_Version_e1_1 ;
2187                /* HDCP 1.1 only; disable the Pj interrupts */
2188                BHDM_CHECK_RC(rc, BINT_DisableCallback( hHDMI->hCallback[MAKE_INTR_ENUM(HDCP_PJ)] )) ;
2189
2190#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
2191                BHDM_CHECK_RC(rc, BINT_DisableCallback( hHDMI->hCallback[MAKE_INTR_ENUM(HDCP_PJ_MISMATCH)] )) ;
2192#endif         
2193        }
2194       
2195
2196        hHDMI->RxBCaps = *pRxCapsReg ;
2197
2198done:   
2199
2200        BDBG_LEAVE(BHDM_HDCP_GetRxCaps) ;
2201        return rc ;
2202} /* end BHDM_HDCP_GetRxCaps */
2203
2204
2205
2206
2207/******************************************************************************
2208BERR_Code BHDM_HDCP_GetRxStatus
2209Summary: Check the status of the attached receiver.
2210*******************************************************************************/
2211BERR_Code BHDM_HDCP_GetRxStatus(
2212   BHDM_Handle hHDMI,                /* [in] HDMI handle */
2213   uint16_t *pRxStatusReg          /* [out] HDCP Rx Status */
2214) 
2215{
2216        BERR_Code   rc = BERR_SUCCESS;
2217        uint16_t Status ;
2218
2219        BDBG_ENTER(BHDM_HDCP_GetRxStatus) ;
2220        BDBG_ASSERT( hHDMI );
2221
2222#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
2223        /* We can't access I2C if control has been handed over to HW */
2224        if (hHDMI->bAutoRiPjCheckingEnabled)
2225        {
2226                *pRxStatusReg = hHDMI->RxStatus;
2227                goto done;
2228        }
2229#endif
2230
2231        BHDM_CHECK_RC(rc, BREG_I2C_Read(hHDMI->hI2cRegHandle, 
2232                        BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_BSTATUS, (uint8_t *) &Status, 2)) ;
2233               
2234        BREG_LE16(Status) ;
2235               
2236        BDBG_MSG(("Rx BStatus (0x41): %#x", Status)) ;
2237        BDBG_MSG(("------------------------")) ;
2238        BDBG_MSG(("HDMI Mode:            %d", 
2239                Status & BHDM_HDCP_RxStatus_eHdmiMode ? 1 : 0)) ;
2240        BDBG_MSG(("MAX Cascade Exceeded: %d", 
2241                Status & BHDM_HDCP_RxStatus_eMaxRepeatersExceeded ? 1 : 0)) ;
2242        BDBG_MSG(("Max Devs Exceeded:    %d", 
2243                Status & BHDM_HDCP_RxStatus_eMaxDevicesExceeded ? 1 : 0)) ;
2244
2245        *pRxStatusReg = Status ;
2246
2247#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
2248        hHDMI->RxStatus =  *pRxStatusReg ;
2249#endif
2250
2251
2252done:   
2253        BDBG_LEAVE(BHDM_HDCP_GetRxStatus) ;
2254        return rc ;
2255} /* end BHDM_HDCP_GetRxStatus */
2256
2257
2258
2259/******************************************************************************
2260BERR_Code BHDM_HDCP_CheckForRepeater
2261Summary: Check if the attached receiver is an HDCP Receiver.
2262*******************************************************************************/
2263BERR_Code BHDM_HDCP_CheckForRepeater(
2264   BHDM_Handle hHDMI,                /* [in] HDMI handle */
2265   uint8_t *uiRepeater          /* [out] HDCP Rx Status */
2266) 
2267{
2268        BERR_Code   rc = BERR_SUCCESS;
2269        uint8_t RxCaps ;
2270
2271        BDBG_ENTER(BHDM_HDCP_CheckForRepeater) ;
2272        BDBG_ASSERT( hHDMI );
2273
2274        BHDM_CHECK_RC(rc, BHDM_HDCP_GetRxCaps(hHDMI, &RxCaps)) ;
2275        if (RxCaps & BHDM_HDCP_RxCaps_eHdcpRepeater)
2276        {
2277                BDBG_MSG(("HDCP Repeater Found")) ;
2278                *uiRepeater = 1 ;
2279        }
2280        else
2281        {
2282                BDBG_MSG(("HDCP Standard Receiver Found")) ;
2283                *uiRepeater = 0 ;
2284        }
2285#if BHDM_CONFIG_REPEATER_SIMULATION_TEST
2286                *uiRepeater = 1 ;
2287                BDBG_WRN(("HDCP Repeater Found")) ;
2288#endif
2289done:   
2290        BDBG_LEAVE(BHDM_HDCP_CheckForRepeater) ;
2291        return rc ;
2292} /* end BHDM_HDCP_CheckForRepeater */
2293
2294
2295/******************************************************************************
2296BERR_Code BHDM_HDCP_GetRepeaterDepth
2297Summary: Get the depth (number of levels) of HDCP Repeaters
2298*******************************************************************************/
2299BERR_Code BHDM_HDCP_GetRepeaterDepth(
2300   BHDM_Handle hHDMI,      /* [in] HDMI handle */
2301   uint8_t *pRepeaterDepth /* [out] pointer to hold Levels of HDCP Repeaters */
2302) 
2303{
2304        BERR_Code   rc = BERR_SUCCESS;
2305        uint16_t    BStatus = 0 ;
2306
2307        BDBG_ENTER(BHDM_HDCP_GetRepeaterDepth) ;
2308        BDBG_ASSERT( hHDMI );
2309
2310
2311        BHDM_CHECK_RC(rc, BHDM_HDCP_GetRxStatus(hHDMI, &BStatus)) ;
2312       
2313        /* shift the BStatus Register to get the Repeater Depth; HDCP Spec Table 2-4 */
2314        BStatus = (uint16_t) (BStatus >> 8) ;
2315       
2316        BStatus = BStatus & 0x07 ;
2317        *pRepeaterDepth = (uint8_t) BStatus ;
2318        BDBG_MSG(("Repeater Depth: %X", BStatus)) ;
2319
2320done:   
2321        BDBG_LEAVE(BHDM_HDCP_GetRepeaterDepth) ;
2322        return rc ;
2323} /* end BHDM_HDCP_GetRepeaterDepth */
2324
2325
2326
2327
2328/******************************************************************************
2329BERR_Code BHDM_HDCP_GetRepeaterDeviceCount
2330Summary: Get the number of devices attached to the HDCP Repeater.
2331*******************************************************************************/
2332BERR_Code BHDM_HDCP_GetRepeaterDeviceCount(
2333   BHDM_Handle hHDMI,   /* [in] HDMI handle */
2334   uint8_t *pNumDevices /* [out] pointer to # of devices attached to the HDCP
2335                           Repeater */
2336) 
2337{
2338        BERR_Code   rc = BERR_SUCCESS;
2339        uint16_t    BStatus = 0 ;
2340
2341        BDBG_ENTER(BHDM_HDCP_GetRepeaterDeviceCount) ;
2342        BDBG_ASSERT( hHDMI );
2343
2344        BHDM_CHECK_RC(rc, BHDM_HDCP_GetRxStatus(hHDMI, &BStatus)) ;
2345
2346        /* AND the Device Count bits in the BStatus Register to get the Device Count */
2347        /* See HDCP Spec */
2348        BStatus = (uint8_t) (BStatus & 0x7F) ;
2349        BDBG_MSG(("Repeater Device Count: %X", BStatus)) ;
2350
2351        /* copy the Repeater Depth Value */
2352        *pNumDevices = (uint8_t) BStatus ;
2353
2354done : 
2355        BDBG_LEAVE(BHDM_HDCP_GetRepeaterDeviceCount) ;
2356        return rc ;
2357} /* end BHDM_HDCP_GetRepeaterDeviceCount */
2358
2359
2360
2361
2362/******************************************************************************
2363BERR_Code BHDM_HDCP_ReadRepeaterKsvFIFO
2364Summary: Read the KSV list from the attached repeater.
2365*******************************************************************************/
2366BERR_Code BHDM_HDCP_ReadRxRepeaterKsvFIFO(
2367   BHDM_Handle hHDMI,      /* [in] HDMI handle */
2368   uint8_t *pRxKsvList,    /* [out] pointer to memory to hold KSV List */
2369   uint16_t uiRxDeviceCount,  /* [in ] number of Ksvs in the Rx KSV List */
2370   const uint8_t *pRevokedKsvList,  /* [in] pointer to Revoked KSV List */
2371   const uint16_t uiRevokedKsvCount /* [in] number of KSVs in Revoked Ksv List */
2372) 
2373{
2374        BERR_Code   rc = BERR_SUCCESS;
2375       
2376        uint16_t uiBufSize ;
2377        bool bRevoked ;
2378        uint8_t iNumKsvBytes ;
2379
2380#if BHDM_CONFIG_REPEATER_SIMULATION_TEST
2381        uint8_t TestKsvFifo[] = 
2382        {
2383                0x2e, 0x17, 0x6a, 0x79, 0x35, 
2384                0x0f, 0xe2, 0x71, 0x8e, 0x47, 
2385                0xa6, 0x97, 0x53, 0xe8, 0x74
2386        } ;
2387#endif
2388
2389        BDBG_ENTER(BHDM_HDCP_ReadRxRepeaterKsvFIFO) ;
2390        BDBG_ASSERT( hHDMI );
2391
2392        uiBufSize = uiRxDeviceCount * BHDM_HDCP_KSV_LENGTH ;
2393
2394        /* Read the KSV FIFO */
2395        /* NOTE: the KSV_FIFO offset in the receiver does not auto-increment when read...
2396        ** all values come from the same offset
2397        */
2398               
2399#if BHDM_CONFIG_REPEATER_SIMULATION_TEST
2400                pRxKsvList = &TestKsvFifo[0] ;
2401#else
2402        BHDM_CHECK_RC(rc, BREG_I2C_Read(hHDMI->hI2cRegHandle, 
2403                        BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_REPEATER_KSV_FIFO, pRxKsvList, uiBufSize )) ;
2404#endif         
2405
2406
2407               
2408#if BDBG_DEBUG_BUILD
2409        {
2410                uint16_t    i ;
2411                BDBG_MSG(("Downstream Devices KSVs: %d", uiRxDeviceCount)) ;
2412                       
2413                for (i = 0 ; i < uiRxDeviceCount; i++) 
2414                {
2415                        BDBG_MSG(("KSV[%d]: = %02X %02X %02X %02X %02X ", 
2416                                i, pRxKsvList[i*5+4], pRxKsvList[i*5+3], pRxKsvList[i*5+2], 
2417                                pRxKsvList[i*5+1], pRxKsvList[i*5])) ;
2418                }
2419        }
2420#endif 
2421
2422        /* keep a copy of the attached ksv list */
2423        /* free any previous list that may have been allocated */
2424        if (hHDMI->HDCP_RepeaterKsvList)
2425                BKNI_Free(hHDMI->HDCP_RepeaterKsvList) ;
2426       
2427               
2428        hHDMI->HDCP_RepeaterDeviceCount = uiRxDeviceCount ;
2429        iNumKsvBytes = (uint16_t) (hHDMI->HDCP_RepeaterDeviceCount * BHDM_HDCP_KSV_LENGTH) ;
2430       
2431        /* there could be no devices attached to the repeater; finished */
2432        if (!iNumKsvBytes)
2433        {
2434                hHDMI->HDCP_RepeaterKsvList  = (uint8_t *) 0  ;
2435                goto done ;
2436        }
2437       
2438        hHDMI->HDCP_RepeaterKsvList  = (uint8_t *) BKNI_Malloc(sizeof(uint8_t) * iNumKsvBytes) ;
2439        BKNI_Memcpy(hHDMI->HDCP_RepeaterKsvList, pRxKsvList, iNumKsvBytes) ;
2440
2441
2442        /* check if the Repeater's Ksv List has any revoked Ksvs */
2443        if (uiRevokedKsvCount)
2444        {
2445                BHDM_HDCP_P_CheckRevokedKsvList(
2446                        (uint8_t *) pRevokedKsvList, uiRevokedKsvCount, 
2447                        pRxKsvList, uiRxDeviceCount, &bRevoked) ;
2448               
2449                if (bRevoked)
2450                {
2451                        rc = BHDM_HDCP_RX_BKSV_REVOKED ;
2452                        goto done ;
2453                }
2454        }
2455
2456done:   
2457        BDBG_LEAVE(BHDM_HDCP_ReadRxRepeaterKsvFIFO) ;
2458        return rc ;
2459} /* end BHDM_HDCP_ReadRepeaterKsvFIFO */
2460
2461
2462
2463/******************************************************************************
2464BERR_Code BHDM_HDCP_WriteTxKsvFIFO
2465Summary: Write the KSV list retrieved from the attached repeater to the
2466Transmitter core
2467*******************************************************************************/
2468BERR_Code BHDM_HDCP_WriteTxKsvFIFO(
2469        BHDM_Handle hHDMI, 
2470        uint8_t *KsvList, 
2471        uint16_t uiRxDeviceCount)
2472{
2473        BERR_Code rc = BERR_SUCCESS ;
2474        uint8_t     
2475                i, j ;
2476               
2477        uint8_t   
2478                timeoutMs,
2479                Ksv[5] ;
2480
2481        uint32_t   
2482                Register,
2483                BksvRegisterValue,
2484                RepeaterBusy ;
2485               
2486#if BHDM_CONFIG_REPEATER_SIMULATION_TEST
2487        uint8_t SHA_1[] =
2488        {
2489                0x86, 0xd5, 0xcb, 0x0f,
2490                0xef, 0x07, 0xc1, 0xef,
2491                0x1d, 0x0a, 0xd7, 0xcc,
2492                0xda, 0x6d, 0x18, 0xb1,
2493                0x5e, 0xff, 0xb3, 0x1f
2494        } ;
2495       
2496#endif
2497
2498        BDBG_ENTER(BHDM_HDCP_WriteTxKsvFIFO) ;
2499        BDBG_ASSERT( hHDMI );
2500
2501        for (i = 0 ; i < uiRxDeviceCount; i++)
2502        {
2503               
2504                /* wait until the Tx Repeater core is ready for a Ksv */
2505                timeoutMs = 10 ;
2506                do
2507                {
2508                        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_STATUS) ;
2509                        RepeaterBusy = BCHP_GET_FIELD_DATA(Register, HDMI_CP_STATUS, O_REPEATER_IS_BUSY) ;
2510                        if (!RepeaterBusy)
2511                                break ;
2512                               
2513                        BKNI_Sleep(1) ;
2514                        BDBG_WRN(("Tx Repeater Core Busy!")) ;
2515                } while ( timeoutMs-- ) ;
2516
2517
2518                /* copy the next Ksv */
2519                for (j = 0 ; j < BHDM_HDCP_KSV_LENGTH ; j++)
2520                        Ksv[j] = KsvList[BHDM_HDCP_KSV_LENGTH * i  + j] ;
2521
2522                /* write the 4 LSBs RxBksv to the transmitter... */
2523                BksvRegisterValue = 
2524                          Ksv[0]
2525                        | Ksv[1] <<  8
2526                        | Ksv[2] << 16
2527                        | Ksv[3] << 24 ;
2528               
2529                BREG_Write32(hHDMI->hRegister, BCHP_HDMI_KSV_FIFO_0, BksvRegisterValue) ;
2530#if 0
2531                BDBG_MSG((" Key[%d] %X", i, BksvRegisterValue)) ;
2532#endif         
2533               
2534                /* write the 1 MSB RxBksv to the transmitter... */
2535                BksvRegisterValue = Ksv[4] ;
2536                BREG_Write32(hHDMI->hRegister, BCHP_HDMI_KSV_FIFO_1, BksvRegisterValue) ;
2537#if 0           
2538                BDBG_MSG((" Key[%d] MSB %X", i, BksvRegisterValue)) ;
2539#endif         
2540        }
2541       
2542        BDBG_LEAVE(BHDM_HDCP_WriteTxKsvFIFO) ;
2543        return rc ;
2544}
2545
2546/******************************************************************************
2547BERR_Code BHDM_HDCP_IsLinkAuthenticated
2548Summary: Check if the current link is authenticated.
2549*******************************************************************************/
2550BERR_Code BHDM_HDCP_IsLinkAuthenticated(BHDM_Handle hHDMI)
2551{
2552        if (hHDMI->HDCP_AuthenticatedLink)
2553                return BERR_SUCCESS ;
2554        else
2555                return BHDM_HDCP_NO_AUTHENTICATED_LINK ;
2556}
2557
2558
2559#define DUMP_CP_STATUS  Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_STATUS) ; \
2560        BDBG_MSG(("CP_STATUS: %04X", Register)) ;
2561
2562/******************************************************************************
2563BERR_Code BHDM_HDCP_InitializeRepeaterAuthentication
2564Summary: Initialize the HDCP Core to authenticate the attached repeater
2565*******************************************************************************/
2566BERR_Code BHDM_HDCP_InitializeRepeaterAuthentication(BHDM_Handle hHDMI)
2567{
2568        BERR_Code rc = BERR_SUCCESS ;
2569
2570        uint32_t Register ;
2571        uint16_t BStatus ;
2572       
2573        /* load the initial values to the core */
2574        /* BCaps was already written by BHDM_ReadRxBksv */
2575        BHDM_CHECK_RC(rc, BREG_I2C_Read(hHDMI->hI2cRegHandle, 
2576                        BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_BSTATUS, (unsigned char *) &BStatus, 2)) ;
2577
2578        BREG_LE16(BStatus) ;
2579
2580        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_BKSV1) ;
2581        Register &= ~BCHP_MASK(HDMI_BKSV1, I_BSTATUS_15_0) ;
2582
2583        Register |=  BCHP_FIELD_DATA(HDMI_BKSV1, I_BSTATUS_15_0, BStatus) ;
2584        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_BKSV1, Register) ;
2585
2586#if 0
2587        BDBG_MSG(("Bksv1: %X", Register)) ;
2588#endif 
2589
2590        DUMP_CP_STATUS  ;
2591
2592        /* initilize Repeater logic */
2593        Register = BCHP_MASK(HDMI_HDCP_CTL, I_INIT_REPEATER) ;
2594        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_HDCP_CTL, Register) ;
2595       
2596        DUMP_CP_STATUS  ;
2597done:   
2598        return rc ;
2599}
2600
2601
2602/******************************************************************************
2603BERR_Code BHDM_HDCP_RepeaterAuthentication
2604Summary: Initialize the HDCP Core to authenticate the attached repeater
2605*******************************************************************************/
2606BERR_Code BHDM_HDCP_RepeaterAuthenticateLink(BHDM_Handle hHDMI, uint8_t *RepeaterAuthenticated) 
2607{
2608        BERR_Code rc ;
2609        uint8_t   
2610                i,
2611                timeoutMs,
2612                RepeaterBusy,
2613                Ksv[5] ;
2614               
2615       
2616        uint32_t Register ;
2617        uint32_t BksvRegisterValue ;
2618
2619
2620        /* wait for core to finish V calculation */
2621        timeoutMs = 10 ;
2622        do
2623        {
2624                Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_STATUS) ;
2625                RepeaterBusy = BCHP_GET_FIELD_DATA(Register, HDMI_CP_STATUS, O_REPEATER_IS_BUSY) ;
2626                if (!RepeaterBusy)
2627                        break ;
2628                       
2629                BKNI_Sleep(1) ;
2630                BDBG_MSG(("Waiting for TxCore Repeater V Calculation...")) ;
2631        } while ( timeoutMs-- ) ;
2632
2633       
2634        if (RepeaterBusy)
2635        {
2636                BDBG_ERR(("TxCore failed Repeater V Calculation"));
2637                *RepeaterAuthenticated = 0 ; 
2638                goto done ;
2639        }
2640               
2641       
2642        /*
2643        -- now read/load the results 160 byte SHA-1 Hash from the receiver...
2644        -- use the Ksv to store each 32 bit part of the V value
2645        */
2646
2647        for (i = 0; i < 5; i++)
2648        {
2649#if BHDM_CONFIG_REPEATER_SIMULATION_TEST
2650                BKNI_Memcpy(&BksvRegisterValue, (uint8_t *) &SHA_1[i*4],  4) ;
2651#else
2652                BHDM_CHECK_RC(rc, BREG_I2C_Read(hHDMI->hI2cRegHandle, 
2653                                BHDM_HDCP_RX_I2C_ADDR,  BHDM_HDCP_REPEATER_SHA1_V_H0 + (i * 4), Ksv, 4 )) ;
2654
2655                BksvRegisterValue =
2656                  Ksv[0]
2657                | (Ksv[1] <<  8)
2658                | (Ksv[2] << 16)
2659                | (Ksv[3] << 24) ;
2660#endif
2661                BDBG_MSG(("SHA-1 H%d Key = %X", i, BksvRegisterValue)) ;
2662
2663                BREG_Write32(hHDMI->hRegister, BCHP_HDMI_V, BksvRegisterValue) ; 
2664        }
2665       
2666
2667        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_STATUS) ;
2668        if (Register & BCHP_MASK(HDMI_CP_STATUS, O_V_MATCH))
2669        {
2670                BDBG_MSG(("Repeater AUTHENTICATED")) ;
2671                *RepeaterAuthenticated = 1 ; 
2672
2673#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
2674                if (hHDMI->DeviceSettings.bEnableAutoRiPjChecking) {
2675                        BHDM_HDCP_P_EnableAutoRiPjChecking(hHDMI, hHDMI->HdcpOptions.PjChecking) ;
2676                }
2677#endif
2678        }
2679        else
2680        {
2681                BDBG_ERR(("Repeater FAILED Authentication")) ;
2682                *RepeaterAuthenticated = 0 ; 
2683        }
2684        DUMP_CP_STATUS  ;
2685
2686done:   
2687        return BERR_SUCCESS ;
2688}
2689
2690
2691/******************************************************************************
2692BERR_Code BHDM_HDCP_GetRxKsv
2693Summary: Return KSV information obtained from the authentication
2694*******************************************************************************/
2695BERR_Code BHDM_HDCP_GetRxKsv(BHDM_Handle hHDMI, 
2696        uint8_t *AttachedDeviceKsv
2697)
2698{
2699        BERR_Code rc = BERR_SUCCESS ;
2700        uint8_t RxDeviceAttached ;
2701
2702        /* make sure HDMI Cable is connected to something... */
2703        BHDM_CHECK_RC(rc, BHDM_RxDeviceAttached(hHDMI, &RxDeviceAttached));
2704        if (!RxDeviceAttached)
2705        {
2706                rc = BHDM_NO_RX_DEVICE ;
2707                goto done ;
2708        }
2709       
2710        /* make sure the Rx has been read;  */
2711        BHDM_CHECK_RC(rc, BHDM_HDCP_ReadRxBksv(hHDMI, (uint8_t *) 0, 0)) ; 
2712
2713        /* copy the KSV of the attached device */
2714        BKNI_Memcpy(AttachedDeviceKsv, hHDMI->HDCP_RxKsv, BHDM_HDCP_KSV_LENGTH) ;
2715       
2716done:
2717        return rc ;     
2718}
2719
2720
2721/******************************************************************************
2722BERR_Code BHDM_HDCP_GetRepeaterKsvFifo
2723Summary: Return KSV information obtained from the authentication
2724*******************************************************************************/
2725BERR_Code BHDM_HDCP_GetRepeaterKsvFifo(BHDM_Handle hHDMI, 
2726        uint8_t *DownstreamKsvsBuffer, uint16_t DownstreamKsvsBufferSize
2727)
2728{
2729        BERR_Code rc = BERR_SUCCESS ;
2730        uint16_t iNumKsvBytes ;
2731        uint8_t RxDeviceAttached ;
2732
2733        /* make sure HDMI Cable is connected to something... */
2734        BHDM_CHECK_RC(rc, BHDM_RxDeviceAttached(hHDMI, &RxDeviceAttached));
2735        if (!RxDeviceAttached)
2736        {
2737                rc = BHDM_NO_RX_DEVICE ;
2738                goto done ;
2739        }
2740
2741        /* make sure link is authenticated */   
2742        rc = BHDM_HDCP_IsLinkAuthenticated(hHDMI) ;
2743        if (rc != BERR_SUCCESS)
2744        {
2745                BDBG_WRN(("Repeater KSV FIFO available only after authentication")) ;
2746                return rc ;
2747        }
2748       
2749        /* copy the Downstream KSV list */
2750        if (hHDMI->HDCP_RepeaterKsvList)
2751        {
2752                iNumKsvBytes = 
2753                        (uint16_t) hHDMI->HDCP_RepeaterDeviceCount * BHDM_HDCP_KSV_LENGTH ;
2754                       
2755                if (DownstreamKsvsBufferSize < iNumKsvBytes)
2756                {
2757                        BDBG_ERR(("Allocated buffer of %d bytes too small for KSV list of %d bytes", 
2758                                DownstreamKsvsBufferSize, iNumKsvBytes)) ;
2759                        return BERR_INVALID_PARAMETER ;
2760                }
2761               
2762                BKNI_Memcpy(DownstreamKsvsBuffer, hHDMI->HDCP_RepeaterKsvList, iNumKsvBytes) ;
2763        }
2764       
2765done:
2766        return rc ;     
2767}
2768
2769
2770#if !defined(BHDM_CONFIG_DISABLE_HDCP_AUTH_REPEATER_DEVCOUNT0)
2771/******************************************************************************
2772BERR_Code BHDM_HDCP_ForceVCalculation
2773Summary: Force the V Calculation for attached repeaters with device count zero
2774*******************************************************************************/
2775BERR_Code BHDM_HDCP_ForceVCalculation(BHDM_Handle hHDMI)
2776{
2777        uint32_t Register ;
2778        BREG_Handle hRegister = hHDMI->hRegister ;
2779       
2780        Register = BREG_Read32(hRegister, BCHP_HDMI_HDCP_CTL) ;
2781        Register |= BCHP_MASK(HDMI_HDCP_CTL, I_FORCE_VCALC) ;
2782        BREG_Write32(hRegister, BCHP_HDMI_HDCP_CTL, Register) ;
2783       
2784        Register &= ~BCHP_MASK(HDMI_HDCP_CTL, I_FORCE_VCALC) ;
2785        BREG_Write32(hRegister, BCHP_HDMI_HDCP_CTL, Register) ;
2786       
2787        return BERR_SUCCESS ;
2788}
2789#endif
2790
2791
2792/******************************************************************************
2793BERR_Code BHDM_HDCP_GetOptions
2794Summary: Get current options used for HDCP Authtentication etc.
2795*******************************************************************************/
2796BERR_Code BHDM_HDCP_GetOptions(
2797        BHDM_Handle hHDMI, BHDM_HDCP_OPTIONS *HdcpOptions)
2798{
2799        BKNI_Memcpy(HdcpOptions, &hHDMI->HdcpOptions, sizeof(BHDM_HDCP_OPTIONS)) ;
2800        return BERR_SUCCESS ;
2801}
2802
2803
2804/******************************************************************************
2805BERR_Code BHDM_HDCP_SetOptions
2806Summary: Set options used for HDCP Authtentication etc.
2807*******************************************************************************/
2808BERR_Code BHDM_HDCP_SetOptions(
2809        BHDM_Handle hHDMI, BHDM_HDCP_OPTIONS *HdcpOptions)
2810{
2811        BKNI_Memcpy(&hHDMI->HdcpOptions, HdcpOptions, sizeof(BHDM_HDCP_OPTIONS)) ;
2812        return BERR_SUCCESS ;
2813}
2814
2815
2816
2817BERR_Code BHDM_HDCP_P_DEBUG_PjForceVideo(BHDM_Handle hHDMI, uint8_t value)
2818{
2819#if BDBG_DEBUG_BUILD
2820        uint32_t Register ;
2821       
2822        Register = BREG_Read32(hHDMI->hRegister,  BCHP_HDMI_CP_TST) ;
2823        Register &= 
2824                ~(BCHP_MASK(HDMI_CP_TST, I_TST_FORCE_VIDEO_ALL_ONES) 
2825                | BCHP_MASK(HDMI_CP_TST, I_TST_FORCE_VIDEO_ALL_ZEROS)) ;
2826
2827        if (value)
2828                Register |= BCHP_FIELD_DATA(HDMI_CP_TST,  I_TST_FORCE_VIDEO_ALL_ONES, 1) ;
2829        else 
2830                Register |= BCHP_FIELD_DATA(HDMI_CP_TST,  I_TST_FORCE_VIDEO_ALL_ZEROS, 1) ;
2831               
2832        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_TST, Register) ;
2833#else
2834    BSTD_UNUSED(hHDMI);
2835    BSTD_UNUSED(value);
2836#endif
2837        return BERR_SUCCESS ;
2838}
2839
2840
2841BERR_Code BHDM_HDCP_P_DEBUG_PjCleanVideo(BHDM_Handle hHDMI, uint8_t value)
2842{
2843#if BDBG_DEBUG_BUILD
2844        uint32_t Register ;
2845
2846        BSTD_UNUSED(value) ;
2847       
2848        Register = BREG_Read32(hHDMI->hRegister,  BCHP_HDMI_CP_TST) ;
2849        Register &= 
2850                ~(BCHP_MASK(HDMI_CP_TST, I_TST_FORCE_VIDEO_ALL_ONES) 
2851                | BCHP_MASK(HDMI_CP_TST, I_TST_FORCE_VIDEO_ALL_ZEROS)) ;
2852
2853        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_TST, Register) ;
2854#else
2855    BSTD_UNUSED(hHDMI);
2856    BSTD_UNUSED(value);
2857#endif
2858        return BERR_SUCCESS ;
2859}
2860
2861
2862#if BHDM_CONFIG_HDCP_AUTO_RI_PJ_CHECKING_SUPPORT
2863/******************************************************************************
2864BERR_Code BHDM_HDCP_P_ConfigureAutoRi
2865Summary: Configure HDMI HDCP RI register for Auto (hardware) Ri Checking feature.
2866*******************************************************************************/
2867BERR_Code BHDM_HDCP_P_ConfigureAutoRi(BHDM_Handle hHDMI)
2868{
2869        uint32_t Register;
2870       
2871        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_3) ;
2872        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_EN) 
2873                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_ADDR_OFFSET)
2874                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_DATA)
2875                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_EN)
2876                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_ADDR_OFFSET)
2877                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_DATA));
2878
2879#if BHDM_CONFIG_HDCP_ADVANCED_HW_AUTO_RI_PJ_SUPPORT
2880        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_EN, 0x1)
2881                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_ADDR_OFFSET, 0xb)
2882                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_DATA, 0x0)
2883                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_EN, 0x1)
2884                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_ADDR_OFFSET, 0xa)
2885                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_DATA, 0xd3);
2886#else
2887        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_EN, 0x1)
2888                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_ADDR_OFFSET, 0xb)
2889                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_0_WR_DATA, 0x0)
2890                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_EN, 0x1)
2891                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_ADDR_OFFSET, 0x1)
2892                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_3, RI_IIC_REG_1_WR_DATA, 0x8);
2893#endif
2894        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_3, Register) ;
2895
2896
2897        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_4) ;
2898#if BHDM_CONFIG_HDCP_ADVANCED_HW_AUTO_RI_PJ_SUPPORT
2899        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_EN) 
2900                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_ADDR_OFFSET)
2901                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_DATA)
2902                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_3_WR_EN)
2903                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_3_WR_ADDR_OFFSET)
2904                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_3_WR_DATA));
2905
2906        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_EN, 0x1)
2907                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_ADDR_OFFSET, 0x9)
2908                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_DATA, 0x81)
2909                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_3_WR_EN, 0x1)
2910                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_3_WR_ADDR_OFFSET, 0x1)
2911                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_3_WR_DATA, 0x8);
2912#else
2913        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_EN) 
2914                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_ADDR_OFFSET)
2915                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_DATA)
2916                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_3_WR_EN));
2917
2918        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_EN, 0x1)
2919                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_ADDR_OFFSET, 0xb)
2920                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_2_WR_DATA, 0x1)
2921                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_4, RI_IIC_REG_3_WR_EN, 0x0);
2922#endif
2923        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_4, Register) ;
2924
2925#if BHDM_CONFIG_HDCP_ADVANCED_HW_AUTO_RI_PJ_SUPPORT
2926        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_8) ;
2927        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_4_WR_EN) 
2928                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_4_WR_ADDR_OFFSET)
2929                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_4_WR_DATA)
2930                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_5_WR_EN)
2931                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_5_WR_ADDR_OFFSET)
2932                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_5_WR_DATA));
2933
2934        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_4_WR_EN, 0x1)
2935                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_4_WR_ADDR_OFFSET, 0xb)
2936                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_8, RI_IIC_REG_4_WR_DATA, 0x1);
2937        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_8, Register) ;
2938#endif
2939
2940        return BERR_SUCCESS;
2941}
2942
2943
2944/******************************************************************************
2945BERR_Code BHDM_HDCP_P_ConfigureAutoPj
2946Summary: Configure HDMI HDCP PJ register for Auto (hardware) Pj Checking feature.
2947*******************************************************************************/
2948BERR_Code BHDM_HDCP_P_ConfigureAutoPj(BHDM_Handle hHDMI)
2949{
2950        uint32_t Register;
2951       
2952        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_5) ;
2953        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_EN) 
2954                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_ADDR_OFFSET)
2955                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_DATA)
2956                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_EN)
2957                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_ADDR_OFFSET)
2958                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_DATA));
2959
2960#if BHDM_CONFIG_HDCP_ADVANCED_HW_AUTO_RI_PJ_SUPPORT
2961        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_EN, 0x1)
2962                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_ADDR_OFFSET, 0xb)
2963                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_DATA, 0x0)
2964                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_EN, 0x1)
2965                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_ADDR_OFFSET, 0xa)
2966                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_DATA, 0xd3);
2967#else
2968        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_EN, 0x1)
2969                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_ADDR_OFFSET, 0xb)
2970                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_0_WR_DATA, 0x0)
2971                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_EN, 0x1)
2972                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_ADDR_OFFSET, 0x1)
2973                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_5, PJ_IIC_REG_1_WR_DATA, 0xa);
2974#endif
2975        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_5, Register) ;
2976
2977
2978        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_6) ;
2979#if BHDM_CONFIG_HDCP_ADVANCED_HW_AUTO_RI_PJ_SUPPORT
2980        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_EN) 
2981                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_ADDR_OFFSET)
2982                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_DATA)
2983                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_3_WR_EN)
2984                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_3_WR_ADDR_OFFSET)
2985                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_3_WR_DATA));
2986
2987        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_EN, 0x1)
2988                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_ADDR_OFFSET, 0x9)
2989                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_DATA, 0x81)
2990                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_3_WR_EN, 0x1)
2991                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_3_WR_ADDR_OFFSET, 0x1)
2992                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_3_WR_DATA, 0xa);
2993#else
2994        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_EN) 
2995                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_ADDR_OFFSET)
2996                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_DATA)
2997                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_3_WR_EN));
2998
2999        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_EN, 0x1)
3000                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_ADDR_OFFSET, 0xb)
3001                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_2_WR_DATA, 0x1)
3002                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_6, PJ_IIC_REG_3_WR_EN, 0x0);
3003#endif
3004        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_6, Register) ;
3005
3006
3007#if BHDM_CONFIG_HDCP_ADVANCED_HW_AUTO_RI_PJ_SUPPORT
3008        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_7) ;
3009        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_4_WR_EN) 
3010                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_4_WR_ADDR_OFFSET)
3011                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_4_WR_DATA)
3012                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_5_WR_EN)
3013                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_5_WR_ADDR_OFFSET)
3014                        | BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_5_WR_DATA));
3015
3016        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_4_WR_EN, 0x1)
3017                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_4_WR_ADDR_OFFSET, 0xb)
3018                        | BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_7, PJ_IIC_REG_4_WR_DATA, 0x1);
3019        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_7, Register) ;
3020#endif
3021
3022        return BERR_SUCCESS;
3023}
3024
3025
3026/******************************************************************************
3027BERR_Code BHDM_HDCP_P_EnableAutoRiPjChecking
3028Summary: Enable Auto (hardware) Ri/Pj Checking feature
3029*******************************************************************************/
3030BERR_Code BHDM_HDCP_P_EnableAutoRiPjChecking (BHDM_Handle hHDMI, uint8_t uiPjChecking)
3031{
3032        BERR_Code rc = BERR_SUCCESS;
3033        uint32_t Register;
3034        uint8_t uiMode;
3035
3036#if !(BHDM_CONFIG_HDCP_ADVANCED_HW_AUTO_RI_PJ_SUPPORT)
3037        uint32_t dataTransferFormat=3, cnt1=1, cnt2=2;
3038#endif
3039
3040        /* Set up I2C HW first */
3041        BHDM_CHECK_RC(rc, BREG_I2C_Read(hHDMI->hI2cRegHandle, 
3042                BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_BSTATUS, (uint8_t *) &hHDMI->RxStatus, 2)) ;       
3043        BREG_LE16(hHDMI->RxStatus) ;
3044       
3045        BHDM_CHECK_RC(rc, BREG_I2C_Read(hHDMI->hI2cRegHandle, 
3046                BHDM_HDCP_RX_I2C_ADDR, BHDM_HDCP_RX_BCAPS, &hHDMI->RxBCaps, 1)) ;
3047       
3048#if !(BHDM_CONFIG_HDCP_ADVANCED_HW_AUTO_RI_PJ_SUPPORT)
3049        rc = BREG_I2C_SetupHdmiHwAccess(hHDMI->hI2cRegHandle, dataTransferFormat, cnt1, cnt2);
3050        if (rc != BERR_SUCCESS)
3051        {
3052                BDBG_ERR(("Error setting up I2C HW for auto Ri/Pj link integrity check"));
3053                goto done;
3054        }
3055#endif
3056
3057        if (uiPjChecking)
3058                uiMode = 2;
3059        else
3060                uiMode = 1;
3061       
3062        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_2) ;
3063        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_2, IIC_REG_RD_ADDR_OFFSET));
3064        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_2, IIC_REG_RD_ADDR_OFFSET, 0xc);
3065        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_2, Register) ;
3066       
3067        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_1) ;
3068        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_1, CLEAR_RI_MISMATCH, 1);
3069        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_1, CLEAR_PJ_MISMATCH, 1);
3070        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_1, Register) ;
3071        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_1, CLEAR_RI_MISMATCH));
3072        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_1, CLEAR_PJ_MISMATCH));
3073        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_1, Register) ;
3074
3075        hHDMI->HDCP_AutoRiMismatch_A = false;
3076        hHDMI->HDCP_AutoRiMismatch_B = false;
3077
3078        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_1, CHECK_MODE));
3079        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_1, CHECK_MODE, uiMode);
3080        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_1, Register) ;
3081
3082        hHDMI->bAutoRiPjCheckingEnabled = true;
3083
3084done:
3085        return rc;
3086}
3087
3088
3089/******************************************************************************
3090BERR_Code BHDM_HDCP_P_DisableAutoRiPjChecking
3091Summary: Disable Auto (hardware) Ri/Pj Checking feature
3092*******************************************************************************/
3093BERR_Code BHDM_HDCP_P_DisableAutoRiPjChecking (BHDM_Handle hHDMI)
3094{
3095        uint32_t Register;
3096        uint8_t uiMode=0;
3097
3098        Register = BREG_Read32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_1) ;
3099        Register &= ~(BCHP_MASK(HDMI_CP_INTEGRITY_CHK_CFG_1, CHECK_MODE));
3100        Register |= BCHP_FIELD_DATA(HDMI_CP_INTEGRITY_CHK_CFG_1, CHECK_MODE, uiMode);
3101        BREG_Write32(hHDMI->hRegister, BCHP_HDMI_CP_INTEGRITY_CHK_CFG_1, Register) ;
3102
3103        hHDMI->bAutoRiPjCheckingEnabled = false;
3104        return BERR_SUCCESS;
3105}
3106
3107#endif
3108
3109
3110
3111
Note: See TracBrowser for help on using the repository browser.