chore: organize solution into module folders (Core/Server/Drivers/Client/Tooling)

Group all 69 projects into category subfolders under src/ and tests/ so the
Rider Solution Explorer mirrors the module structure. Folders: Core, Server,
Drivers (with a nested Driver CLIs subfolder), Client, Tooling.

- Move every project folder on disk with git mv (history preserved as renames).
- Recompute relative paths in 57 .csproj files: cross-category ProjectReferences,
  the lib/ HintPath+None refs in Driver.Historian.Wonderware, and the external
  mxaccessgw refs in Driver.Galaxy and its test project.
- Rebuild ZB.MOM.WW.OtOpcUa.slnx with nested solution folders.
- Re-prefix project paths in functional scripts (e2e, compliance, smoke SQL,
  integration, install).

Build green (0 errors); unit tests pass. Docs left for a separate pass.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Joseph Doherty
2026-05-17 01:55:28 -04:00
parent 69f02fed7f
commit a25593a9c6
1044 changed files with 365 additions and 343 deletions
@@ -0,0 +1,120 @@
namespace ZB.MOM.WW.OtOpcUa.Driver.FOCAS.Wire;
/// <summary>
/// PMC address-letter → FOCAS <c>ADR_*</c> numeric code. Values are the FOCAS/2 wire
/// constants passed as the <c>area</c> argument on <c>pmc_rdpmcrng</c>
/// (G=0, F=1, Y=2, X=3, A=4, R=5, T=6, K=7, C=8, D=9, E=10).
/// </summary>
public enum FocasPmcArea : short
{
G = 0,
F = 1,
Y = 2,
X = 3,
A = 4,
R = 5,
T = 6,
K = 7,
C = 8,
D = 9,
E = 10,
}
/// <summary>
/// PMC data-type numeric codes per FOCAS/2: <c>Byte=0</c>, <c>Word=1</c>, <c>Long=2</c>,
/// <c>Real=4</c>, <c>Double=5</c>. Passed as the <c>data_type</c> argument on
/// <c>pmc_rdpmcrng</c>.
/// </summary>
public enum FocasPmcDataType : short
{
Byte = 0,
Word = 1,
Long = 2,
Real = 4,
Double = 5,
}
/// <summary>
/// CNC operation mode as reported by <c>cnc_rdopmode</c>. Values are the FOCAS-defined
/// mode codes; see <see cref="FocasOperationModeExtensions.ToText"/> for the canonical
/// operator-facing labels.
/// </summary>
public enum FocasOperationMode : short
{
Mdi = 0,
Auto = 1,
TJog = 2,
Edit = 3,
Handle = 4,
Jog = 5,
TeachInHandle = 6,
Reference = 7,
Remote = 8,
Test = 9,
}
/// <summary>Extension helpers over <see cref="FocasOperationMode"/>.</summary>
public static class FocasOperationModeExtensions
{
/// <summary>
/// Canonical operator-facing label for an operation mode (e.g. <c>"AUTO"</c>,
/// <c>"EDIT"</c>). Unknown codes fall back to the raw numeric value as a string
/// so the UI still shows something interpretable.
/// </summary>
public static string ToText(this FocasOperationMode mode) => mode switch
{
FocasOperationMode.Mdi => "MDI",
FocasOperationMode.Auto => "AUTO",
FocasOperationMode.TJog => "T-JOG",
FocasOperationMode.Edit => "EDIT",
FocasOperationMode.Handle => "HANDLE",
FocasOperationMode.Jog => "JOG",
FocasOperationMode.TeachInHandle => "TEACH-IN-HANDLE",
FocasOperationMode.Reference => "REFERENCE",
FocasOperationMode.Remote => "REMOTE",
FocasOperationMode.Test => "TEST",
_ => ((short)mode).ToString(),
};
}
/// <summary>
/// Letter → <see cref="FocasPmcArea"/> lookup. Used by <see cref="WireFocasClient"/> to
/// translate a parsed <see cref="FocasAddress.PmcLetter"/> into the wire code expected by
/// <c>pmc_rdpmcrng</c>.
/// </summary>
internal static class FocasPmcAreaLookup
{
public static FocasPmcArea? FromLetter(string letter) => letter.ToUpperInvariant() switch
{
"G" => FocasPmcArea.G,
"F" => FocasPmcArea.F,
"Y" => FocasPmcArea.Y,
"X" => FocasPmcArea.X,
"A" => FocasPmcArea.A,
"R" => FocasPmcArea.R,
"T" => FocasPmcArea.T,
"K" => FocasPmcArea.K,
"C" => FocasPmcArea.C,
"D" => FocasPmcArea.D,
"E" => FocasPmcArea.E,
_ => null,
};
}
/// <summary>
/// <see cref="FocasDataType"/> → <see cref="FocasPmcDataType"/> mapping for wire PMC
/// reads. Bit reads collapse to byte — the caller extracts the bit from the returned
/// value.
/// </summary>
internal static class FocasPmcDataTypeLookup
{
public static FocasPmcDataType FromFocasDataType(FocasDataType t) => t switch
{
FocasDataType.Bit or FocasDataType.Byte => FocasPmcDataType.Byte,
FocasDataType.Int16 => FocasPmcDataType.Word,
FocasDataType.Int32 => FocasPmcDataType.Long,
FocasDataType.Float32 => FocasPmcDataType.Real,
FocasDataType.Float64 => FocasPmcDataType.Double,
_ => FocasPmcDataType.Byte,
};
}