Add abstract DataModel* getter in EventHandler

This commit is contained in:
Christophe Bedard 2019-08-08 10:11:04 +02:00
parent 5491087299
commit 09f28b73f0
6 changed files with 46 additions and 33 deletions

View file

@ -308,11 +308,7 @@ class TestProfileHandler(unittest.TestCase):
def test_profiling(self) -> None: def test_profiling(self) -> None:
handler = self.__class__.handler handler = self.__class__.handler
expected_df = self.__class__.expected expected_df = self.__class__.expected
result_df = handler.get_data_model().times result_df = handler.data.times
print('RESULT')
print(result_df.to_string())
print('EXPECTED')
print(expected_df.to_string())
assert_frame_equal(result_df, expected_df) assert_frame_equal(result_df, expected_df)

View file

@ -41,4 +41,4 @@ def main():
time_diff = time.time() - start_time time_diff = time.time() - start_time
print(f'processed {len(events)} events in {time_diff * 1000:.2f} ms') print(f'processed {len(events)} events in {time_diff * 1000:.2f} ms')
ros2_handler.get_data_model().print_model() ros2_handler.data.print_model()

View file

@ -104,7 +104,7 @@ class EventHandler(Dependant):
Base event handling class. Base event handling class.
Provides handling functions for some events, depending on the name. Provides handling functions for some events, depending on the name.
To be subclassed. Passes that on to a data model. To be subclassed.
""" """
def __init__( def __init__(
@ -130,6 +130,11 @@ class EventHandler(Dependant):
"""Get the handler functions map.""" """Get the handler functions map."""
return self._handler_map return self._handler_map
@property
def data(self) -> None:
"""Get the data model."""
return None
def register_processor(self, processor: 'Processor') -> None: def register_processor(self, processor: 'Processor') -> None:
"""Register processor with this `EventHandler` so that it can query other handlers.""" """Register processor with this `EventHandler` so that it can query other handlers."""
self.processor = processor self.processor = processor

View file

@ -39,16 +39,20 @@ class CpuTimeHandler(EventHandler):
'sched_switch': 'sched_switch':
self._handle_sched_switch, self._handle_sched_switch,
} }
super().__init__(handler_map=handler_map, **kwargs) super().__init__(
handler_map=handler_map,
**kwargs,
)
self._data = CpuTimeDataModel() self._data_model = CpuTimeDataModel()
# Temporary buffers # Temporary buffers
# cpu_id -> start timestamp of the running thread # cpu_id -> start timestamp of the running thread
self._cpu_start: Dict[int, int] = {} self._cpu_start: Dict[int, int] = {}
def get_data_model(self) -> CpuTimeDataModel: @property
return self._data def data(self) -> CpuTimeDataModel:
return self._data_model
def _handle_sched_switch( def _handle_sched_switch(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -62,6 +66,6 @@ class CpuTimeHandler(EventHandler):
if prev_timestamp is not None: if prev_timestamp is not None:
prev_tid = get_field(event, 'prev_tid') prev_tid = get_field(event, 'prev_tid')
duration = timestamp - prev_timestamp duration = timestamp - prev_timestamp
self._data.add_duration(prev_tid, prev_timestamp, duration, cpu_id) self.data.add_duration(prev_tid, prev_timestamp, duration, cpu_id)
# Set start timestamp of next thread # Set start timestamp of next thread
self._cpu_start[cpu_id] = timestamp self._cpu_start[cpu_id] = timestamp

View file

@ -59,9 +59,12 @@ class ProfileHandler(EventHandler):
'sched_switch': 'sched_switch':
self._handle_sched_switch, self._handle_sched_switch,
} }
super().__init__(handler_map=handler_map, **kwargs) super().__init__(
handler_map=handler_map,
**kwargs,
)
self._data = ProfileDataModel() self._data_model = ProfileDataModel()
self._address_to_func = address_to_func self._address_to_func = address_to_func
# Temporary buffers # Temporary buffers
@ -77,8 +80,9 @@ class ProfileHandler(EventHandler):
# ] # ]
self._current_funcs: Dict[int, List[List[Union[str, int]]]] = defaultdict(list) self._current_funcs: Dict[int, List[List[Union[str, int]]]] = defaultdict(list)
def get_data_model(self) -> ProfileDataModel: @property
return self._data def data(self) -> ProfileDataModel:
return self._data_model
def _handle_sched_switch( def _handle_sched_switch(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -130,7 +134,7 @@ class ProfileHandler(EventHandler):
parent_name = tid_functions[-1][0] if function_depth > 0 else None parent_name = tid_functions[-1][0] if function_depth > 0 else None
duration = metadata.timestamp - start_timestamp duration = metadata.timestamp - start_timestamp
actual_duration = (metadata.timestamp - last_start_timestamp) + total_duration actual_duration = (metadata.timestamp - last_start_timestamp) + total_duration
self._data.add_duration( self.data.add_duration(
tid, tid,
function_depth, function_depth,
function_name, function_name,

View file

@ -63,15 +63,19 @@ class Ros2Handler(EventHandler):
'ros2:callback_end': 'ros2:callback_end':
self._handle_callback_end, self._handle_callback_end,
} }
super().__init__(handler_map=handler_map, **kwargs) super().__init__(
handler_map=handler_map,
**kwargs,
)
self._data = RosDataModel() self._data_model = RosDataModel()
# Temporary buffers # Temporary buffers
self._callback_instances = {} self._callback_instances = {}
def get_data_model(self) -> RosDataModel: @property
return self._data def data(self) -> RosDataModel:
return self._data_model
def _handle_rcl_init( def _handle_rcl_init(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -80,7 +84,7 @@ class Ros2Handler(EventHandler):
timestamp = metadata.timestamp timestamp = metadata.timestamp
pid = metadata.pid pid = metadata.pid
version = get_field(event, 'version') version = get_field(event, 'version')
self._data.add_context(context_handle, timestamp, pid, version) self.data.add_context(context_handle, timestamp, pid, version)
def _handle_rcl_node_init( def _handle_rcl_node_init(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -91,7 +95,7 @@ class Ros2Handler(EventHandler):
rmw_handle = get_field(event, 'rmw_handle') rmw_handle = get_field(event, 'rmw_handle')
name = get_field(event, 'node_name') name = get_field(event, 'node_name')
namespace = get_field(event, 'namespace') namespace = get_field(event, 'namespace')
self._data.add_node(handle, timestamp, tid, rmw_handle, name, namespace) self.data.add_node(handle, timestamp, tid, rmw_handle, name, namespace)
def _handle_rcl_publisher_init( def _handle_rcl_publisher_init(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -102,7 +106,7 @@ class Ros2Handler(EventHandler):
rmw_handle = get_field(event, 'rmw_publisher_handle') rmw_handle = get_field(event, 'rmw_publisher_handle')
topic_name = get_field(event, 'topic_name') topic_name = get_field(event, 'topic_name')
depth = get_field(event, 'queue_depth') depth = get_field(event, 'queue_depth')
self._data.add_publisher(handle, timestamp, node_handle, rmw_handle, topic_name, depth) self.data.add_publisher(handle, timestamp, node_handle, rmw_handle, topic_name, depth)
def _handle_subscription_init( def _handle_subscription_init(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -113,7 +117,7 @@ class Ros2Handler(EventHandler):
rmw_handle = get_field(event, 'rmw_subscription_handle') rmw_handle = get_field(event, 'rmw_subscription_handle')
topic_name = get_field(event, 'topic_name') topic_name = get_field(event, 'topic_name')
depth = get_field(event, 'queue_depth') depth = get_field(event, 'queue_depth')
self._data.add_subscription(handle, timestamp, node_handle, rmw_handle, topic_name, depth) self.data.add_subscription(handle, timestamp, node_handle, rmw_handle, topic_name, depth)
def _handle_rclcpp_subscription_callback_added( def _handle_rclcpp_subscription_callback_added(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -121,7 +125,7 @@ class Ros2Handler(EventHandler):
handle = get_field(event, 'subscription_handle') handle = get_field(event, 'subscription_handle')
timestamp = metadata.timestamp timestamp = metadata.timestamp
callback_object = get_field(event, 'callback') callback_object = get_field(event, 'callback')
self._data.add_callback_object(handle, timestamp, callback_object) self.data.add_callback_object(handle, timestamp, callback_object)
def _handle_rcl_service_init( def _handle_rcl_service_init(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -131,7 +135,7 @@ class Ros2Handler(EventHandler):
node_handle = get_field(event, 'node_handle') node_handle = get_field(event, 'node_handle')
rmw_handle = get_field(event, 'rmw_service_handle') rmw_handle = get_field(event, 'rmw_service_handle')
service_name = get_field(event, 'service_name') service_name = get_field(event, 'service_name')
self._data.add_service(handle, timestamp, node_handle, rmw_handle, service_name) self.data.add_service(handle, timestamp, node_handle, rmw_handle, service_name)
def _handle_rclcpp_service_callback_added( def _handle_rclcpp_service_callback_added(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -139,7 +143,7 @@ class Ros2Handler(EventHandler):
handle = get_field(event, 'service_handle') handle = get_field(event, 'service_handle')
timestamp = metadata.timestamp timestamp = metadata.timestamp
callback_object = get_field(event, 'callback') callback_object = get_field(event, 'callback')
self._data.add_callback_object(handle, timestamp, callback_object) self.data.add_callback_object(handle, timestamp, callback_object)
def _handle_rcl_client_init( def _handle_rcl_client_init(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -149,7 +153,7 @@ class Ros2Handler(EventHandler):
node_handle = get_field(event, 'node_handle') node_handle = get_field(event, 'node_handle')
rmw_handle = get_field(event, 'rmw_client_handle') rmw_handle = get_field(event, 'rmw_client_handle')
service_name = get_field(event, 'service_name') service_name = get_field(event, 'service_name')
self._data.add_client(handle, timestamp, node_handle, rmw_handle, service_name) self.data.add_client(handle, timestamp, node_handle, rmw_handle, service_name)
def _handle_rcl_timer_init( def _handle_rcl_timer_init(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -158,7 +162,7 @@ class Ros2Handler(EventHandler):
timestamp = metadata.timestamp timestamp = metadata.timestamp
period = get_field(event, 'period') period = get_field(event, 'period')
tid = metadata.tid tid = metadata.tid
self._data.add_timer(handle, timestamp, period, tid) self.data.add_timer(handle, timestamp, period, tid)
def _handle_rclcpp_timer_callback_added( def _handle_rclcpp_timer_callback_added(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -166,7 +170,7 @@ class Ros2Handler(EventHandler):
handle = get_field(event, 'timer_handle') handle = get_field(event, 'timer_handle')
timestamp = metadata.timestamp timestamp = metadata.timestamp
callback_object = get_field(event, 'callback') callback_object = get_field(event, 'callback')
self._data.add_callback_object(handle, timestamp, callback_object) self.data.add_callback_object(handle, timestamp, callback_object)
def _handle_rclcpp_callback_register( def _handle_rclcpp_callback_register(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -174,7 +178,7 @@ class Ros2Handler(EventHandler):
callback_object = get_field(event, 'callback') callback_object = get_field(event, 'callback')
timestamp = metadata.timestamp timestamp = metadata.timestamp
symbol = get_field(event, 'symbol') symbol = get_field(event, 'symbol')
self._data.add_callback_symbol(callback_object, timestamp, symbol) self.data.add_callback_symbol(callback_object, timestamp, symbol)
def _handle_callback_start( def _handle_callback_start(
self, event: Dict, metadata: EventMetadata self, event: Dict, metadata: EventMetadata
@ -193,7 +197,7 @@ class Ros2Handler(EventHandler):
del self._callback_instances[callback_object] del self._callback_instances[callback_object]
duration = metadata.timestamp - metadata_start.timestamp duration = metadata.timestamp - metadata_start.timestamp
is_intra_process = get_field(event_start, 'is_intra_process', raise_if_not_found=False) is_intra_process = get_field(event_start, 'is_intra_process', raise_if_not_found=False)
self._data.add_callback_instance( self.data.add_callback_instance(
callback_object, callback_object,
metadata_start.timestamp, metadata_start.timestamp,
duration, duration,