diff --git a/SabreTools.Library/DatFiles/ItemDictionary.cs b/SabreTools.Library/DatFiles/ItemDictionary.cs
index 34ae5342..f2ad9346 100644
--- a/SabreTools.Library/DatFiles/ItemDictionary.cs
+++ b/SabreTools.Library/DatFiles/ItemDictionary.cs
@@ -161,6 +161,12 @@ namespace SabreTools.Library.DatFiles
[JsonIgnore]
public long MediaCount { get; private set; } = 0;
+ ///
+ /// Number of Port items
+ ///
+ [JsonIgnore]
+ public long PortCount { get; private set; } = 0;
+
///
/// Number of RamOption items
///
@@ -584,6 +590,9 @@ namespace SabreTools.Library.DatFiles
SHA1Count += (string.IsNullOrWhiteSpace((item as Media).SHA1) ? 0 : 1);
SHA256Count += (string.IsNullOrWhiteSpace((item as Media).SHA256) ? 0 : 1);
break;
+ case ItemType.Port:
+ PortCount++;
+ break;
case ItemType.RamOption:
RamOptionCount++;
break;
@@ -752,6 +761,9 @@ namespace SabreTools.Library.DatFiles
SHA1Count -= (string.IsNullOrWhiteSpace((item as Media).SHA1) ? 0 : 1);
SHA256Count -= (string.IsNullOrWhiteSpace((item as Media).SHA256) ? 0 : 1);
break;
+ case ItemType.Port:
+ PortCount--;
+ break;
case ItemType.RamOption:
RamOptionCount--;
break;
diff --git a/SabreTools.Library/DatFiles/Json.cs b/SabreTools.Library/DatFiles/Json.cs
index ac06d5fb..d1e9511e 100644
--- a/SabreTools.Library/DatFiles/Json.cs
+++ b/SabreTools.Library/DatFiles/Json.cs
@@ -259,6 +259,9 @@ namespace SabreTools.Library.DatFiles
case ItemType.Media:
datItem = datItemObj.ToObject();
break;
+ case ItemType.Port:
+ datItem = datItemObj.ToObject();
+ break;
case ItemType.RamOption:
datItem = datItemObj.ToObject();
break;
diff --git a/SabreTools.Library/DatFiles/Listxml.cs b/SabreTools.Library/DatFiles/Listxml.cs
index 2dc9ab18..05633164 100644
--- a/SabreTools.Library/DatFiles/Listxml.cs
+++ b/SabreTools.Library/DatFiles/Listxml.cs
@@ -391,6 +391,27 @@ namespace SabreTools.Library.DatFiles
reader.Read();
break;
+ case "port":
+ var port = new Port
+ {
+ Tag = reader.GetAttribute("tag"),
+
+ Source = new Source
+ {
+ Index = indexId,
+ Name = filename,
+ },
+ };
+
+ // Now read the internal tags
+ ReadPort(reader.ReadSubtree(), port);
+
+ datItems.Add(port);
+
+ // Skip the port now that we've processed it
+ reader.Skip();
+ break;
+
case "rom":
datItems.Add(new Rom
{
@@ -546,23 +567,6 @@ namespace SabreTools.Library.DatFiles
reader.Skip();
break;
- case "port":
- var port = new Port();
- port.Tag = reader.GetAttribute("tag");
-
- // Now read the internal tags
- ReadPort(reader.ReadSubtree(), port);
-
- // Ensure the list exists
- if (machine.Ports == null)
- machine.Ports = new List();
-
- machine.Ports.Add(port);
-
- // Skip the port now that we've processed it
- reader.Skip();
- break;
-
default:
reader.Read();
break;
@@ -1303,24 +1307,6 @@ namespace SabreTools.Library.DatFiles
xtw.WriteEndElement();
}
}
- if (datItem.Machine.Ports != null)
- {
- foreach (var port in datItem.Machine.Ports)
- {
- xtw.WriteStartElement("port");
- xtw.WriteOptionalAttributeString("tag", port.Tag);
- if (port.Analogs != null)
- {
- foreach (var analog in port.Analogs)
- {
- xtw.WriteStartElement("analog");
- xtw.WriteOptionalAttributeString("mask", analog.Mask);
- xtw.WriteEndElement();
- }
- }
- xtw.WriteEndElement();
- }
- }
xtw.Flush();
}
@@ -1590,6 +1576,22 @@ namespace SabreTools.Library.DatFiles
xtw.WriteEndElement();
break;
+ case ItemType.Port:
+ var port = datItem as Port;
+ xtw.WriteStartElement("port");
+ xtw.WriteOptionalAttributeString("tag", port.Tag);
+ if (port.Analogs != null)
+ {
+ foreach (var analog in port.Analogs)
+ {
+ xtw.WriteStartElement("analog");
+ xtw.WriteOptionalAttributeString("mask", analog.Mask);
+ xtw.WriteEndElement();
+ }
+ }
+ xtw.WriteEndElement();
+ break;
+
case ItemType.RamOption:
var ramOption = datItem as RamOption;
xtw.WriteStartElement("ramoption");
diff --git a/SabreTools.Library/DatFiles/SabreDat.cs b/SabreTools.Library/DatFiles/SabreDat.cs
index cd064bd4..79376159 100644
--- a/SabreTools.Library/DatFiles/SabreDat.cs
+++ b/SabreTools.Library/DatFiles/SabreDat.cs
@@ -1229,14 +1229,6 @@ namespace SabreTools.Library.DatFiles
xtw.WriteEndElement();
break;
- case ItemType.Analog:
- var analog = datItem as Analog;
- xtw.WriteStartElement("file");
- xtw.WriteAttributeString("type", "analog");
- xtw.WriteOptionalAttributeString("mask", analog.Mask);
- xtw.WriteEndElement();
- break;
-
case ItemType.Archive:
var archive = datItem as Archive;
xtw.WriteStartElement("file");
@@ -1471,6 +1463,23 @@ namespace SabreTools.Library.DatFiles
xtw.WriteEndElement();
break;
+ case ItemType.Port:
+ var port = datItem as Port;
+ xtw.WriteStartElement("file");
+ xtw.WriteAttributeString("type", "port");
+ xtw.WriteOptionalAttributeString("tag", port.Tag);
+ if (port.Analogs != null)
+ {
+ foreach (var analog in port.Analogs)
+ {
+ xtw.WriteStartElement("analog");
+ xtw.WriteOptionalAttributeString("mask", analog.Mask);
+ xtw.WriteEndElement();
+ }
+ }
+ xtw.WriteEndElement();
+ break;
+
case ItemType.RamOption:
var ramOption = datItem as RamOption;
xtw.WriteStartElement("file");
diff --git a/SabreTools.Library/DatItems/Analog.cs b/SabreTools.Library/DatItems/Analog.cs
index 9e019f84..df401b77 100644
--- a/SabreTools.Library/DatItems/Analog.cs
+++ b/SabreTools.Library/DatItems/Analog.cs
@@ -34,8 +34,8 @@ namespace SabreTools.Library.DatItems
base.SetFields(mappings);
// Handle Analog-specific fields
- if (mappings.Keys.Contains(Field.Machine_Port_Analog_Mask))
- Mask = mappings[Field.Machine_Port_Analog_Mask];
+ if (mappings.Keys.Contains(Field.DatItem_Analog_Mask))
+ Mask = mappings[Field.DatItem_Analog_Mask];
}
#endregion
@@ -138,7 +138,7 @@ namespace SabreTools.Library.DatItems
base.RemoveFields(fields);
// Remove the fields
- if (fields.Contains(Field.Machine_Port_Analog_Mask))
+ if (fields.Contains(Field.DatItem_Analog_Mask))
Mask = null;
}
@@ -164,7 +164,7 @@ namespace SabreTools.Library.DatItems
Analog newItem = item as Analog;
// Replace the fields
- if (fields.Contains(Field.Machine_Port_Analog_Mask))
+ if (fields.Contains(Field.DatItem_Analog_Mask))
Mask = newItem.Mask;
}
diff --git a/SabreTools.Library/DatItems/Auxiliary.cs b/SabreTools.Library/DatItems/Auxiliary.cs
index 7f32395b..a08b4e93 100644
--- a/SabreTools.Library/DatItems/Auxiliary.cs
+++ b/SabreTools.Library/DatItems/Auxiliary.cs
@@ -265,30 +265,6 @@ namespace SabreTools.Library.DatItems
#endregion
}
- ///
- /// Represents one ListXML port
- ///
- /// TODO: Promote to DatItem level (contains list)
- [JsonObject("port")]
- public class Port
- {
- #region Fields
-
- ///
- /// Tag for the port
- ///
- [JsonProperty("tag", DefaultValueHandling = DefaultValueHandling.Ignore)]
- public string Tag { get; set; }
-
- ///
- /// List of analogs on the port
- ///
- [JsonProperty("analogs", DefaultValueHandling = DefaultValueHandling.Ignore)]
- public List Analogs { get; set; }
-
- #endregion
- }
-
///
/// Represents one ListXML confsetting or dipvalue
///
diff --git a/SabreTools.Library/DatItems/DatItem.cs b/SabreTools.Library/DatItems/DatItem.cs
index abe911dd..ebf4b561 100644
--- a/SabreTools.Library/DatItems/DatItem.cs
+++ b/SabreTools.Library/DatItems/DatItem.cs
@@ -506,6 +506,9 @@ namespace SabreTools.Library.DatItems
case ItemType.Media:
return new Media();
+ case ItemType.Port:
+ return new Port();
+
case ItemType.RamOption:
return new RamOption();
@@ -550,6 +553,7 @@ namespace SabreTools.Library.DatItems
ItemType.Feature => new Feature(),
ItemType.Instance => new Instance(),
ItemType.Media => new Media(),
+ ItemType.Port => new Port(),
ItemType.RamOption => new RamOption(),
ItemType.Release => new Release(),
ItemType.Rom => new Rom(),
diff --git a/SabreTools.Library/DatItems/Enums.cs b/SabreTools.Library/DatItems/Enums.cs
index 0052a501..10f956b0 100644
--- a/SabreTools.Library/DatItems/Enums.cs
+++ b/SabreTools.Library/DatItems/Enums.cs
@@ -225,14 +225,6 @@ namespace SabreTools.Library.DatItems
Machine_Input_Control_Ways2,
Machine_Input_Control_Ways3,
- // Ports
- Machine_Ports,
- Machine_Port_Tag,
-
- // Ports.Analogs
- Machine_Port_Analogs,
- Machine_Port_Analog_Mask,
-
#endregion
#region Logiqx
@@ -428,6 +420,10 @@ namespace SabreTools.Library.DatItems
DatItem_FeatureStatus,
DatItem_FeatureOverall,
+ // Port.Analogs
+ DatItem_Analogs,
+ DatItem_Analog_Mask,
+
// Ram Option
DatItem_Content,
@@ -497,6 +493,7 @@ namespace SabreTools.Library.DatItems
Extension,
Feature,
Instance,
+ Port,
RamOption,
Release,
Sample,
diff --git a/SabreTools.Library/DatItems/Machine.cs b/SabreTools.Library/DatItems/Machine.cs
index 64b90065..91eea2f8 100644
--- a/SabreTools.Library/DatItems/Machine.cs
+++ b/SabreTools.Library/DatItems/Machine.cs
@@ -164,12 +164,6 @@ namespace SabreTools.Library.DatItems
[JsonProperty("inputs", DefaultValueHandling = DefaultValueHandling.Ignore)]
public List Inputs { get; set; } = null;
- ///
- /// List of associated ports
- ///
- [JsonProperty("ports", DefaultValueHandling = DefaultValueHandling.Ignore)]
- public List Ports { get; set; } = null;
-
#endregion
#region Logiqx Fields
@@ -524,7 +518,6 @@ namespace SabreTools.Library.DatItems
Runnable = this.Runnable,
Displays = this.Displays,
Inputs = this.Inputs,
- Ports = this.Ports,
#endregion
@@ -1006,11 +999,6 @@ namespace SabreTools.Library.DatItems
// TODO: Inputs
// TODO: Inputs.Controls
- // TODO: Ports
- // TODO: Ports.Analogs
- // TODO: Devices
- // TODO: Devices.Instances
- // TODO: Devices.Extensions
#endregion // ListXML
diff --git a/SabreTools.Library/DatItems/Port.cs b/SabreTools.Library/DatItems/Port.cs
new file mode 100644
index 00000000..1a1eb6a2
--- /dev/null
+++ b/SabreTools.Library/DatItems/Port.cs
@@ -0,0 +1,196 @@
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+
+using SabreTools.Library.Filtering;
+using SabreTools.Library.Tools;
+using Newtonsoft.Json;
+
+namespace SabreTools.Library.DatItems
+{
+ ///
+ /// Represents a single port on a machine
+ ///
+ [JsonObject("port")]
+ public class Port : DatItem
+ {
+ #region Fields
+
+ ///
+ /// Tag for the port
+ ///
+ [JsonProperty("tag", DefaultValueHandling = DefaultValueHandling.Ignore)]
+ public string Tag { get; set; }
+
+ ///
+ /// List of analogs on the port
+ ///
+ [JsonProperty("analogs", DefaultValueHandling = DefaultValueHandling.Ignore)]
+ public List Analogs { get; set; }
+
+ #endregion
+
+ #region Accessors
+
+ ///
+ /// Set fields with given values
+ ///
+ /// Mappings dictionary
+ public override void SetFields(Dictionary mappings)
+ {
+ // Set base fields
+ base.SetFields(mappings);
+
+ // Handle Port-specific fields
+ if (mappings.Keys.Contains(Field.DatItem_Name))
+ Tag = mappings[Field.DatItem_Name];
+
+ // TODO: Handle DatItem_Analog*
+ }
+
+ #endregion
+
+ #region Constructors
+
+ ///
+ /// Create a default, empty Port object
+ ///
+ public Port()
+ {
+ ItemType = ItemType.Port;
+ }
+
+ #endregion
+
+ #region Cloning Methods
+
+ public override object Clone()
+ {
+ return new Port()
+ {
+ ItemType = this.ItemType,
+ DupeType = this.DupeType,
+
+ AltName = this.AltName,
+ AltTitle = this.AltTitle,
+
+ Original = this.Original,
+ OpenMSXSubType = this.OpenMSXSubType,
+ OpenMSXType = this.OpenMSXType,
+ Remark = this.Remark,
+ Boot = this.Boot,
+
+ Part = this.Part,
+ Features = this.Features,
+ AreaName = this.AreaName,
+ AreaSize = this.AreaSize,
+ AreaWidth = this.AreaWidth,
+ AreaEndianness = this.AreaEndianness,
+ Value = this.Value,
+ LoadFlag = this.LoadFlag,
+
+ Machine = this.Machine.Clone() as Machine,
+ Source = this.Source.Clone() as Source,
+ Remove = this.Remove,
+
+ Tag = this.Tag,
+ Analogs = this.Analogs,
+ };
+ }
+
+ #endregion
+
+ #region Comparision Methods
+
+ public override bool Equals(DatItem other)
+ {
+ // If we don't have a Port, return false
+ if (ItemType != other.ItemType)
+ return false;
+
+ // Otherwise, treat it as a Port
+ Port newOther = other as Port;
+
+ // If the Port information matches
+ return (Tag == newOther.Tag); // TODO: Handle DatItem_Analog*
+ }
+
+ #endregion
+
+ #region Filtering
+
+ ///
+ /// Check to see if a DatItem passes the filter
+ ///
+ /// Filter to check against
+ /// True if the item passed the filter, false otherwise
+ public override bool PassesFilter(Filter filter)
+ {
+ // Check common fields first
+ if (!base.PassesFilter(filter))
+ return false;
+
+ // Filter on tag
+ if (filter.DatItem_Tag.MatchesPositiveSet(Tag) == false)
+ return false;
+ if (filter.DatItem_Tag.MatchesNegativeSet(Tag) == true)
+ return false;
+
+ // TODO: Handle DatItem_Analog*
+
+ return true;
+ }
+
+ ///
+ /// Remove fields from the DatItem
+ ///
+ /// List of Fields to remove
+ public override void RemoveFields(List fields)
+ {
+ // Remove common fields first
+ base.RemoveFields(fields);
+
+ // Remove the fields
+ if (fields.Contains(Field.DatItem_Tag))
+ Tag = null;
+
+ if (fields.Contains(Field.DatItem_Analogs))
+ Analogs = null;
+
+ // TODO: Handle DatItem_Analog*
+ }
+
+ #endregion
+
+ #region Sorting and Merging
+
+ ///
+ /// Replace fields from another item
+ ///
+ /// DatItem to pull new information from
+ /// List of Fields representing what should be updated
+ public override void ReplaceFields(DatItem item, List fields)
+ {
+ // Replace common fields first
+ base.ReplaceFields(item, fields);
+
+ // If we don't have a Port to replace from, ignore specific fields
+ if (item.ItemType != ItemType.Port)
+ return;
+
+ // Cast for easier access
+ Port newItem = item as Port;
+
+ // Replace the fields
+ if (fields.Contains(Field.DatItem_Name))
+ Tag = newItem.Tag;
+
+ if (fields.Contains(Field.DatItem_Analogs))
+ Analogs = newItem.Analogs;
+
+ // TODO: Handle DatItem_Analog*
+ }
+
+ #endregion
+ }
+}
diff --git a/SabreTools.Library/Filtering/Filter.cs b/SabreTools.Library/Filtering/Filter.cs
index f9ca680c..3a644895 100644
--- a/SabreTools.Library/Filtering/Filter.cs
+++ b/SabreTools.Library/Filtering/Filter.cs
@@ -90,14 +90,6 @@ namespace SabreTools.Library.Filtering
public FilterItem Machine_Input_Control_Ways2 { get; private set; } = new FilterItem();
public FilterItem Machine_Input_Control_Ways3 { get; private set; } = new FilterItem();
- // Ports
- public FilterItem Machine_Ports { get; private set; } = new FilterItem() { Neutral = null };
- public FilterItem Machine_Port_Tag { get; private set; } = new FilterItem();
-
- // Ports.Analogs
- public FilterItem Machine_Port_Analogs { get; private set; } = new FilterItem() { Neutral = null };
- public FilterItem Machine_Port_Analog_Mask { get; private set; } = new FilterItem();
-
#endregion
#region Logiqx
@@ -293,6 +285,10 @@ namespace SabreTools.Library.Filtering
public FilterItem DatItem_FeatureStatus { get; private set; } = new FilterItem() { Positive = FeatureStatus.NULL, Negative = FeatureStatus.NULL };
public FilterItem DatItem_FeatureOverall { get; private set; } = new FilterItem() { Positive = FeatureStatus.NULL, Negative = FeatureStatus.NULL };
+ // Port.Analogs
+ public FilterItem DatItem_Analogs { get; private set; } = new FilterItem() { Neutral = null };
+ public FilterItem DatItem_Analog_Mask { get; private set; } = new FilterItem();
+
// Ram Option
public FilterItem DatItem_Content { get; private set; } = new FilterItem();
@@ -773,34 +769,20 @@ namespace SabreTools.Library.Filtering
Machine_Input_Control_Ways3.PositiveSet.Add(value);
break;
- // Ports
- case Field.Machine_Ports:
- if (negate || value.Equals("false", StringComparison.OrdinalIgnoreCase))
- Machine_Ports.Neutral = false;
- else
- Machine_Ports.Neutral = true;
- break;
-
- case Field.Machine_Port_Tag:
- if (negate)
- Machine_Port_Tag.NegativeSet.Add(value);
- else
- Machine_Port_Tag.PositiveSet.Add(value);
- break;
// Ports.Analogs
- case Field.Machine_Port_Analogs:
+ case Field.DatItem_Analogs:
if (negate || value.Equals("false", StringComparison.OrdinalIgnoreCase))
- Machine_Port_Analogs.Neutral = false;
+ DatItem_Analogs.Neutral = false;
else
- Machine_Port_Analogs.Neutral = true;
+ DatItem_Analogs.Neutral = true;
break;
- case Field.Machine_Port_Analog_Mask:
+ case Field.DatItem_Analog_Mask:
if (negate)
- Machine_Port_Analog_Mask.NegativeSet.Add(value);
+ DatItem_Analog_Mask.NegativeSet.Add(value);
else
- Machine_Port_Analog_Mask.PositiveSet.Add(value);
+ DatItem_Analog_Mask.PositiveSet.Add(value);
break;
#endregion
diff --git a/SabreTools.Library/Tools/Converters.cs b/SabreTools.Library/Tools/Converters.cs
index 1accfea3..1f70f01d 100644
--- a/SabreTools.Library/Tools/Converters.cs
+++ b/SabreTools.Library/Tools/Converters.cs
@@ -671,18 +671,6 @@ namespace SabreTools.Library.Tools
case "input_control_ways3":
return Field.Machine_Input_Control_Ways3;
- case "ports":
- return Field.Machine_Ports;
-
- case "port_tag":
- return Field.Machine_Port_Tag;
-
- case "port_analogs":
- return Field.Machine_Port_Analogs;
-
- case "port_analog_mask":
- return Field.Machine_Port_Analog_Mask;
-
#endregion
#region Logiqx
@@ -1115,6 +1103,13 @@ namespace SabreTools.Library.Tools
case "featureoverall":
return Field.DatItem_FeatureOverall;
+ // Port
+ case "analogs":
+ return Field.DatItem_Analogs;
+
+ case "analog_mask":
+ return Field.DatItem_Analog_Mask;
+
// Ram Option
case "content":
return Field.DatItem_Content;
@@ -1685,6 +1680,8 @@ namespace SabreTools.Library.Tools
return ItemType.Instance;
case "media":
return ItemType.Media;
+ case "port":
+ return ItemType.Port;
case "ramoption":
return ItemType.RamOption;
case "release":
@@ -1722,6 +1719,7 @@ namespace SabreTools.Library.Tools
"feature" => ItemType.Feature,
"instance" => ItemType.Instance,
"media" => ItemType.Media,
+ "port" => ItemType.Port,
"ramoption" => ItemType.RamOption,
"release" => ItemType.Release,
"rom" => ItemType.Rom,
@@ -2305,6 +2303,8 @@ namespace SabreTools.Library.Tools
return "instance";
case ItemType.Media:
return "media";
+ case ItemType.Port:
+ return "port";
case ItemType.RamOption:
return "ramoption";
case ItemType.Release:
@@ -2342,6 +2342,7 @@ namespace SabreTools.Library.Tools
ItemType.Feature => "feature",
ItemType.Instance => "instance",
ItemType.Media => "media",
+ ItemType.Port => "port",
ItemType.RamOption => "ramoption",
ItemType.Release => "release",
ItemType.Rom => "rom",