@@ -1012,5 +1012,70 @@ def test_same_thread_id_multiple_interpreters_stress(self):
10121012 )
10131013
10141014
1015+ class TimestampCollector :
1016+ """Collector that captures timestamps for verification."""
1017+
1018+ def __init__ (self ):
1019+ self .all_timestamps = []
1020+
1021+ def collect (self , stack_frames , timestamps_us = None ):
1022+ if timestamps_us is not None :
1023+ self .all_timestamps .extend (timestamps_us )
1024+
1025+ def export (self , filename ):
1026+ pass
1027+
1028+
1029+ class TestTimestampPreservation (BinaryFormatTestBase ):
1030+ """Tests for timestamp preservation during binary round-trip."""
1031+
1032+ def test_timestamp_preservation (self ):
1033+ """Timestamps are preserved during round-trip."""
1034+ frame = make_frame ("test.py" , 10 , "func" )
1035+ timestamps = [1000000 , 2000000 , 3000000 ]
1036+
1037+ with tempfile .NamedTemporaryFile (suffix = ".bin" , delete = False ) as f :
1038+ filename = f .name
1039+ self .temp_files .append (filename )
1040+
1041+ collector = BinaryCollector (filename , 1000 , compression = "none" )
1042+ for ts in timestamps :
1043+ sample = [make_interpreter (0 , [make_thread (1 , [frame ])])]
1044+ collector .collect (sample , timestamp_us = ts )
1045+ collector .export (None )
1046+
1047+ ts_collector = TimestampCollector ()
1048+ with BinaryReader (filename ) as reader :
1049+ count = reader .replay_samples (ts_collector )
1050+
1051+ self .assertEqual (count , 3 )
1052+ self .assertEqual (ts_collector .all_timestamps , timestamps )
1053+
1054+ def test_timestamp_preservation_with_rle (self ):
1055+ """RLE-batched samples preserve individual timestamps."""
1056+ frame = make_frame ("rle.py" , 42 , "rle_func" )
1057+
1058+ with tempfile .NamedTemporaryFile (suffix = ".bin" , delete = False ) as f :
1059+ filename = f .name
1060+ self .temp_files .append (filename )
1061+
1062+ # Identical samples (triggers RLE) with different timestamps
1063+ collector = BinaryCollector (filename , 1000 , compression = "none" )
1064+ expected_timestamps = []
1065+ for i in range (50 ):
1066+ ts = 1000000 + i * 100
1067+ expected_timestamps .append (ts )
1068+ sample = [make_interpreter (0 , [make_thread (1 , [frame ])])]
1069+ collector .collect (sample , timestamp_us = ts )
1070+ collector .export (None )
1071+
1072+ ts_collector = TimestampCollector ()
1073+ with BinaryReader (filename ) as reader :
1074+ count = reader .replay_samples (ts_collector )
1075+
1076+ self .assertEqual (count , 50 )
1077+ self .assertEqual (ts_collector .all_timestamps , expected_timestamps )
1078+
1079+
10151080if __name__ == "__main__" :
10161081 unittest .main ()
0 commit comments