Skip to content

Fix atexec task execution on 2025 servers#1251

Open
azoxlpf wants to merge 1 commit into
Pennyw0rth:mainfrom
azoxlpf:fix/atexec-2025
Open

Fix atexec task execution on 2025 servers#1251
azoxlpf wants to merge 1 commit into
Pennyw0rth:mainfrom
azoxlpf:fix/atexec-2025

Conversation

@azoxlpf
Copy link
Copy Markdown
Contributor

@azoxlpf azoxlpf commented May 28, 2026

Description

Fixes TSCH_EXEC / schtask_as on recent Windows (e.g. Server 2025) by calling hSchRpcRun after task registration (as impacket’s atexec does) and treating SCHED_S_TASK_HAS_NOT_RUN (0x41303) as a transient state during SchRpcGetLastRunInfo polling instead of failing and deleting the task early.

Type of change

Insert an "x" inside the brackets for relevant items (do not delete options)

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to not work as expected)
  • Deprecation of feature or functionality
  • This change requires a documentation update
  • This requires a third party update (such as Impacket, Dploot, lsassy, etc)
  • This PR was created with the assistance of AI (list what type of assistance, tool(s)/model(s) in the description)

Setup guide for the review

run nxc smb 192.168.56.100 -u 'user' -p 'password' -M schtask_as -o USER='user'' CMD='whoami'

Screenshots (if appropriate):

Before :

image

After :

image

Checklist:

Insert an "x" inside the brackets for completed and relevant items (do not delete options)

  • I have ran Ruff against my changes (poetry: poetry run ruff check ., use --fix to automatically fix what it can)
  • I have added or updated the tests/e2e_commands.txt file if necessary (new modules or features are required to be added to the e2e tests)
  • If reliant on changes of third party dependencies, such as Impacket, dploot, lsassy, etc, I have linked the relevant PRs in those projects
  • I have linked relevant sources that describes the added technique (blog posts, documentation, etc)
  • I have performed a self-review of my own code (not an AI review)
  • I have commented my code, particularly in hard-to-understand areas
  • I have made corresponding changes to the documentation (PR here: https://github.com/Pennyw0rth/NetExec-Wiki)

@NeffIsBack
Copy link
Copy Markdown
Member

Hi and thanks!

Could it be that the Win2025 server is just too slow and the error reporting is different on Win2025? The schtask created by atexec has the trigger "RegistrationTrigger" which should execute on creation. Either Win2025 is too slow, maybe bugged or even the trigger doesn't exist anymore?

@NeffIsBack NeffIsBack added the bug-fix This Pull Request fixes a bug label May 28, 2026
@Dfte
Copy link
Copy Markdown
Contributor

Dfte commented May 28, 2026

WinServ2025 is fucking trash bruuuh, remember the smb timeout -_- slow as fuck
Shouldn't we just rise the timeout value ?

@azoxlpf
Copy link
Copy Markdown
Contributor Author

azoxlpf commented May 28, 2026

Tried a 60s timeout first didn’t help, the task still never ran. Imo the issue is the RegistrationTrigger not firing on Server 2025, not how long we wait

@NeffIsBack
Copy link
Copy Markdown
Member

What happens if you configure one through the UI? Does this not work either? Is this trigger simply broken on Win 2025?

@azoxlpf
Copy link
Copy Markdown
Contributor Author

azoxlpf commented May 29, 2026

UI / local PowerShell : same XML with RegistrationTrigger + NETBIOS\User: works fine (task runs, output file created within a few seconds). So the trigger isn’t broken on Win 2025 in general.

Remote TSCH (NXC) : with only 0x41303 handled as transient and a 60s poll loop (no SchRpcRun): the task never runs, we get 41303 for the full 60s, then timeout, no output file.

With SchRpcRun after registration: it works.

So it’s not a broken trigger on 2025, it’s the remote registration path not starting the task reliably, we need an explicit SchRpcRun plus treating 0x41303 as not yet run during polling (older Windows often return an empty last-run time instead of raising that as an RPC error).

@NeffIsBack
Copy link
Copy Markdown
Member

Such a weird behavior. I would bet this is a bug in Win Server 2025, but just for getting it to work, let's add it.
Just from the code it seems tho that tasks that would run automatically (>Win2025) are triggered twice now tho. Can you check that? Maybe this should just happen if we receive that error from the Win2025 DC.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug-fix This Pull Request fixes a bug

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants