示例#1
0
        public static byte[][] GenerateSubTables()
        {
            var rows = new byte[0x100][];

            for (int i = 0; i < 0x100; i++)
            {
                rows[i] = CriHcaKey.CreateRandomRow((byte)i);
            }

            return(rows);
        }
示例#2
0
        /// <summary>
        /// Finds possible tables used to shuffle the decryption table with a known upper seed
        /// </summary>
        /// <remarks>
        /// As in <see cref="FilterPossibleShufflersWithByte2Zeros"/>, we search each possible shuffle table
        /// to find one with at least 9 rows of all zeros. The difference is this time we know which specific
        /// rows need to be all zeros, the rows containing the upper nibbles 7 through 0xf.
        /// The two shuffler IDs correspond to the positions of the bytes 0 or 0xFF in the table, so this is
        /// used to further filter the possible shufflers.
        /// </remarks>
        public void FindShuffleTable()
        {
            byte[] upperSubTable     = SubTables[UpperSeed];
            byte[] inverseSubTable   = CriHcaKey.InvertTable(upperSubTable);
            int[]  count             = new int[16];
            var    possibleShufflers = new List <ShufflerId>();
            byte   row0 = inverseSubTable[0];
            byte   rowF = inverseSubTable[0xf];

            foreach (var s in PossibleShufflers)
            {
                // Count the number of zeros in each row
                Array.Clear(count, 0, 16);
                foreach (byte v in Byte2Zeros)
                {
                    int unshuffledUpperNibble = BackwardShuffle[s.Pos1][s.Pos2][v] >> 4;
                    count[unshuffledUpperNibble]++;
                }
                bool valid = true;

                // Invalidate the tables without the required empty rows
                for (int i = 0; i < upperSubTable.Length; i++)
                {
                    for (int j = 7; j < 15; j++)
                    {
                        if (count[inverseSubTable[j]] < 16)
                        {
                            valid = false;
                        }
                    }
                    if (count[inverseSubTable[15]] < 15)
                    {
                        valid = false;
                    }
                }

                // Invalidate the tables without the bytes 0x00 and 0xFF in their proper rows
                if ((s.Pos1 >> 4 != row0 && s.Pos1 >> 4 != rowF) ||
                    (s.Pos2 >> 4 != row0 && s.Pos2 >> 4 != rowF) ||
                    s.Pos1 >> 4 == s.Pos2 >> 4)
                {
                    valid = false;
                }

                if (valid)
                {
                    possibleShufflers.Add(s);
                }
            }
            PossibleShufflers = possibleShufflers;
        }
示例#3
0
        public static byte[] GenerateShuffler(int a, int b, bool backward)
        {
            byte[] table  = new byte[256];
            byte   x      = 0;
            int    outPos = 1;

            for (int i = 0; i < 256; i++)
            {
                x += 17;
                if (x != a && x != b)
                {
                    table[outPos++] = x;
                }
            }

            return(backward ? table : CriHcaKey.InvertTable(table));
        }