Repository navigation
Installation
| Item | Value |
|---|---|
| Operating system | Windows 10 / Windows 11 (supportedOS GUID {8e0f7a12-…} in both app manifests) |
| Architectures | x64 and ARM64 (win-x64, win-arm64 runtime identifiers) |
| .NET runtime | None required at run time — both executables are published self-contained, single-file, ReadyToRun |
| Privileges | Installation and service registration require elevation; the service runs as LocalSystem
|
Nothing in the repo declares a minimum Windows build beyond the Windows 10/11 compatibility GUID.
The service reads the Security event log, which is only readable by LocalSystem and
administrators — see Windows Session Model.
| File | Role |
|---|---|
C:\Program Files\StartSet\managedstatekeeper.exe |
CLI and execution engine |
C:\Program Files\StartSet\StartSetService.exe |
Windows service host (StartSet) |
The install directory is added to the machine PATH by the packaged install scripts and by the
MSI's Environment element, so managedstatekeeper is callable by name in new shells.
C:\ProgramData\ManagedState and all payload directories are created by the installer scripts,
by the MSI's CreateFolder components, and again by the service and CLI at run time
(ExecutionEngine.EnsureDirectories). A missing directory is not an error.
Every tagged release publishes startset-x64.zip and startset-arm64.zip containing the two
executables, unsigned. This is the only artifact the public release workflow uploads.
Extract to the install directory:
Expand-Archive .\startset-x64.zip -DestinationPath 'C:\Program Files\StartSet' -ForceRegister and start the service:
sc.exe create StartSet binPath="C:\Program Files\StartSet\StartSetService.exe" start=auto
sc.exe description StartSet "StartSet - Script automation at boot, login, and on-demand"
sc.exe start StartSetRegister the event log source so warnings and errors land in the Application log under a recognised source:
New-EventLog -LogName Application -Source StartSetbuild\msi\Package.wxs is a WiX v6 package definition (WixToolset.Sdk/6.0.0). It installs
per-machine into ProgramFiles64Folder\StartSet, creates every payload directory, adds the
install directory to the system PATH, installs the StartSet service as LocalSystem with
Start="auto", and starts it on install / stops and removes it on uninstall. MajorUpgrade is
configured with Schedule="afterInstallValidate", so upgrades replace in place.
The upgrade code is stable across versions:
7E4F8A2D-3B5C-4D6E-9F1A-2C8D4E5F6A7B
Install silently:
msiexec.exe /i StartSet-<version>-x64.msi /qn /l*v "$env:TEMP\startset_install.log"Note that build.ps1's MSI path does not invoke the .wixproj — it stages a payload/scripts/
build-info.yaml tree and hands it to cimipkg.exe. See Development.
build\nupkg\StartSet.nuspec.template produces StartSet-x64 / StartSet-arm64 packages
carrying the executables under tools\. These are consumed by package managers that install from
a NuGet feed; the nuspec itself performs no service registration, so pair it with the post-install
steps above.
build.ps1 can also emit a cimipkg .pkg (payload + preinstall.ps1 / postinstall.ps1 +
build-info.yaml) and, when IntuneWinAppUtil.exe is on PATH, a .intunewin wrapper for
Intune deployment. The packaged postinstall.ps1 is what creates the directories, sets PATH,
deletes any existing StartSet service, recreates it as automatic-start, and starts it;
preinstall.ps1 stops a running service first.
See Development.
GitHub Actions builds and publishes unsigned binaries (build.ps1 -NoSign -Binaries). Sign
them with your organisation's certificate before distributing to a fleet.
$cert = "Your Certificate Name"
$timestampUrl = "http://timestamp.digicert.com"
Get-ChildItem -Recurse -Include *.exe,*.dll | ForEach-Object {
signtool sign /fd SHA256 /tr $timestampUrl /td SHA256 /n $cert $_.FullName
}Sign MSIs separately, after the binaries inside them have been signed and the package rebuilt:
Get-ChildItem -Filter "StartSet-*.msi" | ForEach-Object {
signtool sign /fd SHA256 /tr $timestampUrl /td SHA256 /n $cert $_.FullName
}build.ps1 will also sign during the build when a certificate is available — see
Development for -Sign, -Thumbprint, -SignMSI and the STARTSET_CERT_CN /
STARTSET_CERT_SUBJECT environment variables.
Check the version. The CLI prints Major.MM.DD.HHMM, derived from the assembly version that
build.ps1 stamps as yyyy.MM.dd.HHmm:
managedstatekeeper --versionConfirm the service is registered as LocalSystem and running:
Get-CimInstance Win32_Service -Filter "Name='StartSet'" | Select-Object State, StartMode, StartNameConfirm the payload tree exists:
Get-ChildItem C:\ProgramData\ManagedStateExercise the engine end to end without a reboot or logon:
managedstatekeeper process boot-everyA session directory should appear under C:\ProgramData\ManagedState\logs\<today>\<HHmm>\.
MSI-installed:
msiexec.exe /x StartSet-<version>-x64.msi /qnManually installed:
sc.exe stop StartSet
sc.exe delete StartSet
Remove-Item 'C:\Program Files\StartSet' -Recurse -ForceNeither route removes C:\ProgramData\ManagedState. Payloads, Config.yaml, the run-once
ledgers, logs and reports survive uninstall — deliberately, so a reinstall does not re-run every
*-once payload. Remove it explicitly if you want a clean slate:
Remove-Item 'C:\ProgramData\ManagedState' -Recurse -ForceStartSet — MIT licensed — windowsadmins/startset — a Windows port of macadmins/outset.
StartSet
How it works
Migrating
Operating
Contributing