diff --git a/Asm65/Formatter.cs b/Asm65/Formatter.cs
index 5ef0ef4..d676df2 100644
--- a/Asm65/Formatter.cs
+++ b/Asm65/Formatter.cs
@@ -111,6 +111,43 @@ namespace Asm65 {
}
return em;
}
+
+ // TODO: FormatConfig should be a class with properties so we can avoid this nonsense
+ public void Normalize() {
+ if (mForceDirectOperandPrefix == null) {
+ mForceDirectOperandPrefix = string.Empty;
+ }
+ if (mForceAbsOpcodeSuffix == null) {
+ mForceAbsOpcodeSuffix = string.Empty;
+ }
+ if (mForceAbsOperandPrefix == null) {
+ mForceAbsOperandPrefix = string.Empty;
+ }
+ if (mForceDirectOpcodeSuffix == null) {
+ mForceDirectOpcodeSuffix = string.Empty;
+ }
+ if (mForceLongOpcodeSuffix == null) {
+ mForceLongOpcodeSuffix = string.Empty;
+ }
+ if (mForceLongOperandPrefix == null) {
+ mForceLongOperandPrefix = string.Empty;
+ }
+ if (mLocalVariableLabelPrefix == null) {
+ mLocalVariableLabelPrefix = string.Empty;
+ }
+ if (mNonUniqueLabelPrefix == null) {
+ mNonUniqueLabelPrefix = string.Empty;
+ }
+ if (mEndOfLineCommentDelimiter == null) {
+ mEndOfLineCommentDelimiter = string.Empty;
+ }
+ if (mFullLineCommentDelimiterBase == null) {
+ mFullLineCommentDelimiterBase = string.Empty;
+ }
+ if (mBoxLineCommentDelimiter == null) {
+ mBoxLineCommentDelimiter = string.Empty;
+ }
+ }
}
#region Text Delimiters
@@ -391,15 +428,8 @@ namespace Asm65 {
///
public Formatter(FormatConfig config) {
mFormatConfig = config; // copy struct
- if (mFormatConfig.mEndOfLineCommentDelimiter == null) {
- mFormatConfig.mEndOfLineCommentDelimiter = string.Empty;
- }
- if (mFormatConfig.mFullLineCommentDelimiterBase == null) {
- mFormatConfig.mFullLineCommentDelimiterBase = string.Empty;
- }
- if (mFormatConfig.mBoxLineCommentDelimiter == null) {
- mFormatConfig.mBoxLineCommentDelimiter = string.Empty;
- }
+
+ mFormatConfig.Normalize();
if (string.IsNullOrEmpty(mFormatConfig.mNonUniqueLabelPrefix)) {
mFormatConfig.mNonUniqueLabelPrefix = "@";
diff --git a/SourceGen/Res/Strings.xaml b/SourceGen/Res/Strings.xaml
index 8b24a58..c133eca 100644
--- a/SourceGen/Res/Strings.xaml
+++ b/SourceGen/Res/Strings.xaml
@@ -130,7 +130,8 @@ limitations under the License.
Visualization ignored
no files available
No exported symbols found.
-
Segment {0}: Kind={2}, SegName='{1}'
+ Segment {0:D2}: {3} Kind={1}, SegName='{2}'
+ Segment {0:D2}: {1} '{2}'
The file doesn't exist.
File is empty
Unable to load data file
diff --git a/SourceGen/Res/Strings.xaml.cs b/SourceGen/Res/Strings.xaml.cs
index 8a76d76..37bd598 100644
--- a/SourceGen/Res/Strings.xaml.cs
+++ b/SourceGen/Res/Strings.xaml.cs
@@ -243,6 +243,8 @@ namespace SourceGen.Res {
(string)Application.Current.FindResource("str_NoExportedSymbolsFound");
public static string OMF_SEG_COMMENT_FMT =
(string)Application.Current.FindResource("str_OmfSegCommentFmt");
+ public static string OMF_SEG_NOTE_FMT =
+ (string)Application.Current.FindResource("str_OmfSegNoteFmt");
public static string OPEN_DATA_DOESNT_EXIST =
(string)Application.Current.FindResource("str_OpenDataDoesntExist");
public static string OPEN_DATA_EMPTY =
diff --git a/SourceGen/Tools/Omf/Loader.cs b/SourceGen/Tools/Omf/Loader.cs
index 35dda01..1029b7a 100644
--- a/SourceGen/Tools/Omf/Loader.cs
+++ b/SourceGen/Tools/Omf/Loader.cs
@@ -17,7 +17,9 @@ using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
+using System.Text;
+using Asm65;
using CommonUtil;
namespace SourceGen.Tools.Omf {
@@ -30,6 +32,7 @@ namespace SourceGen.Tools.Omf {
private const string IIGS_SYSTEM_DEF = "Apple IIgs (GS/OS)";
private OmfFile mOmfFile;
+ private Formatter mFormatter;
private byte[] mLoadedData;
private DisasmProject mNewProject;
@@ -50,10 +53,11 @@ namespace SourceGen.Tools.Omf {
/// Constructor.
///
/// OMF file to load.
- public Loader(OmfFile omfFile) {
+ public Loader(OmfFile omfFile, Formatter formatter) {
Debug.Assert(omfFile.OmfFileKind == OmfFile.FileKind.Load);
mOmfFile = omfFile;
+ mFormatter = formatter;
}
///
@@ -289,35 +293,32 @@ namespace SourceGen.Tools.Omf {
Debug.WriteLine("Failed to apply Apple IIgs system definition");
}
- // Add header comment.
- string cmt = string.Format(Res.Strings.DEFAULT_HEADER_COMMENT_FMT, App.ProgramVersion);
- proj.LongComments.Add(LineListGen.Line.HEADER_COMMENT_OFFSET,
- new MultiLineComment(cmt));
-
ChangeSet cs = new ChangeSet(mSegmentMap.Count * 2);
+ AddHeaderComment(proj, cs);
// Load the segments, and add entries to the project.
int bufOffset = 0;
foreach (SegmentMapEntry ent in mSegmentMap) {
- if (ent != null) {
- // Perform relocation.
- if (!RelocSegment(ent, data, bufOffset)) {
- return false;
- }
-
- // Add one or more address entries. (Normally one, but data segments
- // can straddle multiple pages.)
- AddAddressEntries(proj, ent, bufOffset, cs);
-
- // Add a comment identifying the segment.
- string segCmt = string.Format(Res.Strings.OMF_SEG_COMMENT_FMT,
- ent.Segment.SegNum, ent.Segment.SegName, ent.Segment.Kind);
- UndoableChange uc = UndoableChange.CreateLongCommentChange(bufOffset, null,
- new MultiLineComment(segCmt));
- cs.Add(uc);
-
- bufOffset += ent.Segment.Length;
+ if (ent == null) {
+ continue;
}
+ // Perform relocation.
+ if (!RelocSegment(ent, data, bufOffset)) {
+ return false;
+ }
+
+ // Add one or more address entries. (Normally one, but data segments
+ // can straddle multiple pages.)
+ AddAddressEntries(proj, ent, bufOffset, cs);
+
+ // Add a note identifying the segment.
+ string segCmt = string.Format(Res.Strings.OMF_SEG_NOTE_FMT,
+ ent.Segment.SegNum, ent.Segment.Kind, ent.Segment.SegName);
+ UndoableChange uc = UndoableChange.CreateNoteChange(bufOffset, null,
+ new MultiLineComment(segCmt));
+ cs.Add(uc);
+
+ bufOffset += ent.Segment.Length;
}
proj.PrepForNew(data, "new_proj");
@@ -328,44 +329,44 @@ namespace SourceGen.Tools.Omf {
return true;
}
- private static void AddAddressEntries(DisasmProject proj, SegmentMapEntry ent,
- int bufOffset, ChangeSet cs) {
- int addr = ent.Address;
- int segRem = ent.Segment.Length;
-
- while (true) {
- int origAddr = proj.AddrMap.Get(bufOffset);
- UndoableChange uc = UndoableChange.CreateAddressChange(bufOffset,
- origAddr, addr);
- cs.Add(uc);
-
- // Compare amount of space in this bank to amount left in segment.
- int bankRem = 0x00010000 - (addr & 0xffff);
- if (bankRem > segRem) {
- // All done, bail.
- break;
+ private void AddHeaderComment(DisasmProject proj, ChangeSet cs) {
+ // Add header comment.
+ StringBuilder sb = new StringBuilder();
+ sb.AppendLine(string.Format(Res.Strings.DEFAULT_HEADER_COMMENT_FMT,
+ App.ProgramVersion));
+ sb.AppendLine();
+ foreach (SegmentMapEntry ent in mSegmentMap) {
+ if (ent == null) {
+ continue;
}
-
- // Advance to start of next bank.
- addr += bankRem;
- Debug.Assert((addr & 0x0000ffff) == 0);
- bufOffset += bankRem;
- segRem -= bankRem;
- Debug.WriteLine("Adding additional ORG at " + addr);
+ string segCmt = string.Format(Res.Strings.OMF_SEG_COMMENT_FMT,
+ ent.Segment.SegNum, ent.Segment.Kind, ent.Segment.SegName,
+ mFormatter.FormatAddress(ent.Address, true));
+ sb.AppendLine(segCmt);
}
+
+ UndoableChange uc = UndoableChange.CreateLongCommentChange(
+ LineListGen.Line.HEADER_COMMENT_OFFSET,
+ null, new MultiLineComment(sb.ToString()));
+ cs.Add(uc);
}
+ ///
+ /// Edits the data file, changing values based on the relocation dictionary.
+ ///
private bool RelocSegment(SegmentMapEntry ent, byte[] data, int bufOffset) {
- //const int INVALID_RELOC = 0x00ffffff;
+ const int INVALID_ADDR = 0x00ffffff;
+
byte[] srcData = ent.Segment.GetConstData();
Array.Copy(srcData, 0, data, bufOffset, srcData.Length);
foreach (OmfReloc omfRel in ent.Segment.Relocs) {
int relocAddr = omfRel.RelOffset;
if (omfRel.FileNum != -1 && omfRel.FileNum != 1) {
- // Some other file; not much we can do with this.
+ // Some other file; not much we can do with this. Drop in an obviously
+ // invalid address and keep going.
Debug.WriteLine("Unable to process reloc with FileNum=" + omfRel.FileNum);
- return false;
+ relocAddr = INVALID_ADDR;
} else if (omfRel.SegNum == -1) {
// Within this segment.
relocAddr += ent.Address;
@@ -373,6 +374,9 @@ namespace SourceGen.Tools.Omf {
// Find other segment. This may fail if the file is damaged.
if (omfRel.SegNum < 0 || omfRel.SegNum >= mSegmentMap.Count ||
mSegmentMap[omfRel.SegNum] == null) {
+ // Can't find the segment. Unlike the file case, this was expected to
+ // be something we could resolve with what we were given, so this is
+ // a hard failure.
Debug.WriteLine("Reloc SegNum=" + omfRel.SegNum + " not in map");
return false;
} else {
@@ -413,5 +417,36 @@ namespace SourceGen.Tools.Omf {
return true;
}
+
+ ///
+ /// Adds one or more entries to the address map for the specified segment.
+ ///
+ private static void AddAddressEntries(DisasmProject proj, SegmentMapEntry ent,
+ int bufOffset, ChangeSet cs) {
+ int addr = ent.Address;
+ int segRem = ent.Segment.Length;
+
+ while (true) {
+ // Generate an ORG directive.
+ int origAddr = proj.AddrMap.Get(bufOffset);
+ UndoableChange uc = UndoableChange.CreateAddressChange(bufOffset,
+ origAddr, addr);
+ cs.Add(uc);
+
+ // Compare amount of space in this bank to amount left in segment.
+ int bankRem = 0x00010000 - (addr & 0xffff);
+ if (bankRem > segRem) {
+ // All done, bail.
+ break;
+ }
+
+ // Advance to start of next bank.
+ addr += bankRem;
+ Debug.Assert((addr & 0x0000ffff) == 0);
+ bufOffset += bankRem;
+ segRem -= bankRem;
+ Debug.WriteLine("Adding additional ORG at " + addr);
+ }
+ }
}
}
diff --git a/SourceGen/Tools/Omf/WpfGui/OmfViewer.xaml.cs b/SourceGen/Tools/Omf/WpfGui/OmfViewer.xaml.cs
index cf79bdb..c9cd731 100644
--- a/SourceGen/Tools/Omf/WpfGui/OmfViewer.xaml.cs
+++ b/SourceGen/Tools/Omf/WpfGui/OmfViewer.xaml.cs
@@ -166,7 +166,7 @@ namespace SourceGen.Tools.Omf.WpfGui {
}
private void GenerateProject_Click(object sender, RoutedEventArgs e) {
- Loader loader = new Loader(mOmfFile);
+ Loader loader = new Loader(mOmfFile, mFormatter);
if (!loader.Prepare()) {
// Unexpected. If there's a valid reason for this, we need to add details
// to the error message.
diff --git a/SourceGen/WpfGui/EditAppSettings.xaml.cs b/SourceGen/WpfGui/EditAppSettings.xaml.cs
index 3acd45e..500b893 100644
--- a/SourceGen/WpfGui/EditAppSettings.xaml.cs
+++ b/SourceGen/WpfGui/EditAppSettings.xaml.cs
@@ -984,6 +984,7 @@ namespace SourceGen.WpfGui {
gen.GetDefaultDisplayFormat(out PseudoOp.PseudoOpNames unused,
out Asm65.Formatter.FormatConfig formatConfig);
+ formatConfig.Normalize();
DisplayPresets[i + 2] = new DisplayFormatPreset((int)asmInfo.AssemblerId,
asmInfo.Name, formatConfig.mForceAbsOpcodeSuffix,