예제 #1
0
        public static bool PatchToSupportBigASMHacks()
        {
            bool autorw = Program.m_ROM.CanRW();

            if (!autorw)
            {
                Program.m_ROM.BeginRW();
            }
            if (Program.m_ROM.Read32(0x6590) != 0) //the patch makes this not 0
            {
                if (!autorw)
                {
                    Program.m_ROM.EndRW();
                }
                return(true);
            }
            if (!autorw)
            {
                Program.m_ROM.EndRW();
            }

            if (MessageBox.Show("This requires the ROM to be further patched. " +
                                "Continue with the patch?", "Table Shifting Patch", MessageBoxButtons.YesNo) == DialogResult.No)
            {
                return(false);
            }

            if (!autorw)
            {
                Program.m_ROM.BeginRW();
            }
            NitroOverlay ov2 = new NitroOverlay(Program.m_ROM, 2);

            //Move the ACTOR_SPAWN_TABLE so it can expand
            Program.m_ROM.WriteBlock(0x6590, Program.m_ROM.ReadBlock(0x90864, 0x61c));
            Program.m_ROM.WriteBlock(0x90864, new byte[0x61c]);

            //Adjust pointers
            Program.m_ROM.Write32(0x1a198, 0x02006590);

            //Move the OBJ_TO_ACTOR_TABLE so it can expand
            Program.m_ROM.WriteBlock(0x4b00, ov2.ReadBlock(0x0210cbf4 - ov2.GetRAMAddr(), 0x28c));
            ov2.WriteBlock(0x0210cbf4 - ov2.GetRAMAddr(), new byte[0x28c]);

            //Adjust pointers
            ov2.Write32(0x020fe890 - ov2.GetRAMAddr(), 0x02004b00);
            ov2.Write32(0x020fe958 - ov2.GetRAMAddr(), 0x02004b00);
            ov2.Write32(0x020fea44 - ov2.GetRAMAddr(), 0x02004b00);

            //Add the dynamic library loading and cleanup code
            Program.m_ROM.WriteBlock(0x90864, Properties.Resources.dynamic_library_loader);

            //Add the hooks (by replacing LoadObjBankOverlays())
            Program.m_ROM.WriteBlock(0x2df70, Properties.Resources.static_overlay_loader);

            if (!autorw)
            {
                Program.m_ROM.EndRW();
            }
            ov2.SaveChanges();

            return(true);
        }
예제 #2
0
        public void makeOverlay(uint overlayID)
        {
            FileInfo f = new FileInfo(romdir.FullName + "/newcode.bin");

            if (!f.Exists)
            {
                return;
            }
            FileStream   fs      = f.OpenRead();
            FileInfo     symFile = new FileInfo(romdir.FullName + "/newcode.sym");
            StreamReader symStr  = symFile.OpenText();

            byte[] newdata = new byte[fs.Length];
            fs.Read(newdata, 0, (int)fs.Length);
            fs.Close();


            BinaryWriter newOvl  = new BinaryWriter(new MemoryStream());
            BinaryReader newOvlR = new BinaryReader(newOvl.BaseStream);

            try
            {
                newOvl.Write(newdata);
                alignStream(newOvl.BaseStream, 4);

                uint staticInitCount = 0;

                while (!symStr.EndOfStream)
                {
                    string line = symStr.ReadLine();

                    if (line.Contains("_Z4initv")) //gcc name mangling of init()
                    {
                        uint addr = (uint)parseHex(line.Substring(0, 8));
                        newOvl.Write(addr);
                        ++staticInitCount;
                    }
                }

                /*if (newOvl.BaseStream.Length > 0x4d20)
                 *  throw new InvalidDataException
                 *      ("The overlay must have no more than 19776 bytes; this one will have " + newOvl.BaseStream.Length);*/

                NitroOverlay ovl = new NitroOverlay(Program.m_ROM, overlayID);
                newOvl.BaseStream.Position = 0;
                ovl.SetInitializer(ovl.GetRAMAddr() + (uint)newOvl.BaseStream.Length - 4 * staticInitCount,
                                   4 * staticInitCount);
                ovl.SetSize((uint)newOvl.BaseStream.Length);
                ovl.WriteBlock(0, newOvlR.ReadBytes((int)newOvl.BaseStream.Length));
                ovl.SaveChanges();
            }
            catch (Exception ex)
            {
                new ExceptionMessageBox("Error", ex).ShowDialog();
                return;
            }
            finally
            {
                symStr.Close();
                newOvl.Dispose();
                newOvlR.Close();
            }
        }