From 83580fcd8a219da08b1f713959fcd8797a6f113c Mon Sep 17 00:00:00 2001 From: Carlos Polop Date: Wed, 21 Jan 2026 01:15:38 +0100 Subject: [PATCH] Re-enable winPEAS tests and add linPEAS builder checks --- .github/workflows/CI-master_tests.yml | 7 +++- .github/workflows/PR-tests.yml | 7 ++++ linPEAS/tests/test_builder.py | 40 +++++++++++++++++++ .../winPEASexe/Tests/ArgumentParsingTests.cs | 36 +++++++++++++++++ winPEAS/winPEASexe/Tests/winPEAS.Tests.csproj | 3 +- 5 files changed, 90 insertions(+), 3 deletions(-) create mode 100644 linPEAS/tests/test_builder.py create mode 100644 winPEAS/winPEASexe/Tests/ArgumentParsingTests.cs diff --git a/.github/workflows/CI-master_tests.yml b/.github/workflows/CI-master_tests.yml index 842ef3c..0c3539f 100644 --- a/.github/workflows/CI-master_tests.yml +++ b/.github/workflows/CI-master_tests.yml @@ -51,8 +51,8 @@ jobs: run: msbuild $env:Solution_Path # Execute all unit tests in the solution - #- name: Execute unit tests - # run: dotnet test $env:Solution_Path + - name: Execute unit tests + run: dotnet test $env:Solution_Path --configuration $env:Configuration # Build & update all versions - name: Build all versions @@ -230,6 +230,9 @@ jobs: python3 -m builder.linpeas_builder --all --output linpeas_fat.sh python3 -m builder.linpeas_builder --all-no-fat --output linpeas.sh python3 -m builder.linpeas_builder --small --output linpeas_small.sh + + - name: Run linPEAS builder tests + run: python3 -m unittest discover -s linPEAS/tests -p "test_*.py" # Build linpeas binaries - name: Build linpeas binaries diff --git a/.github/workflows/PR-tests.yml b/.github/workflows/PR-tests.yml index 5a58e73..a269d6f 100644 --- a/.github/workflows/PR-tests.yml +++ b/.github/workflows/PR-tests.yml @@ -43,6 +43,10 @@ jobs: # build - name: run MSBuild run: msbuild $env:Solution_Path + + # Execute unit tests in the solution + - name: Execute unit tests + run: dotnet test $env:Solution_Path --configuration $env:Configuration # Build all versions - name: Build all versions @@ -123,6 +127,9 @@ jobs: python3 -m builder.linpeas_builder --all --output linpeas_fat.sh python3 -m builder.linpeas_builder --all-no-fat --output linpeas.sh python3 -m builder.linpeas_builder --small --output linpeas_small.sh + + - name: Run linPEAS builder tests + run: python3 -m unittest discover -s linPEAS/tests -p "test_*.py" # Run linpeas help as quick test - name: Run linpeas help diff --git a/linPEAS/tests/test_builder.py b/linPEAS/tests/test_builder.py new file mode 100644 index 0000000..d0e8d9a --- /dev/null +++ b/linPEAS/tests/test_builder.py @@ -0,0 +1,40 @@ +import os +import stat +import subprocess +import tempfile +import unittest +from pathlib import Path + + +class LinpeasBuilderTests(unittest.TestCase): + def setUp(self): + self.repo_root = Path(__file__).resolve().parents[2] + self.linpeas_dir = self.repo_root / "linPEAS" + + def _run_builder(self, args, output_path): + cmd = ["python3", "-m", "builder.linpeas_builder"] + args + ["--output", str(output_path)] + result = subprocess.run(cmd, cwd=str(self.linpeas_dir), capture_output=True, text=True) + if result.returncode != 0: + raise AssertionError( + f"linpeas_builder failed:\nstdout:\n{result.stdout}\nstderr:\n{result.stderr}" + ) + + def test_small_build_creates_executable(self): + with tempfile.TemporaryDirectory() as tmpdir: + output_path = Path(tmpdir) / "linpeas_small.sh" + self._run_builder(["--small"], output_path) + self.assertTrue(output_path.exists(), "linpeas_small.sh was not created.") + mode = output_path.stat().st_mode + self.assertTrue(mode & stat.S_IXUSR, "linpeas_small.sh is not executable.") + + def test_include_exclude_modules(self): + with tempfile.TemporaryDirectory() as tmpdir: + output_path = Path(tmpdir) / "linpeas_include.sh" + self._run_builder(["--include", "system_information,container", "--exclude", "container"], output_path) + content = output_path.read_text(encoding="utf-8", errors="ignore") + self.assertIn("Operative system", content) + self.assertNotIn("Am I Containered?", content) + + +if __name__ == "__main__": + unittest.main() diff --git a/winPEAS/winPEASexe/Tests/ArgumentParsingTests.cs b/winPEAS/winPEASexe/Tests/ArgumentParsingTests.cs new file mode 100644 index 0000000..427038c --- /dev/null +++ b/winPEAS/winPEASexe/Tests/ArgumentParsingTests.cs @@ -0,0 +1,36 @@ +using System; +using System.Reflection; +using Microsoft.VisualStudio.TestTools.UnitTesting; +using winPEAS.Checks; + +namespace winPEAS.Tests +{ + [TestClass] + public class ArgumentParsingTests + { + private static bool InvokeIsNetworkTypeValid(string arg) + { + var method = typeof(Checks).GetMethod("IsNetworkTypeValid", BindingFlags.NonPublic | BindingFlags.Static); + Assert.IsNotNull(method, "IsNetworkTypeValid method not found."); + return (bool)method.Invoke(null, new object[] { arg }); + } + + [TestMethod] + public void ShouldAcceptValidNetworkTypes() + { + Assert.IsTrue(InvokeIsNetworkTypeValid("-network=auto")); + Assert.IsTrue(InvokeIsNetworkTypeValid("-network=10.10.10.10")); + Assert.IsTrue(InvokeIsNetworkTypeValid("-network=10.10.10.10/24")); + Assert.IsTrue(InvokeIsNetworkTypeValid("-network=10.10.10.10,10.10.10.20")); + } + + [TestMethod] + public void ShouldRejectInvalidNetworkTypes() + { + Assert.IsFalse(InvokeIsNetworkTypeValid("-network=")); + Assert.IsFalse(InvokeIsNetworkTypeValid("-network=10.10.10.999")); + Assert.IsFalse(InvokeIsNetworkTypeValid("-network=10.10.10.10/64")); + Assert.IsFalse(InvokeIsNetworkTypeValid("-network=not-an-ip")); + } + } +} diff --git a/winPEAS/winPEASexe/Tests/winPEAS.Tests.csproj b/winPEAS/winPEASexe/Tests/winPEAS.Tests.csproj index a494570..bcb93f6 100644 --- a/winPEAS/winPEASexe/Tests/winPEAS.Tests.csproj +++ b/winPEAS/winPEASexe/Tests/winPEAS.Tests.csproj @@ -95,6 +95,7 @@ + @@ -133,4 +134,4 @@ - \ No newline at end of file +