agent: Use BatchingTelemetryMessenger in RansomewarePayload
We don't want the ransomware payload to encrypt all files and then send telemetry to the island. This could lead to a long period of time where the user has no insight into what the monkey is doing on a node. We also don't want to flood the island with telemetries. By using the BatchingTelemetryMessenger, ransomware encryption telemetries are batched together and periodically sent to the island.
This commit is contained in:
parent
fadd978050
commit
85c91f55bb
|
@ -25,6 +25,9 @@ from infection_monkey.system_singleton import SystemSingleton
|
||||||
from infection_monkey.telemetry.attack.t1106_telem import T1106Telem
|
from infection_monkey.telemetry.attack.t1106_telem import T1106Telem
|
||||||
from infection_monkey.telemetry.attack.t1107_telem import T1107Telem
|
from infection_monkey.telemetry.attack.t1107_telem import T1107Telem
|
||||||
from infection_monkey.telemetry.attack.victim_host_telem import VictimHostTelem
|
from infection_monkey.telemetry.attack.victim_host_telem import VictimHostTelem
|
||||||
|
from infection_monkey.telemetry.messengers.batching_telemetry_messenger import (
|
||||||
|
BatchingTelemetryMessenger,
|
||||||
|
)
|
||||||
from infection_monkey.telemetry.messengers.legacy_telemetry_messenger_adapter import (
|
from infection_monkey.telemetry.messengers.legacy_telemetry_messenger_adapter import (
|
||||||
LegacyTelemetryMessengerAdapter,
|
LegacyTelemetryMessengerAdapter,
|
||||||
)
|
)
|
||||||
|
@ -471,6 +474,11 @@ class InfectionMonkey(object):
|
||||||
def run_ransomware():
|
def run_ransomware():
|
||||||
try:
|
try:
|
||||||
telemetry_messenger = LegacyTelemetryMessengerAdapter()
|
telemetry_messenger = LegacyTelemetryMessengerAdapter()
|
||||||
RansomewarePayload(WormConfiguration.ransomware, telemetry_messenger).run_payload()
|
batching_telemetry_messenger = BatchingTelemetryMessenger(telemetry_messenger)
|
||||||
|
RansomewarePayload(
|
||||||
|
WormConfiguration.ransomware, batching_telemetry_messenger
|
||||||
|
).run_payload()
|
||||||
except Exception as ex:
|
except Exception as ex:
|
||||||
LOG.error(f"An unexpected error occurred while running the ransomware payload: {ex}")
|
LOG.error(f"An unexpected error occurred while running the ransomware payload: {ex}")
|
||||||
|
finally:
|
||||||
|
batching_telemetry_messenger.stop()
|
||||||
|
|
|
@ -10,7 +10,7 @@ from infection_monkey.telemetry.messengers.i_telemetry_messenger import ITelemet
|
||||||
WAKES_PER_PERIOD = 4
|
WAKES_PER_PERIOD = 4
|
||||||
|
|
||||||
|
|
||||||
class BatchedTelemetryMessenger(ITelemetryMessenger):
|
class BatchingTelemetryMessenger(ITelemetryMessenger):
|
||||||
"""
|
"""
|
||||||
An ITelemetryMessenger decorator that aggregates IBatchableTelem telemetries
|
An ITelemetryMessenger decorator that aggregates IBatchableTelem telemetries
|
||||||
and periodically sends them to Monkey Island.
|
and periodically sends them to Monkey Island.
|
|
@ -5,8 +5,8 @@ import pytest
|
||||||
from infection_monkey.telemetry.base_telem import BaseTelem
|
from infection_monkey.telemetry.base_telem import BaseTelem
|
||||||
from infection_monkey.telemetry.batchable_telem_mixin import BatchableTelemMixin
|
from infection_monkey.telemetry.batchable_telem_mixin import BatchableTelemMixin
|
||||||
from infection_monkey.telemetry.i_batchable_telem import IBatchableTelem
|
from infection_monkey.telemetry.i_batchable_telem import IBatchableTelem
|
||||||
from infection_monkey.telemetry.messengers.batched_telemetry_messenger import (
|
from infection_monkey.telemetry.messengers.batching_telemetry_messenger import (
|
||||||
BatchedTelemetryMessenger,
|
BatchingTelemetryMessenger,
|
||||||
)
|
)
|
||||||
|
|
||||||
PERIOD = 0.001
|
PERIOD = 0.001
|
||||||
|
@ -54,31 +54,31 @@ class BatchableTelemStub(BatchableTelemMixin, BaseTelem, IBatchableTelem):
|
||||||
|
|
||||||
|
|
||||||
@pytest.fixture
|
@pytest.fixture
|
||||||
def batched_telemetry_messenger(monkeypatch, telemetry_messenger_spy):
|
def batching_telemetry_messenger(monkeypatch, telemetry_messenger_spy):
|
||||||
patch_time(monkeypatch, 0)
|
patch_time(monkeypatch, 0)
|
||||||
btm = BatchedTelemetryMessenger(telemetry_messenger_spy, period=0.001)
|
btm = BatchingTelemetryMessenger(telemetry_messenger_spy, period=0.001)
|
||||||
yield btm
|
yield btm
|
||||||
|
|
||||||
btm.stop()
|
btm.stop()
|
||||||
|
|
||||||
|
|
||||||
def test_send_immediately(batched_telemetry_messenger, telemetry_messenger_spy):
|
def test_send_immediately(batching_telemetry_messenger, telemetry_messenger_spy):
|
||||||
telem = NonBatchableTelemStub()
|
telem = NonBatchableTelemStub()
|
||||||
|
|
||||||
batched_telemetry_messenger.send_telemetry(telem)
|
batching_telemetry_messenger.send_telemetry(telem)
|
||||||
release_GIL()
|
release_GIL()
|
||||||
|
|
||||||
assert len(telemetry_messenger_spy.telemetries) == 1
|
assert len(telemetry_messenger_spy.telemetries) == 1
|
||||||
assert telemetry_messenger_spy.telemetries[0] == telem
|
assert telemetry_messenger_spy.telemetries[0] == telem
|
||||||
|
|
||||||
|
|
||||||
def test_send_telem_batch(monkeypatch, batched_telemetry_messenger, telemetry_messenger_spy):
|
def test_send_telem_batch(monkeypatch, batching_telemetry_messenger, telemetry_messenger_spy):
|
||||||
expected_data = {"entries": [1, 2]}
|
expected_data = {"entries": [1, 2]}
|
||||||
telem1 = BatchableTelemStub(1)
|
telem1 = BatchableTelemStub(1)
|
||||||
telem2 = BatchableTelemStub(2)
|
telem2 = BatchableTelemStub(2)
|
||||||
|
|
||||||
batched_telemetry_messenger.send_telemetry(telem1)
|
batching_telemetry_messenger.send_telemetry(telem1)
|
||||||
batched_telemetry_messenger.send_telemetry(telem2)
|
batching_telemetry_messenger.send_telemetry(telem2)
|
||||||
release_GIL()
|
release_GIL()
|
||||||
|
|
||||||
assert len(telemetry_messenger_spy.telemetries) == 0
|
assert len(telemetry_messenger_spy.telemetries) == 0
|
||||||
|
@ -90,13 +90,13 @@ def test_send_telem_batch(monkeypatch, batched_telemetry_messenger, telemetry_me
|
||||||
|
|
||||||
|
|
||||||
def test_send_different_telem_types(
|
def test_send_different_telem_types(
|
||||||
monkeypatch, batched_telemetry_messenger, telemetry_messenger_spy
|
monkeypatch, batching_telemetry_messenger, telemetry_messenger_spy
|
||||||
):
|
):
|
||||||
telem1 = BatchableTelemStub(1, "cat1")
|
telem1 = BatchableTelemStub(1, "cat1")
|
||||||
telem2 = BatchableTelemStub(2, "cat2")
|
telem2 = BatchableTelemStub(2, "cat2")
|
||||||
|
|
||||||
batched_telemetry_messenger.send_telemetry(telem1)
|
batching_telemetry_messenger.send_telemetry(telem1)
|
||||||
batched_telemetry_messenger.send_telemetry(telem2)
|
batching_telemetry_messenger.send_telemetry(telem2)
|
||||||
release_GIL()
|
release_GIL()
|
||||||
|
|
||||||
assert len(telemetry_messenger_spy.telemetries) == 0
|
assert len(telemetry_messenger_spy.telemetries) == 0
|
||||||
|
@ -108,15 +108,15 @@ def test_send_different_telem_types(
|
||||||
assert telemetry_messenger_spy.telemetries[1] == telem2
|
assert telemetry_messenger_spy.telemetries[1] == telem2
|
||||||
|
|
||||||
|
|
||||||
def test_send_two_batches(monkeypatch, batched_telemetry_messenger, telemetry_messenger_spy):
|
def test_send_two_batches(monkeypatch, batching_telemetry_messenger, telemetry_messenger_spy):
|
||||||
telem1 = BatchableTelemStub(1, "cat1")
|
telem1 = BatchableTelemStub(1, "cat1")
|
||||||
telem2 = BatchableTelemStub(2, "cat1")
|
telem2 = BatchableTelemStub(2, "cat1")
|
||||||
|
|
||||||
batched_telemetry_messenger.send_telemetry(telem1)
|
batching_telemetry_messenger.send_telemetry(telem1)
|
||||||
advance_clock_to_next_period(monkeypatch)
|
advance_clock_to_next_period(monkeypatch)
|
||||||
release_GIL()
|
release_GIL()
|
||||||
|
|
||||||
batched_telemetry_messenger.send_telemetry(telem2)
|
batching_telemetry_messenger.send_telemetry(telem2)
|
||||||
release_GIL()
|
release_GIL()
|
||||||
assert len(telemetry_messenger_spy.telemetries) == 1
|
assert len(telemetry_messenger_spy.telemetries) == 1
|
||||||
|
|
Loading…
Reference in New Issue