InteractiveBeacon tasks don't seem to execute
thespicybyte opened this issue ยท 8 comments
Version: sliver-py==0.0.16
I am attempting to execute a tasks when a new beacon is registered using code based on the interacting with beacons (https://sliverpy.readthedocs.io/en/latest/getting-started.html#interactive-beacons)
import os
import asyncio
from sliver import SliverClientConfig, SliverClient, client_pb2
async def main():
client = await login(CONFIG_PATH)
async for event in client.on('beacon-registered'):
beacon_id = event.Data[2:38].decode()
beacon = await client.interact_beacon(beacon_id)
print('new beacon registered: %s' % beacon.beacon_id)
print('Hostname: %s' % beacon.hostname)
pwd_task = await beacon.pwd()
pwd = await pwd_task
print('PWD: %s' % pwd)
if __name__ == '__main__':
loop = asyncio.get_event_loop()
loop.run_until_complete(main())
Output (when beacon is executed):
new beacon registered: 0b1d292c-bc04-4dc0-83d8-7fda5d22862e
Hostname: client1
I get my future object but it just hangs there indefinitely. I also attempted with a file upload and never saw the file appear on target which makes me think it's not executing. Also not seeing anything in sliver.log
which would indicate execution as well.
Update: I tried from the server and it worked. There is a difference in python versions so maybe that's causing it? Python 3.9.7 on server Python 3.10.1 on client.
Not sure, I'll have to play around debug it a bit more. I'm don't think it would be a Python version problem, but hard to say.
Looks like it was a python version issue. Looking at the asyncio docs for asyncio.get_event_loop() it states "Deprecated since version 3.10: Deprecation warning is emitted if there is no running event loop. In future Python releases, this function will be an alias of get_running_loop()."
Interestingly though, get_event_loop()
was working for me on sessions, for example, and it only seemed to break when we called an async method such as tasking a beacon. Also, if you swap it out directly for get_running_loop()
you get a runtime error:
loop = asyncio.get_running_loop()
RuntimeError: no running event loop
Either way, the docs suggested using asyncio.run()
instead so I gave that a try and it appears to be working.
if __name__ == '__main__':
asyncio.run(main())
I think I might have been a little too optimistic... Although I don't get any warnings at startup anymore and it works with one beacon, when I add any more it seems to get hung up and throws some errors. My ultimate goal is to have a script run along side the server that monitors events for new beacon registrations and then run a few commands. When I run the script above and have a beacon register I get:
new beacon registered: 91a7d7c4-c2fb-4fb8-92db-ab91e7aad2dd
Hostname: client1
PWD: Path: "C:\\Users\\Administrator\\Desktop"
And in the sliver client:
[*] Beacon 91a7d7c4 BEAUTIFUL_ASPECT - tcp([::1]:46968)->192.168.254.1 (client1) - windows/amd64 - Tue, 01 Mar 2022 22:38:11 EST
[*] spicy2 has joined the game
sliver (BEAUTIFUL_ASPECT) > use 91a7d7c4-c2fb-4fb8-92db-ab91e7aad2dd
[*] Active beacon BEAUTIFUL_ASPECT (91a7d7c4-c2fb-4fb8-92db-ab91e7aad2dd)
sliver (BEAUTIFUL_ASPECT) > tasks
ID State Message Type Created Sent Completed
========== =========== ============== =============================== =============================== ===============================
66ffaadd completed Pwd Tue, 01 Mar 2022 22:38:11 EST Tue, 01 Mar 2022 22:38:12 EST Tue, 01 Mar 2022 22:38:12 EST
That's exactly what I want (wont care about the output of the command once it goes to live but the errors persisted with or without the waiting for results).
But now when I start a second beacon...
new beacon registered: 83a75a79-205e-493a-b19f-9bfc37a99dcd
Hostname: client1
PWD: Path: "C:\\Users\\Administrator\\Desktop"
'5b825908-8c01-4684-8491-d85b7a82f8ab'
Traceback (most recent call last):
File "/usr/local/lib/python3.9/dist-packages/sliver/beacon.py", line 75, in taskresult_events
task_future, pb_object = self.beacon_tasks[beacon_task.ID]
KeyError: '5b825908-8c01-4684-8491-d85b7a82f8ab'
sliver (BEAUTIFUL_ASPECT) > use 83a75a79-205e-493a-b19f-9bfc37a99dcd
[*] Active beacon BEAUTIFUL_ASPECT (83a75a79-205e-493a-b19f-9bfc37a99dcd)
sliver (BEAUTIFUL_ASPECT) > tasks
ID State Message Type Created Sent Completed
========== =========== ============== =============================== =============================== ===============================
5b825908 completed Pwd Tue, 01 Mar 2022 22:42:08 EST Tue, 01 Mar 2022 22:42:09 EST Tue, 01 Mar 2022 22:42:09 EST
We get an error in the script but at least we get the output so could live with that but that isn't always the case. When I kick off three beacons within a few seconds of each other it looks like the api has trouble handling it.
new beacon registered: 1e72da59-1825-4042-b1d5-8dd92663db50
Hostname: client1
new beacon registered: 034099c1-3ef3-4e77-8c54-a0841b01c853
Hostname: client1
'5aba4e24-8f52-4d50-985f-ede3c7fa2039'
Traceback (most recent call last):
File "/usr/local/lib/python3.9/dist-packages/sliver/beacon.py", line 75, in taskresult_events
task_future, pb_object = self.beacon_tasks[beacon_task.ID]
KeyError: '5aba4e24-8f52-4d50-985f-ede3c7fa2039'
new beacon registered: e3989f4e-9c83-486f-ae25-8e989d0254f5
Hostname: client1
'2e488cef-3b1d-4563-872e-7679fddfc388'
Traceback (most recent call last):
File "/usr/local/lib/python3.9/dist-packages/sliver/beacon.py", line 75, in taskresult_events
task_future, pb_object = self.beacon_tasks[beacon_task.ID]
KeyError: '2e488cef-3b1d-4563-872e-7679fddfc388'
'2e488cef-3b1d-4563-872e-7679fddfc388'
Traceback (most recent call last):
File "/usr/local/lib/python3.9/dist-packages/sliver/beacon.py", line 75, in taskresult_events
task_future, pb_object = self.beacon_tasks[beacon_task.ID]
KeyError: '2e488cef-3b1d-4563-872e-7679fddfc388'
In the sliver client I can that the third (e3989f4e) beacon's task was actually tasked to the second (034099c1).
sliver (BEAUTIFUL_ASPECT) > use 1e72da59-1825-4042-b1d5-8dd92663db50
[*] Active beacon BEAUTIFUL_ASPECT (1e72da59-1825-4042-b1d5-8dd92663db50)
sliver (BEAUTIFUL_ASPECT) > tasks
ID State Message Type Created Sent Completed
========== =========== ============== =============================== =============================== ===============================
f88f6c48 completed Pwd Tue, 01 Mar 2022 22:58:54 EST Tue, 01 Mar 2022 22:58:55 EST Tue, 01 Mar 2022 22:58:55 EST
sliver (BEAUTIFUL_ASPECT) > use 034099c1-3ef3-4e77-8c54-a0841b01c853
[*] Active beacon BEAUTIFUL_ASPECT (034099c1-3ef3-4e77-8c54-a0841b01c853)
sliver (BEAUTIFUL_ASPECT) > tasks
ID State Message Type Created Sent Completed
========== =========== ============== =============================== =============================== ===============================
2e488cef pending Pwd Tue, 01 Mar 2022 22:59:00 EST
5aba4e24 completed Pwd Tue, 01 Mar 2022 22:58:57 EST Tue, 01 Mar 2022 22:58:58 EST Tue, 01 Mar 2022 22:58:58 EST
sliver (BEAUTIFUL_ASPECT) > use e3989f4e-9c83-486f-ae25-8e989d0254f5
[*] Active beacon BEAUTIFUL_ASPECT (e3989f4e-9c83-486f-ae25-8e989d0254f5)
sliver (BEAUTIFUL_ASPECT) > tasks
ID State Message Type Created Sent Completed
==== ======= ============== ========= ====== ===========
Took a quick look and confirmed the issue still exists. For some reason, the task is handled by the wrong beacon although the user is sending it to the right one. The beacon ID to send the task to is correct but the result shows it was handled by a different beacon, as @thespicybyte pointed out.
new beacon registered: e9dfb336-37cd-4419-98bd-4a0cc7509b04
Hostname: d229e225e03a
DEBUG Sending task with () | {}: beacon.py:171
โญโโโโโโโโโโโโโ <class 'sliver.beacon.InteractiveBeacon'> โโโโโโโโโโโโโโโฎ
โ Wrap all commands that can be executed against a beacon mode implant โ
โ โ
โ โญโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฎ โ
โ โ <sliver.beacon.InteractiveBeacon object at 0x0000026018D6B520> โ โ
โ โฐโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฏ โ
โ โ
โ active_c2 = 'http://172.30.15.15' โ
โ arch = 'amd64' โ
โ beacon_id = 'e9dfb336-37cd-4419-98bd-4a0cc7509b04' โ
โ beacon_tasks = {} โ
โ filename = 'C:\\Users\\ContainerAdministrator\\beacon.exe' โ
โ gid = 'S-1-5-93-2-1' โ
โ hostname = 'd229e225e03a' โ
โ last_checkin = 1661933434 โ
โ name = 'SMOOTH_TRINKET' โ
โ os = 'windows' โ
โ pid = 1668 โ
โ reconnect_interval = 60000000000 โ
โ remote_address = '172.30.10.45:62624' โ
โ timeout = 60 โ
โ transport = 'http(s)' โ
โ uid = 'S-1-5-93-2-1' โ
โ username = 'User Manager\\ContainerAdministrator' โ
โ uuid = '81a5d94f-b0c6-4708-82e9-fcb85f78d023' โ
โ version = 'Server 2016 build 20348 x86_64' โ
โฐโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฏ
โญโโโโโโโโโโโโโโโโโโโโโโโโโโโโ <class 'sliverpb.sliver_pb2.PwdReq'> โโโโโโโโโโโโโโโโโโโโโโโโโโโโโฎ
โ โญโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฎ โ
โ โ Request { โ โ
โ โ Async: true โ โ
โ โ Timeout: 59 โ โ
โ โ SessionID: "e9dfb336-37cd-4419-98bd-4a0cc7509b04" โ โ
โ โ } โ โ
โ โ โ โ
โ โฐโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฏ โ
โ โ
โ DESCRIPTOR = <google.protobuf.pyext._message.MessageDescriptor object at 0x0000026018B5CCD0> โ
โ Extensions = AttributeError('Extensions') โ
โ Request = Async: true โ
โ Timeout: 59 โ
โ SessionID: "e9dfb336-37cd-4419-98bd-4a0cc7509b04" โ
โ โ
โฐโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฏ
[01:10:37] DEBUG RESULT: beacon.py:174
โญโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ <class 'sliverpb.sliver_pb2.Pwd'> โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฎ
โ โญโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฎ โ
โ โ Response { โ โ
โ โ Async: true โ โ
โ โ BeaconID: "15c21505-ace9-4bd6-bd40-7bf823b5f66d" โ โ
โ โ TaskID: "e347d387-60b3-4682-bfa2-e72d872436f2" โ โ
โ โ } โ โ
โ โ โ โ
โ โฐโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฏ โ
โ โ
โ DESCRIPTOR = <google.protobuf.pyext._message.MessageDescriptor object at 0x0000026018B5CD00> โ
โ Extensions = AttributeError('Extensions') โ
โ Path = '' โ
โ Response = Async: true โ
โ BeaconID: "15c21505-ace9-4bd6-bd40-7bf823b5f66d" โ
โ TaskID: "e347d387-60b3-4682-bfa2-e72d872436f2" โ
โ โ
Checking the Sliver logs shows the beacon checking in and finding no tasks (make sense since the tasking occurs after check-in):
INFO[2022-08-31T01:10:34-07:00] [sliver/server/db/logger.go:20] github.com/bishopfox/sliver/server/db/helpers.go:262 record not found
[0.098ms] [rows:0] SELECT * FROM `beacons` WHERE `beacons`.`id` = "e9dfb336-37cd-4419-98bd-4a0cc7509b04" ORDER BY `beacons`.`id` LIMIT 1
INFO[2022-08-31T01:10:34-07:00] [sliver/server/db/logger.go:20] github.com/bishopfox/sliver/server/handlers/beacons.go:88 record not found
[0.035ms] [rows:0] SELECT * FROM `beacons` WHERE `id` = "e9dfb336-37cd-4419-98bd-4a0cc7509b04" ORDER BY `beacons`.`id` LIMIT 1
INFO[2022-08-31T01:10:34-07:00] [github.com/grpc-ecosystem/go-grpc-middleware@v1.2.2/logging/logrus/options.go:211] finished unary call with code OK
INFO[2022-08-31T01:10:35-07:00] [sliver/server/c2/http.go:396] 172.30.10.45:62626 - /api/namespaces/namespaces/api/api/oauth2callback/samples.php?h=46564122 - Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/98.0.2154.678 Safari/537.36
INFO[2022-08-31T01:10:35-07:00] [sliver/server/handlers/beacons.go:145] Beacon e9dfb336-37cd-4419-98bd-4a0cc7509b04 requested pending task(s)
INFO[2022-08-31T01:10:35-07:00] [sliver/server/handlers/beacons.go:177] Sending 0 task(s) to beacon e9dfb336-37cd-4419-98bd-4a0cc7509b04
But the other Beacon finds a task waiting for it and completes it:
INFO[2022-08-31T01:10:40-07:00] [sliver/server/handlers/beacons.go:177] Sending 1 task(s) to beacon 15c21505-ace9-4bd6-bd40-7bf823b5f66d
INFO[2022-08-31T01:10:40-07:00] [sliver/server/c2/http.go:396] 172.30.15.15:49026 - /jquery.js?b=7919643 - Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/99.0.7751.638 Safari/537.36
INFO[2022-08-31T01:10:40-07:00] [sliver/server/c2/http.go:396] 172.30.15.15:49030 - /namespaces/oauth2callback/database/oauth2/rpc.php?c=43236778 - Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/99.0.7751.638 Safari/537.36
INFO[2022-08-31T01:10:40-07:00] [sliver/server/handlers/beacons.go:140] Beacon 15c21505-ace9-4bd6-bd40-7bf823b5f66d returned 1 task result(s)
Basically, everything shows that the calls to the RPC server are correct. I'm gonna try to debug Sliver and see what's happening when the calls come in.
Found the issue. Sliver-py sends the PwdReq
as SessionID
(which is for sessions) not BeaconId
(which is for beacons). So there's two issues here:
- Need to fix the what is going out on the wire because it's the wrong field.
- Sliver needs to check for empty strings when it's handling the call or else the wrong one gets returned
PwdReq being sent to Windows beacon:
โญโโโโโโโโโโโโโโโโโโโโโโโโโโโโ <class 'sliverpb.sliver_pb2.PwdReq'> โโโโโโโโโโโโโโโโโโโโโโโโโโโโโฎ
โ โญโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฎ โ
โ โ Request { โ โ
โ โ Async: true โ โ
โ โ Timeout: 59 โ โ
โ โ SessionID: "efaa0639-f868-48ce-99d0-645c2196cd82" โ โ
โ โ } โ โ
โ โ โ โ
โ โฐโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฏ โ
โ โ
โ DESCRIPTOR = <google.protobuf.pyext._message.MessageDescriptor object at 0x000001E8A0CDBCD0> โ
โ Extensions = AttributeError('Extensions') โ
โ Request = Async: true โ
โ Timeout: 59 โ
โ SessionID: "efaa0639-f868-48ce-99d0-645c2196cd82" โ
โ โ
โฐโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฏ
Debugging Sliver - It receives the request but pulls the wrong beacon in db.BeaconById
because it's an empty string (which is not nil in Go, similar to how ""
is not None
in Python).
Gonna just note here that this is addressed in the protobuf-gen
branch which is a pretty big update of things.
Fixed in v0.0.18