From 84ff71ca9d338934383c6db42ae68da0f8bd4f31 Mon Sep 17 00:00:00 2001 From: Jozef Izso Date: Fri, 23 Jan 2026 17:56:39 +0100 Subject: [PATCH 1/2] Change sample Visual Basic files to use Windows line endings --- tests/VbaCompiler.Tests/data/.gitattributes | 2 ++ tests/VbaCompiler.Tests/data/Class.vb | 9 +++++++++ tests/VbaCompiler.Tests/data/Module.vb | 20 ++++++++++++++++++++ 3 files changed, 31 insertions(+) create mode 100644 tests/VbaCompiler.Tests/data/.gitattributes diff --git a/tests/VbaCompiler.Tests/data/.gitattributes b/tests/VbaCompiler.Tests/data/.gitattributes new file mode 100644 index 0000000..97b2997 --- /dev/null +++ b/tests/VbaCompiler.Tests/data/.gitattributes @@ -0,0 +1,2 @@ +# VBA source files must have Windows line endings (CRLF) +*.vb text eol=crlf diff --git a/tests/VbaCompiler.Tests/data/Class.vb b/tests/VbaCompiler.Tests/data/Class.vb index e69de29..cf54db4 100644 --- a/tests/VbaCompiler.Tests/data/Class.vb +++ b/tests/VbaCompiler.Tests/data/Class.vb @@ -0,0 +1,9 @@ +Public Property Name As String + +Public Sub Initialize() + Name = "John Doe" +End Sub + +Public Function GetGreeting() As String + GetGreeting = "Hello, " & Name & "!" +End Function diff --git a/tests/VbaCompiler.Tests/data/Module.vb b/tests/VbaCompiler.Tests/data/Module.vb index e69de29..c315a32 100644 --- a/tests/VbaCompiler.Tests/data/Module.vb +++ b/tests/VbaCompiler.Tests/data/Module.vb @@ -0,0 +1,20 @@ +Attribute VB_Name = "Module1" +Option Explicit + +' Sample module for VBA compiler testing +Public Sub HelloWorld() + Debug.Print "Hello, World!" +End Sub + +Public Function Add(ByVal a As Integer, ByVal b As Integer) As Integer + Add = a + b +End Function + +Public Function Multiply(ByVal x As Double, ByVal y As Double) As Double + Multiply = x * y +End Function + +Private Sub InternalMethod() + ' This is a private helper method + Debug.Print "Internal method called" +End Sub From e94476a3972cc16ec2ba8d71c12f22cb1d85aa80 Mon Sep 17 00:00:00 2001 From: Jozef Izso Date: Fri, 23 Jan 2026 18:06:18 +0100 Subject: [PATCH 2/2] Update the `VbaProjectRoundTripTests` to ensure the compiled source code matches original content Co-Authored-By: Claude --- .../Streams/VbaProjectRoundTripTests.cs | 36 +++++++++++++------ 1 file changed, 26 insertions(+), 10 deletions(-) diff --git a/tests/VbaCompiler.Tests/Streams/VbaProjectRoundTripTests.cs b/tests/VbaCompiler.Tests/Streams/VbaProjectRoundTripTests.cs index 89ed6b9..5564494 100644 --- a/tests/VbaCompiler.Tests/Streams/VbaProjectRoundTripTests.cs +++ b/tests/VbaCompiler.Tests/Streams/VbaProjectRoundTripTests.cs @@ -2,6 +2,7 @@ // Licensed under MIT-style license (see LICENSE.txt file). using System; +using System.Collections.Generic; using System.IO; using System.Linq; using System.Text; @@ -24,6 +25,8 @@ class VbaProjectRoundTripTests { private byte[] _compiledVbaProject = null!; private byte[] _compiledMultiModuleVbaProject = null!; + private string _testModuleExpectedSource = null!; + private string _classExpectedSource = null!; [SetUp] public void Setup() @@ -34,6 +37,12 @@ public void Setup() var modulePath = Path.Combine(sourcePath, "TestModule.vb"); var classPath = Path.Combine(sourcePath, "Class.vb"); + // Generate expected compiled source using ModuleUnit (includes VBA headers) + var testModule = ModuleUnit.FromFile(modulePath, ModuleUnitType.Module, null); + var classModule = ModuleUnit.FromFile(classPath, ModuleUnitType.Class, null); + _testModuleExpectedSource = testModule.ToModuleCode(); + _classExpectedSource = classModule.ToModuleCode(); + // Compile single-module project var compiler = CreateTestCompiler("RoundTripTest"); compiler.AddModule(modulePath); @@ -140,7 +149,7 @@ public void CompileVbaProject_ShouldProduceReadableModules() } [Test] - public void CompileVbaProject_DecompiledCodeShouldContainOriginalSource() + public void CompileVbaProject_DecompiledCodeShouldMatchOriginalSource() { using var compoundFile = new CompoundFile(new MemoryStream(_compiledVbaProject)); var vbaStorage = compoundFile.RootStorage.GetStorage("VBA"); @@ -168,16 +177,12 @@ public void CompileVbaProject_DecompiledCodeShouldContainOriginalSource() var decompressedSource = Encoding.GetEncoding(1252).GetString(VbaCompression.Decompress(moduleCode)); - ClassicAssert.IsTrue(decompressedSource.Contains("HelloWorld"), - "Decompiled source should contain 'HelloWorld' function"); - ClassicAssert.IsTrue(decompressedSource.Contains("AddNumbers"), - "Decompiled source should contain 'AddNumbers' function"); - ClassicAssert.IsTrue(decompressedSource.Contains("MsgBox"), - "Decompiled source should contain 'MsgBox' call"); + ClassicAssert.AreEqual(_testModuleExpectedSource, decompressedSource, + "Decompiled source should exactly match the original source with VBA headers"); } [Test] - public void CompileVbaProject_WithMultipleModules_AllShouldBeDecompilable() + public void CompileVbaProject_WithMultipleModules_AllShouldMatchOriginalSource() { using var compoundFile = new CompoundFile(new MemoryStream(_compiledMultiModuleVbaProject)); var vbaStorage = compoundFile.RootStorage.GetStorage("VBA"); @@ -192,6 +197,13 @@ public void CompileVbaProject_WithMultipleModules_AllShouldBeDecompilable() var modules = VbadDecompiler.DirStream.GetModules(dirData).ToList(); ClassicAssert.AreEqual(2, modules.Count, "Should have exactly 2 modules (TestModule and Class)"); + // Map of module names to their expected source + var expectedSources = new Dictionary + { + { "TestModule", _testModuleExpectedSource }, + { "Class", _classExpectedSource } + }; + foreach (var module in modules) { var moduleStream = vbaStorage.GetStream(module.Name); @@ -205,8 +217,12 @@ public void CompileVbaProject_WithMultipleModules_AllShouldBeDecompilable() ClassicAssert.Greater(moduleCode.Length, 0, $"Module '{module.Name}' code after offset is empty"); - var decompressedCode = VbaCompression.Decompress(moduleCode); - ClassicAssert.IsNotNull(decompressedCode, $"Module '{module.Name}' should decompress successfully"); + var decompressedSource = Encoding.GetEncoding(1252).GetString(VbaCompression.Decompress(moduleCode)); + + ClassicAssert.IsTrue(expectedSources.ContainsKey(module.Name!), + $"Unexpected module '{module.Name}' found in compiled project"); + ClassicAssert.AreEqual(expectedSources[module.Name!], decompressedSource, + $"Decompiled source for module '{module.Name}' should exactly match the original source with VBA headers"); } } }