Fix a problem with the detailed event list "seek backward". In the following
condition:
- Long interval between events (e.g. generated with power management suspend).
- Happening close to trace start.
- Trace start near 0s 0ns.
The substraction could underflow. Fix this by comparing the time to substract
and floor to trace start time if it would underflow.
The visible effect was that the detailed event list is seeked to the end of the
trace rather than the previous event when going "up" one event prior to the
suspend begin.
Signed-off-by: Mathieu Desnoyers <mathieu.desnoyers@polymtl.ca>
CC: Viktor Rosendahl <viktor.rosendahl@nokia.com>
if(ltt_time_compare(time, self->time_span.end_time) > 0) {
time = self->time_span.end_time;
}
if(ltt_time_compare(time, self->time_span.end_time) > 0) {
time = self->time_span.end_time;
}
time_offset = first_offset;
lttv_hooks_add(hooks, seek_back_event_hook, &sd, LTTV_PRIO_DEFAULT);
time_offset = first_offset;
lttv_hooks_add(hooks, seek_back_event_hook, &sd, LTTV_PRIO_DEFAULT);
lttv_process_traceset_begin(self, NULL, NULL, NULL, hooks, NULL);
while(1) {
lttv_process_traceset_begin(self, NULL, NULL, NULL, hooks, NULL);
while(1) {
- /* stop criteria : - n events found
- * - asked_time < beginning of trace */
- if(ltt_time_compare(asked_time, self->time_span.start_time) < 0) break;
-
lttv_traceset_context_position_copy(end_pos, next_iter_end_pos);
/* We must seek the traceset back to time - time_offset */
/* this time becomes the new reference time */
lttv_traceset_context_position_copy(end_pos, next_iter_end_pos);
/* We must seek the traceset back to time - time_offset */
/* this time becomes the new reference time */
- time = ltt_time_sub(time, time_offset);
+ if(ltt_time_compare(time, time_offset) > 0)
+ time = ltt_time_sub(time, time_offset);
+ else
+ time = self->time_span.start_time;
time_seeker(self, time);
lttv_traceset_context_position_save(self, next_iter_end_pos);
/* Resync the time in case of a seek_closest */
time_seeker(self, time);
lttv_traceset_context_position_save(self, next_iter_end_pos);
/* Resync the time in case of a seek_closest */
lttv_process_traceset_middle(self, ltt_time_infinite,
G_MAXUINT, end_pos);
lttv_process_traceset_middle(self, ltt_time_infinite,
G_MAXUINT, end_pos);
+ /* stop criteria : - n events found
+ * - asked_time < beginning of trace */
if(sd.events_found < n) {
if(sd.first_event > 0) {
/* Save the first position */
if(sd.events_found < n) {
if(sd.first_event > 0) {
/* Save the first position */
}
g_ptr_array_set_size(sd.array, n-sd.events_found);
sd.first_event = 0;
}
g_ptr_array_set_size(sd.array, n-sd.events_found);
sd.first_event = 0;
+
+ /*
+ * Did not fill our event list and started before the beginning of the
+ * trace. There is no hope to fill it then.
+ * It is OK to compare with trace start time here because we explicitely
+ * seeked by time (not by position), so we cannot miss multiple event
+ * happening exactly at trace start.
+ */
+ if(ltt_time_compare(asked_time, self->time_span.start_time) == 0)
+ break;
} else break; /* Second end criterion : n events found */
} else break; /* Second end criterion : n events found */
time_offset = ltt_time_mul(time_offset, BACKWARD_SEEK_MUL);
}
time_offset = ltt_time_mul(time_offset, BACKWARD_SEEK_MUL);
}