1 /*****************************************************************************
3 *****************************************************************************
4 * Copyright (C) 2004 the VideoLAN team
7 * Authors: Jon Lech Johansen <jon-vl@nanocrew.net>
8 * Sam Hocevar <sam@zoy.org>
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
23 *****************************************************************************/
29 #include <vlc_common.h>
43 # if !defined( UNDER_CE )
51 #ifdef HAVE_SYS_STAT_H
52 # include <sys/stat.h>
54 #include <sys/types.h>
56 /* In Solaris (and perhaps others) PATH_MAX is in limits.h. */
60 # include <mach/mach.h>
61 # include <IOKit/IOKitLib.h>
62 # include <CoreFoundation/CFNumber.h>
66 #include "drmstables.h"
68 #if !defined( UNDER_CE )
69 /*****************************************************************************
70 * aes_s: AES keys structure
71 *****************************************************************************
72 * This structure stores a set of keys usable for encryption and decryption
73 * with the AES/Rijndael algorithm.
74 *****************************************************************************/
77 uint32_t pp_enc_keys[ AES_KEY_COUNT + 1 ][ 4 ];
78 uint32_t pp_dec_keys[ AES_KEY_COUNT + 1 ][ 4 ];
81 #define Digest DigestMD5
83 /*****************************************************************************
84 * shuffle_s: shuffle structure
85 *****************************************************************************
86 * This structure stores the static information needed to shuffle data using
88 *****************************************************************************/
92 uint32_t p_commands[ 20 ];
93 uint32_t p_bordel[ 16 ];
96 #define SWAP( a, b ) { (a) ^= (b); (b) ^= (a); (a) ^= (b); }
98 /*****************************************************************************
99 * drms_s: DRMS structure
100 *****************************************************************************
101 * This structure stores the static information needed to decrypt DRMS data.
102 *****************************************************************************/
107 uint8_t p_iviv[ 16 ];
113 char psz_homedir[ PATH_MAX ];
116 /*****************************************************************************
118 *****************************************************************************/
119 static void InitAES ( struct aes_s *, uint32_t * );
120 static void DecryptAES ( struct aes_s *, uint32_t *, const uint32_t * );
122 static void InitShuffle ( struct shuffle_s *, uint32_t *, uint32_t );
123 static void DoShuffle ( struct shuffle_s *, uint32_t *, uint32_t );
125 static uint32_t FirstPass ( uint32_t * );
126 static void SecondPass ( uint32_t *, uint32_t );
127 static void ThirdPass ( uint32_t * );
128 static void FourthPass ( uint32_t * );
129 static void TinyShuffle1 ( uint32_t * );
130 static void TinyShuffle2 ( uint32_t * );
131 static void TinyShuffle3 ( uint32_t * );
132 static void TinyShuffle4 ( uint32_t * );
133 static void TinyShuffle5 ( uint32_t * );
134 static void TinyShuffle6 ( uint32_t * );
135 static void TinyShuffle7 ( uint32_t * );
136 static void TinyShuffle8 ( uint32_t * );
137 static void DoExtShuffle ( uint32_t * );
139 static int GetSystemKey ( uint32_t *, bool );
140 static int WriteUserKey ( void *, uint32_t * );
141 static int ReadUserKey ( void *, uint32_t * );
142 static int GetUserKey ( void *, uint32_t * );
144 static int GetSCIData ( char *, uint32_t **, uint32_t * );
145 static int HashSystemInfo ( uint32_t * );
146 static int GetiPodID ( int64_t * );
148 #ifdef WORDS_BIGENDIAN
149 /*****************************************************************************
150 * Reverse: reverse byte order
151 *****************************************************************************/
152 static inline void Reverse( uint32_t *p_buffer, int n )
156 for( i = 0; i < n; i++ )
158 p_buffer[ i ] = GetDWLE(&p_buffer[ i ]);
161 # define REVERSE( p, n ) Reverse( p, n )
163 # define REVERSE( p, n )
166 /*****************************************************************************
167 * BlockXOR: XOR two 128 bit blocks
168 *****************************************************************************/
169 static inline void BlockXOR( uint32_t *p_dest, uint32_t *p_s1, uint32_t *p_s2 )
173 for( i = 0; i < 4; i++ )
175 p_dest[ i ] = p_s1[ i ] ^ p_s2[ i ];
179 /*****************************************************************************
180 * drms_alloc: allocate a DRMS structure
181 *****************************************************************************/
182 void *drms_alloc( const char *psz_homedir )
184 struct drms_s *p_drms;
186 p_drms = calloc( 1, sizeof(struct drms_s) );
190 strncpy( p_drms->psz_homedir, psz_homedir, PATH_MAX );
191 p_drms->psz_homedir[ PATH_MAX - 1 ] = '\0';
193 return (void *)p_drms;
196 /*****************************************************************************
197 * drms_free: free a previously allocated DRMS structure
198 *****************************************************************************/
199 void drms_free( void *_p_drms )
201 struct drms_s *p_drms = (struct drms_s *)_p_drms;
203 free( (void *)p_drms->p_name );
207 /*****************************************************************************
208 * drms_decrypt: unscramble a chunk of data
209 *****************************************************************************/
210 void drms_decrypt( void *_p_drms, uint32_t *p_buffer, uint32_t i_bytes, uint32_t *p_key )
212 struct drms_s *p_drms = (struct drms_s *)_p_drms;
213 uint32_t p_key_buf[ 4 ];
214 unsigned int i_blocks;
216 /* AES is a block cypher, round down the byte count */
217 i_blocks = i_bytes / 16;
218 i_bytes = i_blocks * 16;
220 /* Initialise the key */
224 memcpy( p_key, p_drms->p_key, 16 );
232 REVERSE( p_buffer, 4 );
233 DecryptAES( &p_drms->aes, p_tmp, p_buffer );
234 BlockXOR( p_tmp, p_key, p_tmp );
236 /* Use the previous scrambled data as the key for next block */
237 memcpy( p_key, p_buffer, 16 );
239 /* Copy unscrambled data back to the buffer */
240 memcpy( p_buffer, p_tmp, 16 );
241 REVERSE( p_buffer, 4 );
247 /*****************************************************************************
248 * drms_get_p_key: copy the p_key into user buffer
249 ****************************************************************************/
250 void drms_get_p_key( void *_p_drms, uint32_t *p_key )
252 struct drms_s *p_drms = (struct drms_s *)_p_drms;
254 memcpy( p_key, p_drms->p_key, 16 );
257 /*****************************************************************************
258 * drms_init: initialise a DRMS structure
259 *****************************************************************************
263 * -2: invalid argument
264 * -3: could not get system key
265 * -4: could not get SCI data
266 * -5: no user key found in SCI data
267 * -6: invalid user key
268 *****************************************************************************/
269 int drms_init( void *_p_drms, uint32_t i_type,
270 uint8_t *p_info, uint32_t i_len )
272 struct drms_s *p_drms = (struct drms_s *)_p_drms;
278 if( i_len < sizeof(p_drms->i_user) )
284 p_drms->i_user = U32_AT( p_info );
288 if( i_len < sizeof(p_drms->i_key) )
294 p_drms->i_key = U32_AT( p_info );
298 if( i_len < sizeof(p_drms->p_key) )
304 memcpy( p_drms->p_iviv, p_info, 16 );
308 p_drms->p_name = (uint8_t*) strdup( (char *)p_info );
310 if( p_drms->p_name == NULL )
318 uint32_t p_priv[ 64 ];
328 AddMD5( &md5, p_drms->p_name, strlen( (char *)p_drms->p_name ) );
329 AddMD5( &md5, p_drms->p_iviv, 16 );
332 if( p_drms->i_user == 0 && p_drms->i_key == 0 )
334 static const char p_secret[] = "tr1-th3n.y00_by3";
335 memcpy( p_drms->p_key, p_secret, 16 );
336 REVERSE( p_drms->p_key, 4 );
340 i_ret = GetUserKey( p_drms, p_drms->p_key );
347 InitAES( &p_drms->aes, p_drms->p_key );
349 memcpy( p_priv, p_info, 64 );
350 memcpy( p_drms->p_key, md5.p_digest, 16 );
351 drms_decrypt( p_drms, p_priv, 64, NULL );
352 REVERSE( p_priv, 64 );
354 if( p_priv[ 0 ] != 0x6e757469 ) /* itun */
360 InitAES( &p_drms->aes, p_priv + 6 );
361 memcpy( p_drms->p_key, p_priv + 12, 16 );
363 free( (void *)p_drms->p_name );
364 p_drms->p_name = NULL;
372 /* The following functions are local */
374 /*****************************************************************************
375 * InitAES: initialise AES/Rijndael encryption/decryption tables
376 *****************************************************************************
377 * The Advanced Encryption Standard (AES) is described in RFC 3268
378 *****************************************************************************/
379 static void InitAES( struct aes_s *p_aes, uint32_t *p_key )
382 uint32_t i_key, i_seed;
384 memset( p_aes->pp_enc_keys[1], 0, 16 );
385 memcpy( p_aes->pp_enc_keys[0], p_key, 16 );
387 /* Generate the key tables */
388 i_seed = p_aes->pp_enc_keys[ 0 ][ 3 ];
390 for( i_key = 0; i_key < AES_KEY_COUNT; i_key++ )
394 i_seed = AES_ROR( i_seed, 8 );
396 j = p_aes_table[ i_key ];
398 j ^= p_aes_encrypt[ (i_seed >> 24) & 0xff ]
399 ^ AES_ROR( p_aes_encrypt[ (i_seed >> 16) & 0xff ], 8 )
400 ^ AES_ROR( p_aes_encrypt[ (i_seed >> 8) & 0xff ], 16 )
401 ^ AES_ROR( p_aes_encrypt[ i_seed & 0xff ], 24 );
403 j ^= p_aes->pp_enc_keys[ i_key ][ 0 ];
404 p_aes->pp_enc_keys[ i_key + 1 ][ 0 ] = j;
405 j ^= p_aes->pp_enc_keys[ i_key ][ 1 ];
406 p_aes->pp_enc_keys[ i_key + 1 ][ 1 ] = j;
407 j ^= p_aes->pp_enc_keys[ i_key ][ 2 ];
408 p_aes->pp_enc_keys[ i_key + 1 ][ 2 ] = j;
409 j ^= p_aes->pp_enc_keys[ i_key ][ 3 ];
410 p_aes->pp_enc_keys[ i_key + 1 ][ 3 ] = j;
415 memcpy( p_aes->pp_dec_keys[ 0 ],
416 p_aes->pp_enc_keys[ 0 ], 16 );
418 for( i = 1; i < AES_KEY_COUNT; i++ )
420 for( t = 0; t < 4; t++ )
422 uint32_t j, k, l, m, n;
424 j = p_aes->pp_enc_keys[ i ][ t ];
426 k = (((j >> 7) & 0x01010101) * 27) ^ ((j & 0xff7f7f7f) << 1);
427 l = (((k >> 7) & 0x01010101) * 27) ^ ((k & 0xff7f7f7f) << 1);
428 m = (((l >> 7) & 0x01010101) * 27) ^ ((l & 0xff7f7f7f) << 1);
432 n = AES_ROR( l ^ j, 16 ) ^ AES_ROR( k ^ j, 8 ) ^ AES_ROR( j, 24 );
434 p_aes->pp_dec_keys[ i ][ t ] = k ^ l ^ m ^ n;
439 /*****************************************************************************
440 * DecryptAES: decrypt an AES/Rijndael 128 bit block
441 *****************************************************************************/
442 static void DecryptAES( struct aes_s *p_aes,
443 uint32_t *p_dest, const uint32_t *p_src )
445 uint32_t p_wtxt[ 4 ]; /* Working cyphertext */
447 unsigned int i_round, t;
449 for( t = 0; t < 4; t++ )
451 /* FIXME: are there any endianness issues here? */
452 p_wtxt[ t ] = p_src[ t ] ^ p_aes->pp_enc_keys[ AES_KEY_COUNT ][ t ];
456 for( i_round = 0; i_round < (AES_KEY_COUNT - 1); i_round++ )
458 for( t = 0; t < 4; t++ )
460 p_tmp[ t ] = AES_XOR_ROR( p_aes_itable, p_wtxt );
463 for( t = 0; t < 4; t++ )
465 p_wtxt[ t ] = p_tmp[ t ]
466 ^ p_aes->pp_dec_keys[ (AES_KEY_COUNT - 1) - i_round ][ t ];
470 /* Final round (9) */
471 for( t = 0; t < 4; t++ )
473 p_dest[ t ] = AES_XOR_ROR( p_aes_decrypt, p_wtxt );
474 p_dest[ t ] ^= p_aes->pp_dec_keys[ 0 ][ t ];
478 /*****************************************************************************
479 * InitShuffle: initialise a shuffle structure
480 *****************************************************************************
481 * This function initialises tables in the p_shuffle structure that will be
482 * used later by DoShuffle. The only external parameter is p_sys_key.
483 *****************************************************************************/
484 static void InitShuffle( struct shuffle_s *p_shuffle, uint32_t *p_sys_key,
487 char p_secret1[] = "Tv!*";
488 static const char p_secret2[] = "____v8rhvsaAvOKM____FfUH%798=[;."
489 "____f8677680a634____ba87fnOIf)(*";
492 p_shuffle->i_version = i_version;
494 /* Fill p_commands using the key and a secret seed */
495 for( i = 0; i < 20; i++ )
501 AddMD5( &md5, (const uint8_t *)p_sys_key, 16 );
502 AddMD5( &md5, (const uint8_t *)p_secret1, 4 );
507 REVERSE( md5.p_digest, 1 );
508 i_hash = ((int32_t)U32_AT(md5.p_digest)) % 1024;
510 p_shuffle->p_commands[ i ] = i_hash < 0 ? i_hash * -1 : i_hash;
513 /* Fill p_bordel with completely meaningless initial values. */
514 memcpy( p_shuffle->p_bordel, p_secret2, 64 );
515 for( i = 0; i < 4; i++ )
517 p_shuffle->p_bordel[ 4 * i ] = U32_AT(p_sys_key + i);
518 REVERSE( p_shuffle->p_bordel + 4 * i + 1, 3 );
522 /*****************************************************************************
523 * DoShuffle: shuffle buffer
524 *****************************************************************************
525 * This is so ugly and uses so many MD5 checksums that it is most certainly
526 * one-way, though why it needs to be so complicated is beyond me.
527 *****************************************************************************/
528 static void DoShuffle( struct shuffle_s *p_shuffle,
529 uint32_t *p_buffer, uint32_t i_size )
532 uint32_t p_big_bordel[ 16 ];
533 uint32_t *p_bordel = p_shuffle->p_bordel;
536 static const uint32_t p_secret3[] =
538 0xAAAAAAAA, 0x01757700, 0x00554580, 0x01724500, 0x00424580,
539 0x01427700, 0x00000080, 0xC1D59D01, 0x80144981, 0x815C8901,
540 0x80544981, 0x81D45D01, 0x00000080, 0x81A3BB03, 0x00A2AA82,
541 0x01A3BB03, 0x0022A282, 0x813BA202, 0x00000080, 0x6D575737,
542 0x4A5275A5, 0x6D525725, 0x4A5254A5, 0x6B725437, 0x00000080,
543 0xD5DDB938, 0x5455A092, 0x5D95A013, 0x4415A192, 0xC5DD393A,
544 0x00000080, 0x55555555
546 static const uint32_t i_secret3 = sizeof(p_secret3)/sizeof(p_secret3[0]);
548 static const char p_secret4[] =
549 "pbclevtug (p) Nccyr Pbzchgre, Vap. Nyy Evtugf Erfreirq.";
550 static const uint32_t i_secret4 = sizeof(p_secret4)/sizeof(p_secret4[0]); /* It include the terminal '\0' */
552 /* Using the MD5 hash of a memory block is probably not one-way enough
553 * for the iTunes people. This function randomises p_bordel depending on
554 * the values in p_commands to make things even more messy in p_bordel. */
555 for( i = 0; i < 20; i++ )
557 uint8_t i_command, i_index;
559 if( !p_shuffle->p_commands[ i ] )
564 i_command = (p_shuffle->p_commands[ i ] & 0x300) >> 8;
565 i_index = p_shuffle->p_commands[ i ] & 0xff;
570 p_bordel[ i_index & 0xf ] = p_bordel[ i_index >> 4 ]
571 + p_bordel[ ((i_index + 0x10) >> 4) & 0xf ];
574 p_bordel[ i_index >> 4 ] ^= p_shuffle_xor[ 0xff - i_index ];
577 p_bordel[ i_index >> 4 ] -= p_shuffle_sub[ 0xff - i_index ];
580 p_bordel[ i_index >> 4 ] += p_shuffle_add[ 0xff - i_index ];
585 if( p_shuffle->i_version == 0x01000300 )
587 DoExtShuffle( p_bordel );
590 /* Convert our newly randomised p_bordel to big endianness and take
593 for( i = 0; i < 16; i++ )
595 p_big_bordel[ i ] = U32_AT(p_bordel + i);
597 AddMD5( &md5, (const uint8_t *)p_big_bordel, 64 );
598 if( p_shuffle->i_version == 0x01000300 )
600 uint32_t p_tmp3[i_secret3];
601 char p_tmp4[i_secret4];
603 memcpy( p_tmp3, p_secret3, sizeof(p_secret3) );
604 REVERSE( p_tmp3, i_secret3 );
606 #define ROT13(c) (((c)>='A'&&(c)<='Z')?(((c)-'A'+13)%26)+'A':\
607 ((c)>='a'&&(c)<='z')?(((c)-'a'+13)%26)+'a':c)
608 for( uint32_t i = 0; i < i_secret4; i++ )
609 p_tmp4[i] = ROT13( p_secret4[i] );
612 AddMD5( &md5, (const uint8_t *)p_tmp3, sizeof(p_secret3) );
613 AddMD5( &md5, (const uint8_t *)p_tmp4, i_secret4 );
617 /* XOR our buffer with the computed checksum */
618 for( i = 0; i < i_size; i++ )
620 p_buffer[ i ] ^= md5.p_digest[ i ];
624 /*****************************************************************************
625 * DoExtShuffle: extended shuffle
626 *****************************************************************************
627 * This is even uglier.
628 *****************************************************************************/
629 static void DoExtShuffle( uint32_t * p_bordel )
633 i_ret = FirstPass( p_bordel );
635 SecondPass( p_bordel, i_ret );
637 ThirdPass( p_bordel );
639 FourthPass( p_bordel );
642 static uint32_t FirstPass( uint32_t * p_bordel )
644 uint32_t i, i_cmd, i_ret = 5;
646 TinyShuffle1( p_bordel );
652 p_bordel[ 1 ] += 0x10000000;
653 p_bordel[ 3 ] += 0x12777;
655 if( (p_bordel[ 10 ] & 1) && i_ret )
658 p_bordel[ 1 ] -= p_bordel[ 2 ];
659 p_bordel[ 11 ] += p_bordel[ 12 ];
663 if( (p_bordel[ 1 ] + p_bordel[ 2 ]) >= 0x7D0 )
665 switch( ((p_bordel[ 3 ] ^ 0x567F) >> 2) & 7 )
668 for( i = 0; i < 3; i++ )
670 if( p_bordel[ i + 10 ] > 0x4E20 )
672 p_bordel[ i + 1 ] += p_bordel[ i + 2 ];
677 p_bordel[ 1 ] -= p_bordel[ 2 ];
680 p_bordel[ 11 ] += p_bordel[ 12 ];
683 p_bordel[ 3 ] ^= p_bordel[ 4 ];
686 p_bordel[ 13 ] &= p_bordel[ 14 ];
689 p_bordel[ 0 ] |= p_bordel[ 1 ];
701 for( i = 0, i_cmd = 0; i < 16; i++ )
703 if( p_bordel[ i ] < p_bordel[ i_cmd ] )
709 if( i_ret && i_cmd != 5 )
717 p_bordel[ 8 ] &= p_bordel[ 6 ] >> 1;
721 for( i = 0; i < 3; i++ )
724 if( p_bordel[ 11 ] & 5 )
726 p_bordel[ 8 ] += p_bordel[ 9 ];
736 i_cmd = (p_bordel[ 15 ] + 0x93) >> 3;
737 if( p_bordel[ 15 ] & 0x100 )
746 while( p_bordel[ 11 ] & 1 )
748 p_bordel[ 11 ] >>= 1;
753 p_bordel[ 14 ] -= 0x19FE;
765 i_cmd = ((p_bordel[ 3 ] + p_bordel[ 4 ] + 10) >> 1) - p_bordel[ 4 ];
773 p_bordel[ 14 ] >>= 1;
782 p_bordel[ 15 ] &= 0x55;
785 p_bordel[ 2 ] &= 0xB62FC;
791 TinyShuffle2( p_bordel );
796 static void SecondPass( uint32_t * p_bordel, uint32_t i_tmp )
798 uint32_t i, i_cmd, i_jc = 5;
800 TinyShuffle3( p_bordel );
802 for( i = 0, i_cmd = 0; i < 16; i++ )
804 if( p_bordel[ i ] > p_bordel[ i_cmd ] )
813 if( p_bordel[ 1 ] < p_bordel[ 8 ] )
819 if( (p_bordel[ 9 ] & 0x7777) == 0x3333 )
826 if( p_bordel[ 1 ] < p_bordel[ 8 ] )
835 p_bordel[ 1 ] -= p_bordel[ 5 ];
836 for( i = 0; i < 3; i++ )
838 switch( p_bordel[ 1 ] & 3 )
847 p_bordel[ 13 ] &= 0xFEFEFEF7;
850 p_bordel[ 8 ] |= 0x80080011;
862 p_bordel[ 15 ] ^= 0x18547EFF;
868 switch( ( p_bordel[ 12 ] + p_bordel[ 13 ] + p_bordel[ 6 ] ) % 5 )
888 i = 3; /* Restart the whole loop */
893 TinyShuffle4( p_bordel );
897 TinyShuffle5( p_bordel );
899 switch( ( p_bordel[ 2 ] * 2 + 15 ) % 5 )
902 if( ( p_bordel[ 3 ] + i_tmp ) <=
903 ( p_bordel[ 1 ] + p_bordel[ 15 ] ) )
909 p_bordel[ 10 ] -= 0x13;
916 if( !( p_bordel[ 2 ] & 1 ) || i_jc == 0 )
922 p_bordel[ 2 ] += 0x13;
926 p_bordel[ 2 ] &= 0x10076000;
929 static void ThirdPass( uint32_t * p_bordel )
933 i_cmd = ((p_bordel[ 7 ] + p_bordel[ 14 ] + 10) >> 1) - p_bordel[ 14 ];
944 p_bordel[ i_cmd + 3 ] &= 0x5EDE36B;
945 p_bordel[ 5 ] += p_bordel[ 8 ];
946 p_bordel[ 4 ] += p_bordel[ 7 ];
947 p_bordel[ 3 ] += p_bordel[ 6 ];
948 p_bordel[ 2 ] += p_bordel[ 5 ];
951 p_bordel[ 1 ] += p_bordel[ 4 ];
952 p_bordel[ 0 ] += p_bordel[ 3 ];
953 TinyShuffle6( p_bordel );
956 if( (p_bordel[ 11 ] & p_bordel[ 2 ]) > 0x211B )
965 p_bordel[ 9 ] ^= p_bordel[ 2 ];
968 p_bordel[ 2 ] ^= (p_bordel[ 1 ] & p_bordel[ 13 ]);
971 p_bordel[ 0 ] -= p_bordel[ 11 ] & p_bordel[ 15 ];
974 p_bordel[ 6 ] >>= (p_bordel[ 14 ] & 3);
978 SWAP( p_bordel[ 0 ], p_bordel[ 10 ] );
980 TinyShuffle6( p_bordel );
985 static void FourthPass( uint32_t * p_bordel )
989 TinyShuffle7( p_bordel );
991 switch( p_bordel[ 5 ] % 5)
997 p_bordel[ 11 ] ^= (p_bordel[ 3 ] + p_bordel[ 6 ] + p_bordel[ 8 ]);
1000 for( i = 4; i < 15 && (p_bordel[ i ] & 5) == 0; i++ )
1002 SWAP( p_bordel[ i ], p_bordel[ 15 - i ] );
1006 p_bordel[ 12 ] -= 1;
1007 p_bordel[ 13 ] += 1;
1008 p_bordel[ 2 ] -= 0x64;
1009 p_bordel[ 3 ] += 0x64;
1010 TinyShuffle8( p_bordel );
1014 for( i = 0, j = 0; i < 16; i++ )
1016 if( p_bordel[ i ] > p_bordel[ j ] )
1022 switch( p_bordel[ j ] % 100 )
1025 SWAP( p_bordel[ 0 ], p_bordel[ j ] );
1028 p_bordel[ 1 ] >>= 1;
1029 p_bordel[ 2 ] <<= 1;
1030 p_bordel[ 14 ] >>= 3;
1031 p_bordel[ 15 ] <<= 4;
1034 p_bordel[ j ] += p_bordel[ 13 ];
1037 p_bordel[ 1 ] += 0x20E;
1038 p_bordel[ 5 ] += 0x223D;
1039 p_bordel[ 13 ] -= 0x576;
1040 p_bordel[ 15 ] += 0x576;
1043 p_bordel[ 2 ] -= 0x64;
1044 p_bordel[ 3 ] += 0x64;
1045 p_bordel[ 12 ] -= 1;
1046 p_bordel[ 13 ] += 1;
1050 p_bordel[ j ] += p_bordel[ 13 ];
1054 TinyShuffle8( p_bordel );
1057 /*****************************************************************************
1058 * TinyShuffle[12345678]: tiny shuffle subroutines
1059 *****************************************************************************
1060 * These standalone functions are little helpers for the shuffling process.
1061 *****************************************************************************/
1062 static void TinyShuffle1( uint32_t * p_bordel )
1064 uint32_t i_cmd = (p_bordel[ 5 ] + 10) >> 2;
1066 if( p_bordel[ 5 ] > 0x7D0 )
1080 if( p_bordel[ 4 ] & 5 )
1082 p_bordel[ 1 ] ^= 0x4D;
1086 p_bordel[ 12 ] += 5;
1091 static void TinyShuffle2( uint32_t * p_bordel )
1095 for( i = 0, j = 0; i < 16; i++ )
1097 if( (p_bordel[ i ] & 0x777) > (p_bordel[ j ] & 0x777) )
1105 for( ; j < 15; j++ )
1107 p_bordel[ j ] += p_bordel[ j + 1 ];
1112 p_bordel[ 2 ] &= 0xB62FC;
1116 static void TinyShuffle3( uint32_t * p_bordel )
1118 uint32_t i_cmd = p_bordel[ 6 ] + 0x194B;
1120 if( p_bordel[ 6 ] > 0x2710 )
1128 p_bordel[ 3 ] += 0x19FE;
1131 p_bordel[ 7 ] -= p_bordel[ 3 ] >> 2;
1134 p_bordel[ 5 ] ^= 0x248A;
1139 static void TinyShuffle4( uint32_t * p_bordel )
1143 for( i = 0, j = 0; i < 16; i++ )
1145 if( p_bordel[ i ] < p_bordel[ j ] )
1151 if( (p_bordel[ j ] % (j + 1)) > 10 )
1154 p_bordel[ 2 ] += 0x13;
1155 p_bordel[ 12 ] += 1;
1159 static void TinyShuffle5( uint32_t * p_bordel )
1163 p_bordel[ 2 ] &= 0x7F3F;
1165 for( i = 0; i < 5; i++ )
1167 switch( ( p_bordel[ 2 ] + 10 + i ) % 5 )
1170 p_bordel[ 12 ] &= p_bordel[ 2 ];
1173 p_bordel[ 3 ] ^= p_bordel[ 15 ];
1176 p_bordel[ 15 ] += 0x576;
1179 p_bordel[ 7 ] -= 0x2D;
1182 p_bordel[ 1 ] <<= 1;
1188 static void TinyShuffle6( uint32_t * p_bordel )
1192 for( i = 0; i < 8; i++ )
1194 j = p_bordel[ 3 ] & 0x7514 ? 5 : 7;
1195 SWAP( p_bordel[ i ], p_bordel[ i + j ] );
1199 static void TinyShuffle7( uint32_t * p_bordel )
1203 i = (((p_bordel[ 9 ] + p_bordel[ 15 ] + 12) >> 2) - p_bordel[ 4 ]) & 7;
1207 SWAP( p_bordel[ i ], p_bordel[ i + 3 ] );
1210 SWAP( p_bordel[ 1 ], p_bordel[ 10 ] );
1213 static void TinyShuffle8( uint32_t * p_bordel )
1217 i = (p_bordel[ 0 ] & p_bordel[ 6 ]) & 0xF;
1219 switch( p_bordel[ i ] % 1000 )
1222 if( (p_bordel[ i ] & 0x777) > (p_bordel[ 7 ] & 0x5555) )
1224 p_bordel[ i ] ^= p_bordel[ 5 ] & p_bordel[ 3 ];
1228 p_bordel[ 15 ] &= 0x5555;
1231 p_bordel[ i ] ^= p_bordel[ 15 ];
1234 SWAP( p_bordel[ 0 ], p_bordel[ 3 ] );
1235 SWAP( p_bordel[ 1 ], p_bordel[ 6 ] );
1236 SWAP( p_bordel[ 3 ], p_bordel[ 6 ] );
1237 SWAP( p_bordel[ 4 ], p_bordel[ 9 ] );
1238 SWAP( p_bordel[ 5 ], p_bordel[ 8 ] );
1239 SWAP( p_bordel[ 6 ], p_bordel[ 7 ] );
1240 SWAP( p_bordel[ 13 ], p_bordel[ 14 ] );
1243 p_bordel[ i ] += p_bordel[ 1 ] ^ 0x80080011;
1244 p_bordel[ i ] += p_bordel[ 2 ] ^ 0xBEEFDEAD;
1245 p_bordel[ i ] += p_bordel[ 3 ] ^ 0x8765F444;
1246 p_bordel[ i ] += p_bordel[ 4 ] ^ 0x78145326;
1249 p_bordel[ 12 ] -= p_bordel[ i ];
1250 p_bordel[ 13 ] += p_bordel[ i ];
1253 p_bordel[ i ] += p_bordel[ 1 ];
1254 p_bordel[ i ] -= p_bordel[ 7 ];
1255 p_bordel[ i ] -= p_bordel[ 8 ];
1256 p_bordel[ i ] += p_bordel[ 9 ];
1257 p_bordel[ i ] += p_bordel[ 13 ];
1261 p_bordel[ i + 1 ] >>= 1;
1262 p_bordel[ i + 2 ] <<= 4;
1263 p_bordel[ i + 3 ] >>= 3;
1266 p_bordel[ 1 ] += 0x20E;
1267 p_bordel[ 5 ] += 0x223D;
1268 p_bordel[ 13 ] -= 0x576;
1269 p_bordel[ 15 ] += 0x576;
1272 if( (p_bordel[ i ] ^ 0x8765F441) < 0x2710 )
1274 SWAP( p_bordel[ 0 ], p_bordel[ 1 ] );
1278 SWAP( p_bordel[ 1 ], p_bordel[ 11 ] );
1284 /*****************************************************************************
1285 * GetSystemKey: get the system key
1286 *****************************************************************************
1287 * Compute the system key from various system information, see HashSystemInfo.
1288 *****************************************************************************/
1289 static int GetSystemKey( uint32_t *p_sys_key, bool b_ipod )
1291 static const char p_secret5[ 8 ] = "YuaFlafu";
1292 static const char p_secret6[ 8 ] = "zPif98ga";
1295 uint32_t p_system_hash[ 4 ];
1297 /* Compute the MD5 hash of our system info */
1298 if( ( !b_ipod && HashSystemInfo( p_system_hash ) ) ||
1299 ( b_ipod && GetiPodID( &i_ipod_id ) ) )
1304 /* Combine our system info hash with additional secret data. The resulting
1305 * MD5 hash will be our system key. */
1307 AddMD5( &md5, (const uint8_t*)p_secret5, 8 );
1311 AddMD5( &md5, (const uint8_t *)p_system_hash, 6 );
1312 AddMD5( &md5, (const uint8_t *)p_system_hash, 6 );
1313 AddMD5( &md5, (const uint8_t *)p_system_hash, 6 );
1314 AddMD5( &md5, (const uint8_t *)p_secret6, 8 );
1318 i_ipod_id = U64_AT(&i_ipod_id);
1319 AddMD5( &md5, (const uint8_t *)&i_ipod_id, sizeof(i_ipod_id) );
1320 AddMD5( &md5, (const uint8_t *)&i_ipod_id, sizeof(i_ipod_id) );
1321 AddMD5( &md5, (const uint8_t *)&i_ipod_id, sizeof(i_ipod_id) );
1326 memcpy( p_sys_key, md5.p_digest, 16 );
1332 # define DRMS_DIRNAME "drms"
1334 # define DRMS_DIRNAME ".drms"
1337 /*****************************************************************************
1338 * WriteUserKey: write the user key to hard disk
1339 *****************************************************************************
1340 * Write the user key to the hard disk so that it can be reused later or used
1341 * on operating systems other than Win32.
1342 *****************************************************************************/
1343 static int WriteUserKey( void *_p_drms, uint32_t *p_user_key )
1345 struct drms_s *p_drms = (struct drms_s *)_p_drms;
1348 char psz_path[ PATH_MAX ];
1350 snprintf( psz_path, PATH_MAX - 1,
1351 "%s/" DRMS_DIRNAME, p_drms->psz_homedir );
1353 #if defined( WIN32 )
1354 if( !mkdir( psz_path ) || errno == EEXIST )
1356 if( !mkdir( psz_path, 0755 ) || errno == EEXIST )
1359 snprintf( psz_path, PATH_MAX - 1, "%s/" DRMS_DIRNAME "/%08X.%03d",
1360 p_drms->psz_homedir, p_drms->i_user, p_drms->i_key );
1362 file = vlc_fopen( psz_path, "wb" );
1365 i_ret = fwrite( p_user_key, sizeof(uint32_t),
1366 4, file ) == 4 ? 0 : -1;
1374 /*****************************************************************************
1375 * ReadUserKey: read the user key from hard disk
1376 *****************************************************************************
1377 * Retrieve the user key from the hard disk if available.
1378 *****************************************************************************/
1379 static int ReadUserKey( void *_p_drms, uint32_t *p_user_key )
1381 struct drms_s *p_drms = (struct drms_s *)_p_drms;
1384 char psz_path[ PATH_MAX ];
1386 snprintf( psz_path, PATH_MAX - 1,
1387 "%s/" DRMS_DIRNAME "/%08X.%03d", p_drms->psz_homedir,
1388 p_drms->i_user, p_drms->i_key );
1390 file = vlc_fopen( psz_path, "rb" );
1393 i_ret = fread( p_user_key, sizeof(uint32_t),
1394 4, file ) == 4 ? 0 : -1;
1401 /*****************************************************************************
1402 * GetUserKey: get the user key
1403 *****************************************************************************
1404 * Retrieve the user key from the hard disk if available, otherwise generate
1405 * it from the system key. If the key could be successfully generated, write
1406 * it to the hard disk for future use.
1407 *****************************************************************************/
1408 static int GetUserKey( void *_p_drms, uint32_t *p_user_key )
1410 static const char p_secret7[] = "mUfnpognadfgf873";
1411 struct drms_s *p_drms = (struct drms_s *)_p_drms;
1413 struct shuffle_s shuffle;
1415 uint32_t *p_sci_data = NULL;
1416 uint32_t i_user, i_key;
1417 uint32_t p_sys_key[ 4 ];
1418 uint32_t i_sci_size = 0, i_blocks, i_remaining;
1419 uint32_t *p_sci0, *p_sci1, *p_buffer;
1420 uint32_t p_sci_key[ 4 ];
1424 if( ReadUserKey( p_drms, p_user_key ) == 0 )
1426 REVERSE( p_user_key, 4 );
1430 psz_ipod = getenv( "IPOD" );
1432 if( GetSystemKey( p_sys_key, psz_ipod ? true : false ) )
1437 if( GetSCIData( psz_ipod, &p_sci_data, &i_sci_size ) )
1442 /* Phase 1: unscramble the SCI data using the system key and shuffle
1443 * it using DoShuffle(). */
1445 /* Skip the first 4 bytes (some sort of header). Decrypt the rest. */
1446 i_blocks = (i_sci_size - 4) / 16;
1447 i_remaining = (i_sci_size - 4) - (i_blocks * 16);
1448 p_buffer = p_sci_data + 1;
1450 /* Decrypt and shuffle our data at the same time */
1451 InitAES( &aes, p_sys_key );
1452 REVERSE( p_sys_key, 4 );
1453 REVERSE( p_sci_data, 1 );
1454 InitShuffle( &shuffle, p_sys_key, p_sci_data[ 0 ] );
1456 memcpy( p_sci_key, p_secret7, 16 );
1457 REVERSE( p_sci_key, 4 );
1461 uint32_t p_tmp[ 4 ];
1463 REVERSE( p_buffer, 4 );
1464 DecryptAES( &aes, p_tmp, p_buffer );
1465 BlockXOR( p_tmp, p_sci_key, p_tmp );
1467 /* Use the previous scrambled data as the key for next block */
1468 memcpy( p_sci_key, p_buffer, 16 );
1470 /* Shuffle the decrypted data using a custom routine */
1471 DoShuffle( &shuffle, p_tmp, 4 );
1473 /* Copy this block back to p_buffer */
1474 memcpy( p_buffer, p_tmp, 16 );
1479 if( i_remaining >= 4 )
1481 REVERSE( p_buffer, i_remaining / 4 );
1482 DoShuffle( &shuffle, p_buffer, i_remaining / 4 );
1485 /* Phase 2: look for the user key in the generated data. I must admit I
1486 * do not understand what is going on here, because it almost
1487 * looks like we are browsing data that makes sense, even though
1488 * the DoShuffle() part made it completely meaningless. */
1491 REVERSE( p_sci_data + 5, 1 );
1492 i = U32_AT( p_sci_data + 5 );
1493 i_sci_size -= 22 * sizeof(uint32_t);
1494 p_sci1 = p_sci_data + 22;
1497 while( i_sci_size >= 20 && i > 0 )
1499 if( p_sci0 == NULL )
1501 i_sci_size -= 18 * sizeof(uint32_t);
1502 if( i_sci_size < 20 )
1508 REVERSE( p_sci1 + 17, 1 );
1509 y = U32_AT( p_sci1 + 17 );
1520 i_user = U32_AT( p_sci0 );
1521 i_key = U32_AT( p_sci1 );
1522 REVERSE( &i_user, 1 );
1523 REVERSE( &i_key, 1 );
1524 if( i_user == p_drms->i_user && ( ( i_key == p_drms->i_key ) ||
1525 ( !p_drms->i_key && ( p_sci1 == (p_sci0 + 18) ) ) ) )
1527 memcpy( p_user_key, p_sci1 + 1, 16 );
1528 REVERSE( p_sci1 + 1, 4 );
1529 WriteUserKey( p_drms, p_sci1 + 1 );
1536 i_sci_size -= 5 * sizeof(uint32_t);
1544 /*****************************************************************************
1545 * GetSCIData: get SCI data from "SC Info.sidb"
1546 *****************************************************************************
1547 * Read SCI data from "\Apple Computer\iTunes\SC Info\SC Info.sidb"
1548 *****************************************************************************/
1549 static int GetSCIData( char *psz_ipod, uint32_t **pp_sci,
1550 uint32_t *pi_sci_size )
1553 char *psz_path = NULL;
1554 char p_tmp[ 4 * PATH_MAX ];
1557 if( psz_ipod == NULL )
1560 const char *SCIfile =
1561 "\\Apple Computer\\iTunes\\SC Info\\SC Info.sidb";
1562 strncpy(p_tmp, config_GetConfDir(), sizeof(p_tmp -1));
1563 if( strlen( p_tmp ) + strlen( SCIfile ) >= PATH_MAX )
1565 strcat(p_tmp, SCIfile);
1566 p_tmp[sizeof( p_tmp ) - 1] = '\0';
1572 #define ISCINFO "iSCInfo"
1573 if( strstr( psz_ipod, ISCINFO ) == NULL )
1575 snprintf( p_tmp, sizeof(p_tmp) - 1,
1576 "%s/iPod_Control/iTunes/" ISCINFO "2", psz_ipod );
1581 psz_path = psz_ipod;
1585 if( psz_path == NULL )
1590 file = vlc_fopen( psz_path, "rb" );
1595 if( !fstat( fileno( file ), &st ) && st.st_size >= 4 )
1597 *pp_sci = malloc( st.st_size );
1598 if( *pp_sci != NULL )
1600 if( fread( *pp_sci, 1, st.st_size,
1601 file ) == (size_t)st.st_size )
1603 *pi_sci_size = st.st_size;
1608 free( (void *)*pp_sci );
1620 /*****************************************************************************
1621 * HashSystemInfo: hash system information
1622 *****************************************************************************
1623 * This function computes the MD5 hash of the C: hard drive serial number,
1624 * BIOS version, CPU type and Windows version.
1625 *****************************************************************************/
1626 static int HashSystemInfo( uint32_t *p_system_hash )
1638 static const LPCTSTR p_reg_keys[ 3 ][ 2 ] =
1641 _T("HARDWARE\\DESCRIPTION\\System"),
1642 _T("SystemBiosVersion")
1646 _T("HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0"),
1647 _T("ProcessorNameString")
1651 _T("SOFTWARE\\Microsoft\\Windows\\CurrentVersion"),
1658 AddMD5( &md5, "cache-control", 13 );
1659 AddMD5( &md5, "Ethernet", 8 );
1661 GetVolumeInformation( _T("C:\\"), NULL, 0, &i_serial,
1662 NULL, NULL, NULL, 0 );
1663 AddMD5( &md5, (const uint8_t *)&i_serial, 4 );
1665 for( i = 0; i < sizeof(p_reg_keys) / sizeof(p_reg_keys[ 0 ]); i++ )
1667 if( RegOpenKeyEx( HKEY_LOCAL_MACHINE, p_reg_keys[ i ][ 0 ],
1668 0, KEY_READ, &i_key ) != ERROR_SUCCESS )
1673 if( RegQueryValueEx( i_key, p_reg_keys[ i ][ 1 ],
1674 NULL, NULL, NULL, &i_size ) != ERROR_SUCCESS )
1676 RegCloseKey( i_key );
1680 p_reg_buf = malloc( i_size );
1682 if( p_reg_buf != NULL )
1684 if( RegQueryValueEx( i_key, p_reg_keys[ i ][ 1 ],
1685 NULL, NULL, p_reg_buf,
1686 &i_size ) == ERROR_SUCCESS )
1688 AddMD5( &md5, (const uint8_t *)p_reg_buf, i_size );
1694 RegCloseKey( i_key );
1703 memcpy( p_system_hash, md5.p_digest, 16 );
1708 /*****************************************************************************
1709 * GetiPodID: Get iPod ID
1710 *****************************************************************************
1711 * This function gets the iPod ID.
1712 *****************************************************************************/
1713 static int GetiPodID( int64_t *p_ipod_id )
1717 #define PROD_NAME "iPod"
1718 #define VENDOR_NAME "Apple Computer, Inc."
1720 char *psz_ipod_id = getenv( "IPODID" );
1721 if( psz_ipod_id != NULL )
1723 *p_ipod_id = strtoll( psz_ipod_id, NULL, 16 );
1731 io_iterator_t iterator;
1732 CFMutableDictionaryRef match_dic;
1733 CFMutableDictionaryRef smatch_dic;
1735 if( IOMasterPort( MACH_PORT_NULL, &port ) == KERN_SUCCESS )
1737 smatch_dic = IOServiceMatching( "IOFireWireUnit" );
1738 match_dic = CFDictionaryCreateMutable( kCFAllocatorDefault, 0,
1739 &kCFTypeDictionaryKeyCallBacks,
1740 &kCFTypeDictionaryValueCallBacks );
1742 if( smatch_dic != NULL && match_dic != NULL )
1744 CFDictionarySetValue( smatch_dic,
1745 CFSTR("FireWire Vendor Name"),
1746 CFSTR(VENDOR_NAME) );
1747 CFDictionarySetValue( smatch_dic,
1748 CFSTR("FireWire Product Name"),
1751 CFDictionarySetValue( match_dic,
1752 CFSTR(kIOPropertyMatchKey),
1754 CFRelease( smatch_dic );
1756 if( IOServiceGetMatchingServices( port, match_dic,
1757 &iterator ) == KERN_SUCCESS )
1759 while( ( device = IOIteratorNext( iterator ) ) != 0 )
1761 value = IORegistryEntryCreateCFProperty( device,
1762 CFSTR("GUID"), kCFAllocatorDefault, kNilOptions );
1766 if( CFGetTypeID( value ) == CFNumberGetTypeID() )
1769 CFNumberGetValue( (CFNumberRef)value,
1770 kCFNumberLongLongType,
1772 *p_ipod_id = i_ipod_id;
1779 IOObjectRelease( device );
1784 IOObjectRelease( iterator );
1790 CFRelease( match_dic );
1792 CFRelease( smatch_dic );
1796 mach_port_deallocate( mach_task_self(), port );
1803 #else /* !defined( UNDER_CE ) */
1805 void *drms_alloc( const char *psz_homedir ){ return NULL; }
1806 void drms_free( void *a ){}
1807 void drms_decrypt( void *a, uint32_t *b, uint32_t c, uint32_t *k ){}
1808 void drms_get_p_key( void *p_drms, uint32_t *p_key ){}
1809 int drms_init( void *a, uint32_t b, uint8_t *c, uint32_t d ){ return -1; }
1811 #endif /* defined( UNDER_CE ) */