private void UpdateText(TextBox selected) { Util.NumberBase noBase = radioDec.Checked ? Util.NumberBase.Decimal : Util.NumberBase.Hexadecimal; int digits = noBase == Util.NumberBase.Hexadecimal && radioROM.Checked ? 6 : 0; int size = Data.GetROMSize(); if (start < 0) { start = 0; } if (end >= size) { end = size - 1; } count = end - start; if (count < 0) { count = 0; } updatingText = true; if (selected != textStart) { textStart.Text = Util.NumberToBaseString(radioROM.Checked ? Util.ConvertPCtoSNES(start) : start, noBase, digits); } if (selected != textEnd) { textEnd.Text = Util.NumberToBaseString(radioROM.Checked ? Util.ConvertPCtoSNES(end) : end, noBase, digits); } if (selected != textCount) { textCount.Text = Util.NumberToBaseString(count, noBase, 0); } updatingText = false; }
private void table_CellValuePushed(object sender, DataGridViewCellValueEventArgs e) { string value = e.Value as string; int result; int row = e.RowIndex + viewOffset; if (row >= Data.GetROMSize()) { return; } switch (e.ColumnIndex) { case 0: Data.AddLabel(Util.ConvertPCtoSNES(row), value, true); break; // todo (validate for valid label characters) case 8: if (int.TryParse(value, NumberStyles.HexNumber, null, out result)) { Data.SetDataBank(row, result); } break; case 9: if (int.TryParse(value, NumberStyles.HexNumber, null, out result)) { Data.SetDirectPage(row, result); } break; case 10: Data.SetMFlag(row, (value == "8" || value == "M")); break; case 11: Data.SetXFlag(row, (value == "8" || value == "X")); break; case 12: Data.AddComment(Util.ConvertPCtoSNES(row), value, true); break; } table.InvalidateRow(e.RowIndex); }
private static void AddTemporaryLabels() { List <int> addMe = new List <int>(); int pointer = 0; while (pointer < Data.GetROMSize()) { int length = GetLineByteLength(pointer); Data.FlagType flag = Data.GetFlag(pointer); if (unlabeled == FormatUnlabeled.ShowAll) { addMe.Add(Util.ConvertPCtoSNES(pointer)); } else if (unlabeled != FormatUnlabeled.ShowNone && (flag == Data.FlagType.Opcode || flag == Data.FlagType.Pointer16Bit || flag == Data.FlagType.Pointer24Bit || flag == Data.FlagType.Pointer32Bit)) { int ia = Util.GetIntermediateAddressOrPointer(pointer); if (ia >= 0 && Util.ConvertSNEStoPC(ia) >= 0) { addMe.Add(ia); } } pointer += length; } // TODO +/- labels for (int i = 0; i < addMe.Count; i++) { Data.AddLabel(addMe[i], Util.GetDefaultLabel(addMe[i]), false); } }
private static string GetIncSrc(int offset, int length) { int bank = Util.ConvertPCtoSNES(offset) >> 16; string s = string.Format("incsrc \"bank_{0}.asm\"", Util.NumberToBaseString(bank, Util.NumberBase.Hexadecimal, 2)); return(string.Format("{0," + (length * -1) + "}", s)); }
public static int GetIntermediateAddress(int offset) { int bank, directPage, operand, programCounter; int opcode = Data.GetROMByte(offset); AddressMode mode = GetAddressMode(offset); switch (mode) { case AddressMode.DIRECT_PAGE: case AddressMode.DIRECT_PAGE_X_INDEX: case AddressMode.DIRECT_PAGE_Y_INDEX: case AddressMode.DIRECT_PAGE_INDIRECT: case AddressMode.DIRECT_PAGE_X_INDEX_INDIRECT: case AddressMode.DIRECT_PAGE_INDIRECT_Y_INDEX: case AddressMode.DIRECT_PAGE_LONG_INDIRECT: case AddressMode.DIRECT_PAGE_LONG_INDIRECT_Y_INDEX: directPage = Data.GetDirectPage(offset); operand = Data.GetROMByte(offset + 1); return((directPage + operand) & 0xFFFF); case AddressMode.DIRECT_PAGE_S_INDEX: case AddressMode.DIRECT_PAGE_S_INDEX_INDIRECT_Y_INDEX: return(Data.GetROMByte(offset + 1)); case AddressMode.ADDRESS: case AddressMode.ADDRESS_X_INDEX: case AddressMode.ADDRESS_Y_INDEX: case AddressMode.ADDRESS_X_INDEX_INDIRECT: bank = (opcode == 0x20 || opcode == 0x4C || opcode == 0x7C || opcode == 0xFC) ? Util.ConvertPCtoSNES(offset) >> 16 : Data.GetDataBank(offset); operand = Util.GetROMWord(offset + 1); return((bank << 16) | operand); case AddressMode.ADDRESS_INDIRECT: case AddressMode.ADDRESS_LONG_INDIRECT: operand = Util.GetROMWord(offset + 1); return(operand); case AddressMode.LONG: case AddressMode.LONG_X_INDEX: operand = Util.GetROMLong(offset + 1); return(operand); case AddressMode.RELATIVE_8: programCounter = Util.ConvertPCtoSNES(offset + 2); bank = programCounter >> 16; offset = (sbyte)Data.GetROMByte(offset + 1); return((bank << 16) | ((programCounter + offset) & 0xFFFF)); case AddressMode.RELATIVE_16: programCounter = Util.ConvertPCtoSNES(offset + 3); bank = programCounter >> 16; offset = (short)Util.GetROMWord(offset + 1); return((bank << 16) | ((programCounter + offset) & 0xFFFF)); } return(-1); }
private void table_CellValueNeeded(object sender, DataGridViewCellValueEventArgs e) { int row = e.RowIndex + viewOffset; if (row >= Data.GetROMSize()) { return; } switch (e.ColumnIndex) { case 0: e.Value = Data.GetLabel(Util.ConvertPCtoSNES(row)); break; case 1: e.Value = Util.NumberToBaseString(Util.ConvertPCtoSNES(row), Util.NumberBase.Hexadecimal, 6); break; case 2: e.Value = (char)Data.GetROMByte(row); break; case 3: e.Value = Util.NumberToBaseString(Data.GetROMByte(row), DisplayBase); break; case 4: e.Value = Util.PointToString(Data.GetInOutPoint(row)); break; case 5: int len = Manager.GetInstructionLength(row); if (row + len <= Data.GetROMSize()) { e.Value = Util.GetInstruction(row); } else { e.Value = ""; } break; case 6: int ia = Util.GetIntermediateAddressOrPointer(row); if (ia >= 0) { e.Value = Util.NumberToBaseString(ia, Util.NumberBase.Hexadecimal, 6); } else { e.Value = ""; } break; case 7: e.Value = Util.TypeToString(Data.GetFlag(row)); break; case 8: e.Value = Util.NumberToBaseString(Data.GetDataBank(row), Util.NumberBase.Hexadecimal, 2); break; case 9: e.Value = Util.NumberToBaseString(Data.GetDirectPage(row), Util.NumberBase.Hexadecimal, 4); break; case 10: e.Value = Util.BoolToSize(Data.GetMFlag(row)); break; case 11: e.Value = Util.BoolToSize(Data.GetXFlag(row)); break; case 12: e.Value = Data.GetComment(Util.ConvertPCtoSNES(row)); break; } }
// trim to length // negative length = right justified private static string GetLabel(int offset, int length) { int snes = Util.ConvertPCtoSNES(offset); string label = Data.GetLabel(snes); usedLabels.Add(snes); bool noColon = label.Length == 0 || label[0] == '-' || label[0] == '+'; return(string.Format("{0," + (length * -1) + "}", label + (noColon ? "" : ":"))); }
private void textPC_TextChanged(object sender, EventArgs e) { if (!updatingText) { updatingText = true; NumberStyles style = radioDec.Checked ? NumberStyles.Number : NumberStyles.HexNumber; Util.NumberBase noBase = radioDec.Checked ? Util.NumberBase.Decimal : Util.NumberBase.Hexadecimal; if (int.TryParse(textPC.Text, style, null, out int offset)) { int addr = Util.ConvertPCtoSNES(offset); if (addr >= 0) { textROM.Text = Util.NumberToBaseString(addr, noBase, 6); } } updatingText = false; } }
private void buttonScan_Click(object sender, EventArgs e) { textLog.Text = ""; int found = 0, offset = 0; while (found < 500 && offset < Data.GetROMSize()) { Data.FlagType flag = Data.GetFlag(offset), check = flag == Data.FlagType.Opcode ? Data.FlagType.Operand : flag; int step = flag == Data.FlagType.Opcode ? Manager.GetInstructionLength(offset) : Util.TypeStepSize(flag); if (flag == Data.FlagType.Operand) { found++; textLog.Text += string.Format("{0} (0x{1}): Operand without Opcode\r\n", Util.NumberToBaseString(Util.ConvertPCtoSNES(offset), Util.NumberBase.Hexadecimal, 6, true), Util.NumberToBaseString(offset, Util.NumberBase.Hexadecimal, 0)); } else if (step > 1) { for (int i = 1; i < step; i++) { if (Data.GetFlag(offset + i) != check) { found++; textLog.Text += string.Format("{0} (0x{1}): {2} is not {3}\r\n", Util.NumberToBaseString(Util.ConvertPCtoSNES(offset + i), Util.NumberBase.Hexadecimal, 6, true), Util.NumberToBaseString(offset + i, Util.NumberBase.Hexadecimal, 0), Util.TypeToString(Data.GetFlag(offset + i)), Util.TypeToString(check)); } } } offset += step; } if (found == 0) { textLog.Text = "No misaligned flags found!"; } }
public GotoDialog(int offset) { InitializeComponent(); textROM.Text = Util.NumberToBaseString(Util.ConvertPCtoSNES(offset), Util.NumberBase.Hexadecimal, 6); textPC.Text = Util.NumberToBaseString(offset, Util.NumberBase.Hexadecimal, 0); }
public static int CreateLog(StreamWriter sw, StreamWriter er) { Dictionary <int, string> tempAlias = Data.GetAllLabels(); Data.Restore(a: new Dictionary <int, string>(tempAlias)); AliasList.me.locked = true; bankSize = Data.GetROMMapMode() == Data.ROMMapMode.LoROM ? 0x8000 : 0x10000; // todo AddTemporaryLabels(); string[] split = format.Split('%'); err = er; errorCount = 0; usedLabels = new List <int>(); list = new List <Tuple <string, int> >(); for (int i = 0; i < split.Length; i++) { if (i % 2 == 0) { list.Add(Tuple.Create(split[i], int.MaxValue)); } else { int colon = split[i].IndexOf(':'); if (colon < 0) { list.Add(Tuple.Create(split[i], parameters[split[i]].Item2)); } else { list.Add(Tuple.Create(split[i].Substring(0, colon), int.Parse(split[i].Substring(colon + 1)))); } } } int pointer = 0, size = (Data.GetTable() == ExportDisassembly.sampleTable) ? 0x7B : Data.GetROMSize(), bank = -1; if (structure == FormatStructure.OneBankPerFile) { folder = Path.GetDirectoryName(((FileStream)sw.BaseStream).Name); sw.WriteLine(GetLine(pointer, "map")); sw.WriteLine(GetLine(pointer, "empty")); for (int i = 0; i < size; i += bankSize) { sw.WriteLine(GetLine(i, "incsrc")); } sw.WriteLine(GetLine(-1, "incsrc")); } else { sw.WriteLine(GetLine(pointer, "map")); sw.WriteLine(GetLine(pointer, "empty")); } while (pointer < size) { int snes = Util.ConvertPCtoSNES(pointer); if ((snes >> 16) != bank) { if (structure == FormatStructure.OneBankPerFile) { sw.Close(); sw = new StreamWriter(string.Format("{0}/bank_{1}.asm", folder, Util.NumberToBaseString((snes >> 16), Util.NumberBase.Hexadecimal, 2))); } sw.WriteLine(GetLine(pointer, "empty")); sw.WriteLine(GetLine(pointer, "org")); sw.WriteLine(GetLine(pointer, "empty")); if ((snes % bankSize) != 0) { err.WriteLine("({0}) Offset 0x{1:X}: An instruction crossed a bank boundary.", ++errorCount, pointer); } bank = snes >> 16; } string label; if ((Data.GetInOutPoint(pointer) & (Data.InOutPoint.ReadPoint)) != 0 || (tempAlias.TryGetValue(pointer, out label) && label.Length > 0)) { sw.WriteLine(GetLine(pointer, "empty")); } sw.WriteLine(GetLine(pointer, null)); if ((Data.GetInOutPoint(pointer) & (Data.InOutPoint.EndPoint)) != 0) { sw.WriteLine(GetLine(pointer, "empty")); } pointer += GetLineByteLength(pointer); } if (structure == FormatStructure.OneBankPerFile) { sw.Close(); sw = new StreamWriter(string.Format("{0}/labels.asm", folder)); } else { sw.WriteLine(GetLine(pointer, "empty")); } foreach (KeyValuePair <int, string> pair in Data.GetAllLabels()) { if (!usedLabels.Contains(pair.Key)) { sw.WriteLine(GetLine(pair.Key, "labelassign")); } } if (structure == FormatStructure.OneBankPerFile) { sw.Close(); } Data.Restore(a: tempAlias); AliasList.me.locked = false; return(errorCount); }
// trim to length private static string GetComment(int offset, int length) { return(string.Format("{0," + (length * -1) + "}", Data.GetComment(Util.ConvertPCtoSNES(offset)))); }
// length forced to 6 private static string GetProgramCounter(int offset, int length) { return(Util.NumberToBaseString(Util.ConvertPCtoSNES(offset), Util.NumberBase.Hexadecimal, 6)); }
private static string GetORG(int offset, int length) { string org = "ORG " + Util.NumberToBaseString(Util.ConvertPCtoSNES(offset), Util.NumberBase.Hexadecimal, 6, true); return(string.Format("{0," + (length * -1) + "}", org)); }
private static int GetLineByteLength(int offset) { int max = 1, step = 1; int size = Data.GetROMSize(); switch (Data.GetFlag(offset)) { case Data.FlagType.Opcode: switch (Data.GetArchitechture(offset)) { case Data.Architechture.CPU65C816: return(CPU65C816.GetInstructionLength(offset)); case Data.Architechture.APUSPC700: return(1); case Data.Architechture.GPUSuperFX: return(1); } return(1); case Data.FlagType.Unreached: case Data.FlagType.Operand: case Data.FlagType.Data8Bit: case Data.FlagType.Graphics: case Data.FlagType.Music: case Data.FlagType.Empty: max = dataPerLine; break; case Data.FlagType.Text: max = 21; break; case Data.FlagType.Data16Bit: step = 2; max = dataPerLine; break; case Data.FlagType.Data24Bit: step = 3; max = dataPerLine; break; case Data.FlagType.Data32Bit: step = 4; max = dataPerLine; break; case Data.FlagType.Pointer16Bit: step = 2; max = 2; break; case Data.FlagType.Pointer24Bit: step = 3; max = 3; break; case Data.FlagType.Pointer32Bit: step = 4; max = 4; break; } int min = step, myBank = offset / bankSize; while ( min < max && offset + min < size && Data.GetFlag(offset + min) == Data.GetFlag(offset) && Data.GetLabel(Util.ConvertPCtoSNES(offset + min)) == "" && (offset + min) / bankSize == myBank ) { min += step; } return(min); }
// differences between version 0 and version 1: // version 0: addresses for aliases and comments were stored in PC offset format. // tables: B, D lo, D hi, X, M, flag, arch, inoutpoint // lists: alias, comment // version 1: addresses for aliases and comments are stored in SNES address format. // tables: B, D lo, D hi, X, M, flag, arch, inoutpoint, ??? // lists: alias, comment, ??? private static void OpenVersion0(byte[] unzipped, OpenFileDialog open) { MessageBox.Show( "This project file is in an older format.\n" + "You may want to back up your work or 'Save As' in case the conversion goes wrong.\n" + "The project file will be untouched until it is saved again.", "Project File Out of Date", MessageBoxButtons.OK, MessageBoxIcon.Exclamation); Data.ROMMapMode mode = (Data.ROMMapMode)unzipped[HEADER_SIZE]; Data.ROMSpeed speed = (Data.ROMSpeed)unzipped[HEADER_SIZE + 1]; int size = Util.ByteArrayToInteger(unzipped, HEADER_SIZE + 2); string romName = "", romLocation = ""; byte[] rom; int pointer = HEADER_SIZE + 6; for (int i = 0; i < 0x15; i++) { romName += (char)unzipped[pointer++]; } int checksums = Util.ByteArrayToInteger(unzipped, pointer); pointer += 4; while (unzipped[pointer] != 0) { romLocation += (char)unzipped[pointer++]; } pointer++; if (ValidateROM(romLocation, romName, checksums, mode, out rom, open)) { Data.Initiate(rom, mode, speed); for (int i = 0; i < size; i++) { Data.SetDataBank(i, unzipped[pointer + i]); } for (int i = 0; i < size; i++) { Data.SetDirectPage(i, unzipped[pointer + size + i] | (unzipped[pointer + 2 * size + i] << 8)); } for (int i = 0; i < size; i++) { Data.SetXFlag(i, unzipped[pointer + 3 * size + i] != 0); } for (int i = 0; i < size; i++) { Data.SetMFlag(i, unzipped[pointer + 4 * size + i] != 0); } for (int i = 0; i < size; i++) { Data.SetFlag(i, (Data.FlagType)unzipped[pointer + 5 * size + i]); } for (int i = 0; i < size; i++) { Data.SetArchitechture(i, (Data.Architechture)unzipped[pointer + 6 * size + i]); } for (int i = 0; i < size; i++) { Data.SetInOutPoint(i, (Data.InOutPoint)unzipped[pointer + 7 * size + i]); } pointer += 8 * size; int label_count = Util.ByteArrayToInteger(unzipped, pointer); pointer += 4; AliasList.me.Reset(); for (int i = 0; i < label_count; i++) { int offset = Util.ConvertPCtoSNES(Util.ByteArrayToInteger(unzipped, pointer)); // pc -> snes pointer += 4; string label = ""; while (unzipped[pointer] != 0) { label += (char)unzipped[pointer++]; } pointer++; Data.AddLabel(offset, label, true); } int comment_count = Util.ByteArrayToInteger(unzipped, pointer); pointer += 4; for (int i = 0; i < comment_count; i++) { int offset = Util.ConvertPCtoSNES(Util.ByteArrayToInteger(unzipped, pointer)); // pc -> snes pointer += 4; string comment = ""; while (unzipped[pointer] != 0) { comment += (char)unzipped[pointer++]; } pointer++; Data.AddComment(offset, comment, true); } } else { throw new Exception("Couldn't open the ROM file!"); } }