peass-ng/PEASS-ng · error · System.ArgumentOutOfRangeException

A maximum of 32 actions is allowed within a single task.

Error message

A maximum of 32 actions is allowed within a single task.

What it means

When an Action is bound to a Task Scheduler v2 task definition, the library checks the current count against ActionCollection.MaxActions (32, the Windows Task Scheduler limit). If 32 or more actions already exist, Bind throws ArgumentOutOfRangeException. Windows itself will not accept more than 32 actions in one task.

Source

Thrown at winPEAS/winPEASexe/winPEAS/TaskScheduler/Action.cs:209

        {
            if (Id != null)
                iTask.SetDataItem("ActionId", Id);
            var bindable = this as IBindAsExecAction;
            if (bindable != null)
                iTask.SetDataItem("ActionType", InternalActionType.ToString());
            unboundValues.TryGetValue("Path", out var o);
            iTask.SetApplicationName(bindable != null ? ExecAction.PowerShellPath : o?.ToString() ?? string.Empty);
            unboundValues.TryGetValue("Arguments", out o);
            iTask.SetParameters(bindable != null ? ExecAction.BuildPowerShellCmd(ActionType.ToString(), GetPowerShellCommand()) : o?.ToString() ?? string.Empty);
            unboundValues.TryGetValue("WorkingDirectory", out o);
            iTask.SetWorkingDirectory(o?.ToString() ?? string.Empty);
        }

        internal virtual void Bind(ITaskDefinition iTaskDef)
        {
            var iActions = iTaskDef.Actions;
            if (iActions.Count >= ActionCollection.MaxActions)
                throw new ArgumentOutOfRangeException(nameof(iTaskDef), @"A maximum of 32 actions is allowed within a single task.");
            CreateV2Action(iActions);
            Marshal.ReleaseComObject(iActions);
            foreach (var key in unboundValues.Keys)
            {
                try { ReflectionHelper.SetProperty(iAction, key, unboundValues[key]); }
                catch (TargetInvocationException tie) { throw tie.InnerException; }
                catch { }
            }
            unboundValues.Clear();
        }

        /// <summary>Copies the properties from another <see cref="Action"/> the current instance.</summary>
        /// <param name="sourceAction">The source <see cref="Action"/>.</param>
        internal virtual void CopyProperties([NotNull] Action sourceAction) => Id = sourceAction.Id;

        internal abstract void CreateV2Action(IActionCollection iActions);

        internal abstract string GetPowerShellCommand();

View on GitHub (pinned to 53fb989abc)

Solutions

  1. Check ActionCollection.Count before Add and cap at 32; split overflow into additional tasks
  2. Group related commands into a single ExecAction running a script/cmd wrapper to reduce action count
  3. Clear or rebuild the action collection when re-configuring a task instead of appending each time
  4. Catch ArgumentOutOfRangeException in Bind/Add and surface a clear 'task full' message

Example fix

// before
foreach (var exe in exes) task.Definition.Actions.Add(new ExecAction(exe, args));
// after
foreach (var batch in exes.Chunk(32))
{
    var t = TaskService.Instance.CreateTask(...);
    foreach (var exe in batch) t.Definition.Actions.Add(new ExecAction(exe, args));
    t.RegisterTaskDefinition(...);
}
Defensive patterns

Strategy: validation

Validate before calling

if (actions.Count + newActions.Count > 32)
    throw new InvalidOperationException("Task action limit (32) would be exceeded; split into multiple tasks.");

Try / catch

try { def.Actions.Add(action); }
catch (ArgumentOutOfRangeException)
{
    log.Error("Task already has the maximum 32 actions; create an additional task.");
}

Prevention

When it happens

Trigger: Adding a 33rd action to a task definition before registration; programmatically building a task from a loop/list of executables without capping the list; deserializing a task XML with more than 32 actions.

Common situations: Bulk-deployment scripts that create one task with an unbounded list of commands; migration tools importing legacy batch scripts into a single task; generated configurations where each update appends an action instead of replacing them.

Related errors


AI-assisted analysis of peass-ng/PEASS-ng@53fb989abc (2026-09-02). Data as JSON: /api/errors/7e09cfcdabf8b0c3. Report an issue: GitHub.