Exemple #1
0
        private static void TriangleMapParse_cmd04(ROM rom, TriangleMap map, TriangleMapParseState state)
        {
            state.vertexLoadCmd = (UInt64)rom.Read64();
            byte vertexDesc = rom.Read8(1);

            byte  vertexCount            = (byte)(((vertexDesc & 0xF0) >> 4) + 1);
            byte  vertexOffset           = (byte)((vertexDesc & 0x0F));
            Int32 vertexSegmentedAddress = rom.Read32(4);

            state.segmentedVertexBufferAddress = vertexSegmentedAddress;

            Int32 romPtr = rom.GetROMAddress(vertexSegmentedAddress);

            if (romPtr == -1)
            {
                throw new ArgumentException("Invalid segmented address!");
            }

            rom.PushOffset(romPtr);
            for (int vertex = vertexOffset; vertex < vertexCount; vertex++)
            {
                Int64 lo = rom.Read64();
                Int64 hi = rom.Read64(8);

                state.vbuf[vertex]         = new Vertex((UInt64)lo, (UInt64)hi);
                state.vbufRomStart[vertex] = rom.offset;
                state.scrollBuf[vertex]    = FindMatchingScroll(state.scrolls, vertexSegmentedAddress, state.td);

                rom.AddOffset(0x10);
                vertexSegmentedAddress += 0x10;
            }
            rom.PopOffset();
        }
Exemple #2
0
        private static void FixParse_cmdB9(ROM rom, DisplayListRegion region, RegionFixState state)
        {
            if (state.config.disableFog)
            {
                rom.Write64(0);
                return;
            }

            if (!state.config.fixOtherMode)
            {
                return;
            }

            if (!region.isFogEnabled)
            {
                return;
            }

            if ((ulong)rom.Read64(-8) != 0xBA00140200000000 || (ulong)rom.Read64(8) != 0xB600000000010000)
            {
                return;
            }

            UInt64 B9Cmd = OtherMode.GetB9Cmd(region.layer);

            if (B9Cmd != 0)
            {
                rom.Write64(B9Cmd);
            }
        }
Exemple #3
0
        private static void OptimizeParse_cmd04(ROM rom, DisplayListRegion region, RegionOptimizeState state)
        {
            // initial state
            if (state.last04Cmd == 0)
            {
                state.last04Cmd = rom.Read64();
                return;
            }

            Int64 cmd = rom.Read64();

            // if current 04 loads the same vertices, remove current cmd
            if (cmd == state.last04Cmd)
            {
                rom.Write64(0);
                return;
            }

            // new vertices are being loaded, update the thing
            state.last04Cmd = cmd;

            // if previous cmd is 0x04, it will be overriden by current 04 anyways
            if (rom.Read8(-8) == 0x04)
            {
                rom.Write64(0, -8);
            }
        }
Exemple #4
0
        private static void RelocationParse_cmdB9(ROM rom, RelocationTable table, DisplayListRegion region)
        {
            if (!region.DLFixesNeeded)
            {
                return;
            }

            if (!region.isFogEnabled)
            {
                return;
            }

            if ((ulong)rom.Read64(-8) != 0xBA00140200000000)
            {
                return;
            }

            if (region.layer == 1)
            {
                rom.Write64(0xB900031D00552078);
            }
            if (region.layer == 4)
            {
                rom.Write64(0xB900031D00443078);
            }
            if (region.layer == 5)
            {
                rom.Write64(0xB900031D005049D8);
            }
        }
Exemple #5
0
 private static void RegionParse_cmdB9(ROM rom, List <Region> regions, RegionParseState state)
 {
     if (state.B9cmdfirst == 0)
     {
         state.B9cmdfirst = rom.Read64();
     }
 }
Exemple #6
0
        private static void OptimizeParse_cmdB7(ROM rom, DisplayListRegion region, RegionOptimizeState state)
        {
            // Very failsafe approach
            state.lastB6Cmd = 0;

            Int64 cmd = rom.Read64();

            // Basically NOP
            if ((UInt64)cmd == 0xB700000000000000)
            {
                rom.Write64(0);
                return;
            }


            // initial state
            if (state.lastB7Cmd == 0)
            {
                state.lastB7Cmd = cmd;
                return;
            }

            // if current cmd loads the same, remove current cmd
            if (cmd == state.lastB7Cmd)
            {
                rom.Write64(0);
                return;
            }
        }
Exemple #7
0
 private static void RegionParse_cmdFC(ROM rom, List <Region> regions, RegionParseState state)
 {
     if (state.FCcmd == -1)
     {
         state.FCcmd = rom.Read64();
     }
     state.FCCount++;
 }
Exemple #8
0
        private static void TriangleMapParse_common(ROM rom, TriangleMap map, TriangleMapParseState state)
        {
            switch (state.state)
            {
            case VisualMapParseStateCmd.Header:
                map.AddHeaderCmd((UInt64)rom.Read64());
                break;

            case VisualMapParseStateCmd.Texture:
                state.td.Add((UInt64)rom.Read64(), rom.GetSegmentedAddress(rom.offset));
                break;

            case VisualMapParseStateCmd.Footer:
                map.AddFooterCmd((UInt64)rom.Read64());
                break;
            }
        }
Exemple #9
0
        private static void TriangleMapParse_cmdBB(ROM rom, TriangleMap map, TriangleMapParseState state)
        {
            if ((UInt64)rom.Read64() == 0xBB000000FFFFFFFF)
            {
                state.state = VisualMapParseStateCmd.Footer;
            }

            TriangleMapParse_common(rom, map, state);
        }
Exemple #10
0
        public static void PerformVisualMapRebuild(ROM realRom, Region region, int maxDLLength)
        {
            // This is fake rom but it works anyways, just more convenient
            // Want to be safe with overwriting the whole display list
            ROM fakeRom = new ROM(region.data);
            VisualMapParseState state = new VisualMapParseState();

            DisplayListRegion dlRegion = (DisplayListRegion)region;
            VisualMap         map      = new VisualMap();

            byte curCmdIndex;

            do
            {
                curCmdIndex = fakeRom.Read8();
                VisualMapParserCmd func = visualMapParser[curCmdIndex];
                func(fakeRom, map, state);
                fakeRom.AddOffset(8);
            }while (fakeRom.offset < region.length);

            ROM visualMapROM    = new ROM(new byte[maxDLLength]);
            int visualMapLength = map.MakeF3D(visualMapROM);


            // Now write data to real rom + trimming
            // bzero
            fakeRom.offset = 0;
            realRom.PushOffset(region.romStart);
            {
                do
                {
                    realRom.Write64(0x0101010101010101);
                    realRom.AddOffset(8);
                    fakeRom.AddOffset(8);
                } while (fakeRom.offset < region.length);
            }
            realRom.PopOffset();

            visualMapROM.offset = 0;
            realRom.PushOffset(region.romStart);
            {
                int start = region.romStart;
                do
                {
                    Int64 cmd = visualMapROM.Read64();
                    visualMapROM.AddOffset(8);

                    realRom.Write64((ulong)cmd);
                    realRom.AddOffset(8);
                } while (visualMapROM.offset < visualMapLength);

                region.length = realRom.offset - start;
                region.data   = new byte[region.length];
                realRom.ReadData(region.romStart, region.length, region.data);
            }
            realRom.PopOffset();
        }
Exemple #11
0
        public static void PerformRegionOptimize(ROM realRom, Region region, FixConfig config)
        {
            // This is fake rom but it works anyways, just more convenient
            // Want to be safe with overwriting the whole display list
            ROM fakeRom = new ROM(region.data);
            RegionOptimizeState state = new RegionOptimizeState(config);

            DisplayListRegion dlRegion = (DisplayListRegion)region;

            byte curCmdIndex;

            do
            {
                curCmdIndex = fakeRom.Read8();
                OptimizeParserCmd func = optimizeParser[curCmdIndex];
                func(fakeRom, dlRegion, state);
                fakeRom.AddOffset(8);
            }while (fakeRom.offset < region.length);

            // Now write data to real rom + trimming
            // bzero
            fakeRom.offset = 0;
            realRom.PushOffset(region.romStart);
            {
                do
                {
                    realRom.Write64(0x0101010101010101);
                    realRom.AddOffset(8);
                    fakeRom.AddOffset(8);
                } while (fakeRom.offset < region.length);
            }
            realRom.PopOffset();

            fakeRom.offset = 0;
            realRom.PushOffset(region.romStart);
            {
                int start = region.romStart;
                do
                {
                    Int64 cmd = fakeRom.Read64();
                    fakeRom.AddOffset(8);

                    if (config.trimNOPs && cmd == 0 && dlRegion.isUnusedTrimmingAllowed)
                    {
                        continue;
                    }

                    realRom.Write64((ulong)cmd);
                    realRom.AddOffset(8);
                } while (fakeRom.offset < region.length);

                region.length = realRom.offset - start;
                region.data   = new byte[region.length];
                realRom.ReadData(region.romStart, region.length, region.data);
            }
            realRom.PopOffset();
        }
Exemple #12
0
        private static void VisualMapParse_cmdFB(ROM rom, VisualMap map, VisualMapParseState state)
        {
            // Some importers have the only EnvColor func for everything lmfao
            if (rom.Read8(8) != 0xFD)
            {
                goto fini;
            }

            state.envColorCmd = (ulong)rom.Read64();
            state.state       = VisualMapParseStateCmd.Texture;
            state.td          = new TextureDescription();

fini:
            VisualMapParse_common(rom, map, state);
        }
Exemple #13
0
        private static void OptimizeParse_cmdBC(ROM rom, DisplayListRegion region, RegionOptimizeState state)
        {
            Int64 cmd = rom.Read64();

            // initial state
            if (state.lastBCCmd == 0)
            {
                state.lastBCCmd = cmd;
                return;
            }

            // if current cmd loads the same, remove current cmd
            if (cmd == state.lastBCCmd)
            {
                rom.Write64(0);
                return;
            }
        }
Exemple #14
0
 private static void RegionParse_cmd10(ROM rom, List <Region> regions, RegionParseState state)
 {
     if (rom.Read64() == 0x1008000000000000)
     {
         if (rom.offset == state.start)
         {
             state.start = rom.offset + rom.Read8(1);
         }
         // Skip empty commands in the beginning of any region
         else if (rom.offset == state.start + rom.Read8(1))
         {
             state.start = rom.offset + rom.Read8(1);
         }
         else
         {
             // Commands is not in the beginning, cut area, start new one that is same as it was before
             if (state.regionState == RegionState.ModelsLoader)
             {
                 CutRegion(rom, regions, state, rom.offset, state.regionState);
             }
         }
     }
 }
Exemple #15
0
 private static void VisualMapParse_cmdBF(ROM rom, VisualMap map, VisualMapParseState state)
 {
     state.isHeader = false;
     state.state    = VisualMapParseStateCmd.Footer;
     map.AddTriangle(state.td, state.vertexLoadCmd, (UInt64)rom.Read64());
 }
Exemple #16
0
 private static void VisualMapParse_cmd04(ROM rom, VisualMap map, VisualMapParseState state)
 {
     state.vertexLoadCmd = (UInt64)rom.Read64();
 }