示例#1
0
        public int creatergh2ecc(string filename, string outputfolder, ref ProgressBar pb, string cpukey)
        {
            eccs dt = new eccs();

            byte[] data;
            int    layout;
            bool   rgh2 = false;

            bool sts = objAlphaPattern.IsMatch(cpukey);

            if (variables.rgh2 && !String.IsNullOrEmpty(cpukey) && sts)
            {
                rgh2 = true;
            }

            long   size      = 0;
            string imagefile = filename;

            System.Text.ASCIIEncoding encoding = new System.Text.ASCIIEncoding();
            if (variables.debugme)
            {
                Console.WriteLine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location));
            }

            string pathforit    = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);
            string cdrgh2file   = Path.Combine(pathforit, @"common/cdxell/CDRGH2");
            string cdfile       = Path.Combine(pathforit, @"common/cdxell/CD");
            string cdjasperfile = Path.Combine(pathforit, @"common/cdxell/CDjasper");

            /// nand image
            {
                byte[] bbimage = Nand.BadBlock.find_bad_blocks_X(imagefile, 0x50);
                data    = Oper.returnportion(ref bbimage, 0, 1 * 1024 * 1024);
                bbimage = null;

                layout = Nand.Nand.getConsole(new Nand.PrivateN(filename)).Layout;

                if (Oper.allsame(Oper.returnportion(ref data, 0x210, 0x200), 0xFF))
                {
                    Console.WriteLine("Invalid Image");
                    return(-1);
                }
                Console.WriteLine("* unpacking flash image, ....");
                unpack_base_image_ecc(ref data, ref pb, ref dt);
                dt.CB_A_crypted = dt.CB_A;
                dt.SMC          = decrypt_SMC(dt.SMC);
            }

            creatergh2eccinit(ref dt);
            ///
            ///Finished Loading images
            ///
            data = null;
            if (dt.CD_plain == null)
            {
                return(-1);
            }
            if (dt.SMC == null)
            {
                return(-1);
            }
            ///
            Console.WriteLine(" * we found the following parts: ");
            Console.WriteLine("SMC: {0}.{1}", (dt.SMC[0x101].ToString()), (dt.SMC[0x102]).ToString());
            ///
            if (dt.CB_A != null)
            {
                Console.WriteLine("CB_A: {0}", Oper.ByteArrayToInt(build(dt.CB_A)));
            }
            else
            {
                Console.WriteLine("CB_A: missing");
            }
            if (dt.CB_B != null)
            {
                Console.WriteLine("CB_B: {0}", Oper.ByteArrayToInt(build(dt.CB_B)));
            }
            else
            {
                Console.WriteLine("CB_B: missing");
            }

            ///
            ///
            int[] rghcbs  = { 6753, 6752, 5773, 4578, 4577, 5772, 9230 };
            int[] rgh1cbs = { 9188 };
            //if (rghcbs.Contains(bytearray_to_int(build(CB_A)))) rgh2 = true;
            if (dt.CB_B != null && !rgh1cbs.Contains(Oper.ByteArrayToInt(build(dt.CB_B))))
            {
                rgh2 = true;
            }
            ///
            ///
            string c;

            if (rgh2)
            {
                dt.CD_plain = Oper.openfile(cdrgh2file, ref size, 1 * 1024 * 1024);
                if (dt.CD_plain == null)
                {
                    return(-1);
                }
                if (dt.CD != null)
                {
                    Console.WriteLine("CD (image): {0}", Oper.ByteArrayToInt(build(dt.CD)));
                }
                else
                {
                    Console.WriteLine("CD (image): missing");
                }
                if (dt.CD_plain != null)
                {
                    Console.WriteLine("CD (decrypted): {0}", Oper.ByteArrayToInt(build(dt.CD_plain)));
                }
                else
                {
                    Console.WriteLine("CD (decrypted): missing");
                }
                byte[] CB_A_img_RAND = { };
                CB_A_img_RAND = Oper.returnportion(ref dt.CB_A_crypted, 0x10, 0x10);
                ///
                byte[] CB_A_img = Nand.Nand.decrypt_CB(dt.CB_A_crypted);
                Console.WriteLine(" * checking required versions...");

                int[] zephyr_builds   = { 4578, 4577, 4575, 4560, 4576 };
                int[] falcon_builds   = { 5771, 5772, 5773 };
                int[] jasper_builds   = { 6750, 6752, 6753, 6754 };
                int[] trinity_builds  = { 9188, 9230, 9231 };
                int[] corona_builds   = { 13121, 13180 };
                int[] xor_hack_builds = { 9230, 9231, 5773, 6753, 6754, 4575, 4560, 13180 };
                int[] patch_builds    = { 5772, 6752, 9188, 13121 };

                if (!zephyr_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))) &&
                    !falcon_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))) &&
                    !jasper_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))) &&
                    !corona_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))) &&
                    !trinity_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    return(-3);
                }
                if (!xor_hack_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))) &&
                    !patch_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))) && String.IsNullOrEmpty(cpukey))
                {
                    return(-4);
                }

                Console.WriteLine("ok");

                Console.WriteLine(" * patching SMC...");
                dt.SMC = patch_SMC(dt.SMC);

                Console.WriteLine(" * Replacing CD...");
                dt.CD       = dt.CD_plain;
                dt.CD_plain = null;

                string cbapath = "", cbbpath = "";

                if (falcon_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    cbapath = Path.Combine(pathforit, "common\\CB\\CB_A.5772.bin");
                    cbbpath = Path.Combine(pathforit, "common\\CB\\CB_B.5772.bin");
                }
                else if (jasper_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    cbapath = Path.Combine(pathforit, "common\\CB\\CB_A.6752.bin");
                    cbbpath = Path.Combine(pathforit, "common\\CB\\CB_B.6752.bin");
                }
                else if (trinity_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    cbapath = Path.Combine(pathforit, "common\\CB\\CB_A.9188.bin");
                    cbbpath = Path.Combine(pathforit, "common\\CB\\CB_B.9188.bin");
                }
                else if (zephyr_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    cbapath = Path.Combine(pathforit, "common\\CB\\CB_A.4577.bin");
                    cbbpath = Path.Combine(pathforit, "common\\CB\\CB_B.4577.bin");
                }
                else if (corona_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    cbapath = Path.Combine(pathforit, "common\\CB\\CB_A.13121.bin");
                    cbbpath = Path.Combine(pathforit, "common\\CB\\CB_B.13121.bin");
                }

                c      = "RGH2 2stage CB img";
                cpukey = "";
wtf:
                if (String.IsNullOrEmpty(cpukey))
                {
                    if (patch_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_B))))
                    {
                        Console.WriteLine(" * patching CB_B...");
                        dt.CB_B = patch_CB(dt.CB_B);
                        dt.CB_A = dt.CB_A_crypted;
                    }
                    else if (xor_hack_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_B))))
                    {
                        Console.WriteLine();
                        Console.WriteLine("* XOR HACK NEEDED FOR CB {0}", Oper.ByteArrayToInt(build(dt.CB_B)));

                        byte[] CB_B_plain = Oper.openfile(Path.Combine(variables.pathforit, @"common\CB\CB_B." + Oper.ByteArrayToInt(build(dt.CB_B)) + ".bin"), ref size, 0);
                        if (CB_B_plain == null)
                        {
                            Console.WriteLine("Failed to open CB_B.{0}.bin", Oper.ByteArrayToInt(build(dt.CB_B))); return(5);
                        }

                        byte[] CB_B_patched = Oper.openfile(cbbpath, ref size, 0);
                        if (CB_B_patched == null)
                        {
                            Console.WriteLine("Failed to open {0}", cbbpath); return(5);
                        }
                        Console.WriteLine(" * patching CB_B...");

                        CB_B_patched = patch_CB(CB_B_patched);
                        if (CB_B_patched == null)
                        {
                            Console.WriteLine("Failed to patch the CB_B"); return(5);
                        }
                        Console.WriteLine(" * Applying XOR Hack to CB_B {0}", Oper.ByteArrayToInt(build(dt.CB_B)));

                        dt.CB_B = xor_hack(dt.CB_B, CB_B_plain, CB_B_patched);
                        Console.WriteLine(" * Replacing CB_A {0} with {1}", Oper.ByteArrayToInt(build(dt.CB_A)), Oper.ByteArrayToInt(build(CB_B_patched)));

                        dt.CB_A = Oper.openfile(cbapath, ref size, 0);
                        if (dt.CB_A == null)
                        {
                            Console.WriteLine("Failed to open {0}", cbapath); return(5);
                        }
                        byte[] CB_A_key = { };
                        dt.CB_A = Nand.Nand.encrypt_CB(dt.CB_A, CB_A_img_RAND, ref CB_A_key);
                    }
                }
                else
                {
                    if (MessageBox.Show("Are you sure you want to build a new bootloader chain?", "Bootloader Chain", MessageBoxButtons.YesNo, MessageBoxIcon.Exclamation) == DialogResult.No)
                    {
                        cpukey = "";
                        goto wtf;
                    }
                    Console.WriteLine("\n * Building new bootloader chain using cpu_key: {0}", cpukey);

                    dt.CB_A = Oper.openfile(cbapath, ref size, 0);
                    dt.CB_B = Oper.openfile(cbbpath, ref size, 0);

                    dt.CB_B = patch_CB(dt.CB_B);

                    byte[] CB_A_key = { };
                    dt.CB_A = Nand.Nand.encrypt_CB(dt.CB_A, CB_A_img_RAND, ref CB_A_key);
                    dt.CB_B = Nand.Nand.encrypt_CB_cpukey(dt.CB_B, CB_A_key, Oper.StringToByteArray(cpukey));
                }
                ///
                ///
                ///
                Console.WriteLine(" * constructing new image...");

                c = c + ", CB=" + Oper.ByteArrayToInt(build(dt.CB_A));
            }
            else
            {
                if (dt.CD != null)
                {
                    Console.WriteLine("CD (image): {0}", Oper.ByteArrayToInt(build(dt.CD)));
                }
                else
                {
                    Console.WriteLine("CD (image): missing");
                }
                if (dt.CD_plain != null)
                {
                    Console.WriteLine("CD (decrypted): {0}", Oper.ByteArrayToInt(build(dt.CD_plain)));
                }
                else
                {
                    Console.WriteLine("CD (decrypted): missing");
                }
                int[] jasper_builds = { 6750, 6752, 6753 };
                if (jasper_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    dt.CD_plain = Oper.openfile(cdjasperfile, ref size, 1 * 1024 * 1024);
                }
                if (dt.CD_plain == null)
                {
                    return(-1);
                }
                byte[] CB_A_img_RAND = { };
                if (!donor)
                {
                    CB_A_img_RAND = Oper.returnportion(ref dt.CB_A_crypted, 0x10, 0x10);
                }
                ///
                if (Oper.ByteArrayToInt(build(dt.CB_A)) >= 1888 && Oper.ByteArrayToInt(build(dt.CB_A)) <= 1940 || Oper.ByteArrayToInt(build(dt.CB_A)) == 7373 || Oper.ByteArrayToInt(build(dt.CB_A)) == 8192)
                {
                    Console.WriteLine(" * using donor CB");
                    dt.CB_A_crypted = null;
                    if (MessageBox.Show("There have been various reports that using a different bootloader improves the glitch speeds on xenon. Click Yes to use the 7375 Bootloader or Click No to use the 1940 one.", "Choose CB", MessageBoxButtons.YesNo, MessageBoxIcon.Exclamation) == DialogResult.Yes)
                    {
                        dt.CB_A = Oper.openfile(Path.Combine(variables.pathforit, @"common\CB\CB_A.7375.bin"), ref size, 0);
                    }
                    else
                    {
                        dt.CB_A = Oper.openfile(Path.Combine(variables.pathforit, @"common\CB\CB_A.1940.bin"), ref size, 0);
                    }
                    if (dt.CB_A == null)
                    {
                        Console.WriteLine("Failed to open CB"); return(5);
                    }
                    dt.CB_B     = null;
                    dt.CD_plain = Oper.openfile(cdfile, ref size, 1 * 1024 * 1024);
                    if (dt.CD_plain == null)
                    {
                        return(-1);
                    }
                }
                ///
                ///
                ///
                int[] xenon_builds  = { 1923, 7375 };
                int[] zephyr_builds = { 4578, 4579, 4575 };
                int[] falcon_builds = { 5771, 5772, 5773 };
                //int[] jasper_builds = { 6750, 6752, 6753 };
                int[] trinity_builds  = { 9188, 9230 };
                int[] corona_builds   = { 13121, 13180 };
                int[] slim_builds     = { 9188, 9230, 13121 };
                int[] xor_hack_builds = { 9230, 5773, 6753, 4575 };

                if (!donor)
                {
                    if ((dt.CB_A_crypted != null) && (Oper.ByteArrayToInt(build(dt.CB_A)) != 9230))
                    {
                        dt.CB_A = Nand.Nand.decrypt_CB(dt.CB_A_crypted);
                        if (dt.CB_A == null)
                        {
                            Console.WriteLine("Error");
                        }
                    }
                }
                if (dt.CB_B != null && !slim_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    Console.WriteLine("Not supported yet");
                    return(5);
                }


                if (trinity_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    Console.WriteLine(" * this image will be valid *only* for: trinity (slim)");
                }
                else if (corona_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    Console.WriteLine(" * this image will be valid *only* for: corona");
                }
                else if (zephyr_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    Console.WriteLine(" * this image will be valid *only* for: zephyr");
                }
                else if (falcon_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    Console.WriteLine(" * this image will be valid *only* for: falcon");
                }
                else if (jasper_builds.Contains(Oper.ByteArrayToInt(build(dt.CB_A))))
                {
                    if (donor)
                    {
                        Console.WriteLine(" * this image will be valid *only* for: jasper (CB_6751)");
                    }
                    else
                    {
                        Console.WriteLine(" * this image will be valid *only* for: jasper (CB_6750)");
                    }
                }
                else
                {
                    Console.WriteLine(" * this image will be valid *only* for: xenon");
                }

                Console.WriteLine(" * patching SMC...");
                dt.SMC = patch_SMC(dt.SMC);

                dt.CD       = dt.CD_plain;
                dt.CD_plain = null;

                if (dt.CB_B != null)
                {
                    Console.WriteLine(" * patching CB_B...");
                    dt.CB_B = patch_CB(dt.CB_B);
                    c       = "patched CB img";
                }
                else
                {
                    //Nand.savefile(CB_A, "CB_f.bin");
                    Console.WriteLine(" * zero-pairing...");
                    for (int bytes = 0x20; bytes < 0x40; bytes++)
                    {
                        dt.CB_A[bytes] = 0x00;
                    }
                    c = "zeropair image";
                }
                if (!Directory.Exists(Path.Combine(Directory.GetCurrentDirectory(), "output")))
                {
                    Directory.CreateDirectory(Path.Combine(Directory.GetCurrentDirectory(), "output"));
                }
                ///
                ///
                ///
                Console.WriteLine(" * constructing new image...");
                byte[] random = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };

                c = c + ", version=01, CB=" + Oper.ByteArrayToInt(build(dt.CB_A));

                if (dt.CB_B == null)
                {
                    byte[] CB_A_key = { };
                    //Nand.savefile(CB_A, "CB_d.bin");
                    dt.CB_A = Nand.Nand.encrypt_CB(dt.CB_A, random, ref CB_A_key);
                    //Nand.savefile(CB_A, "CB_e.bin");
                    //Console.WriteLine(ByteArrayToString(CB_A_key));
                    dt.CD = Nand.Nand.encrypt_CD(dt.CD, random, CB_A_key);
                }
            }

            createrghheader(ref dt, c);
            ///
            dt.SMC = encrypt_SMC(dt.SMC);
            ///
            ///
            byte[] newXell = dt.Xell;
            if (dt.Xell.Length <= 256 * 1024)
            {
                Console.WriteLine(" * No separate recovery Xell available!");
                newXell = Oper.concatByteArrays(dt.Xell, dt.Xell, dt.Xell.Length, dt.Xell.Length);
            }
            dt.Xell = null;
            ///
            /// Start of image creation
            ///
            byte[] Final = { };
            Console.WriteLine(" * Flash Layout:");
            Final = addtoflash(Oper.returnportion(ref dt.Header, 0x00, 0x200), Final, "Header", 0x00, 0x200);
            Final = padto_v2(Final, 0x4000 - dt.SMC.Length);
            ///
            Final       = addtoflash(dt.SMC, Final, "SMC", Final.Length, dt.SMC.Length);
            dt.SMC      = null;
            Final       = addtoflash(dt.Keyvault, Final, "Keyvault", Final.Length, dt.Keyvault.Length);
            dt.Keyvault = null;
            ///
            if (dt.CB_B != null)
            {
                if (!rgh2)
                {
                    Final = addtoflash(dt.CB_A_crypted, Final, "CB_A " + Oper.ByteArrayToInt(build(dt.CB_A)), Final.Length, dt.CB_A_crypted.Length);
                }
                else
                {
                    Final = addtoflash(dt.CB_A, Final, "CB_A " + Oper.ByteArrayToInt(build(dt.CB_A)), Final.Length, dt.CB_A.Length);
                }
                Final = addtoflash(dt.CB_B, Final, "CB_B " + Oper.ByteArrayToInt(build(dt.CB_B)), Final.Length, dt.CB_B.Length);
            }
            else
            {
                Final = addtoflash(dt.CB_A, Final, "CB_A " + Oper.ByteArrayToInt(build(dt.CB_A)), Final.Length, dt.CB_A.Length);
            }
            dt.CB_A = null; dt.CB_B = null; dt.CB_A_crypted = null;
            ///
            Final = addtoflash(dt.CD, Final, "CD " + Oper.ByteArrayToInt(build(dt.CD)), Final.Length, dt.CD.Length);
            dt.CD = null;
            Final = padto_v2(Final, XELL_BASE_FLASH);
            ///
            Final   = addtoflash(Oper.returnportion(ref newXell, 0, 256 * 1024), Final, "Xell (backup)", Final.Length, 256 * 1024);
            Final   = addtoflash(Oper.returnportion(ref newXell, 256 * 1024, newXell.Length - (256 * 1024)), Final, "Xell (main)", Final.Length, newXell.Length - (256 * 1024));
            newXell = null;
            ///
            if (variables.extractfiles || variables.debugme)
            {
                Oper.savefile(Final, Path.Combine(outputfolder, "image_no.ecc"));
            }

            if (hasecc)
            {
                Console.Write(" * Encoding ECC...");
                Final = Nand.Nand.addecc_v2(Final, true, 0, layout);
            }
            else
            {
                Console.WriteLine("NOT adding Spare Data");
            }

            Console.WriteLine("Done!");
            ///
            Oper.savefile(Final, Path.Combine(outputfolder, "image_00000000.ecc"));
            DirectoryInfo dinfo = new DirectoryInfo(outputfolder);

            Console.WriteLine("------------- Written into {0}\n", Path.Combine(dinfo.Name, "image_00000000.ecc"));
            pb.Value = pb.Maximum;
            return(1);
        }