mirror of
https://github.com/xdp-project/bpf-examples.git
synced 2024-05-06 15:54:53 +00:00
pping: Keep track of outstanding timestamps
Add a counter of outstanding (unmatched) timestamped entires in the flow state. Before a timestamp lookup is attempted, check that there are any outstanding timestamps, otherwise avoid the unecessary hash map lookup. Use 32 bit counter for outstanding timestamps to allow atomic increments/decrements using __synch_fetch_and_add. This operation is not supported on smaller integers, which is why such a large counter is used. The atomicity is needed because the counter may be concurrently accessed by both the ingress/egress hook as well as the periodical map cleanup. Signed-off-by: Simon Sundberg <simon.sundberg@kau.se>
This commit is contained in:
@@ -94,9 +94,10 @@ struct flow_state {
|
|||||||
__u64 rec_pkts;
|
__u64 rec_pkts;
|
||||||
__u64 rec_bytes;
|
__u64 rec_bytes;
|
||||||
__u32 last_id;
|
__u32 last_id;
|
||||||
|
__u32 outstanding_timestamps;
|
||||||
bool has_opened;
|
bool has_opened;
|
||||||
enum flow_event_reason opening_reason;
|
enum flow_event_reason opening_reason;
|
||||||
__u16 reserved;
|
__u8 reserved[6];
|
||||||
};
|
};
|
||||||
|
|
||||||
struct packet_id {
|
struct packet_id {
|
||||||
|
|||||||
@@ -687,7 +687,9 @@ static void pping_timestamp_packet(struct flow_state *f_state, void *ctx,
|
|||||||
f_state->last_timestamp = p_info->time;
|
f_state->last_timestamp = p_info->time;
|
||||||
|
|
||||||
if (bpf_map_update_elem(&packet_ts, &p_info->pid, &p_info->time,
|
if (bpf_map_update_elem(&packet_ts, &p_info->pid, &p_info->time,
|
||||||
BPF_NOEXIST) != 0)
|
BPF_NOEXIST) == 0)
|
||||||
|
__sync_fetch_and_add(&f_state->outstanding_timestamps, 1);
|
||||||
|
else
|
||||||
send_map_full_event(ctx, p_info, PPING_MAP_PACKETTS);
|
send_map_full_event(ctx, p_info, PPING_MAP_PACKETTS);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -704,6 +706,9 @@ static void pping_match_packet(struct flow_state *f_state, void *ctx,
|
|||||||
if (!f_state || !p_info->reply_pid_valid)
|
if (!f_state || !p_info->reply_pid_valid)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
if (f_state->outstanding_timestamps == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
p_ts = bpf_map_lookup_elem(&packet_ts, &p_info->reply_pid);
|
p_ts = bpf_map_lookup_elem(&packet_ts, &p_info->reply_pid);
|
||||||
if (!p_ts || p_info->time < *p_ts)
|
if (!p_ts || p_info->time < *p_ts)
|
||||||
return;
|
return;
|
||||||
@@ -711,8 +716,10 @@ static void pping_match_packet(struct flow_state *f_state, void *ctx,
|
|||||||
re.rtt = p_info->time - *p_ts;
|
re.rtt = p_info->time - *p_ts;
|
||||||
|
|
||||||
// Delete timestamp entry as soon as RTT is calculated
|
// Delete timestamp entry as soon as RTT is calculated
|
||||||
if (bpf_map_delete_elem(&packet_ts, &p_info->reply_pid) == 0)
|
if (bpf_map_delete_elem(&packet_ts, &p_info->reply_pid) == 0) {
|
||||||
|
__sync_fetch_and_add(&f_state->outstanding_timestamps, -1);
|
||||||
debug_increment_autodel(PPING_MAP_PACKETTS);
|
debug_increment_autodel(PPING_MAP_PACKETTS);
|
||||||
|
}
|
||||||
|
|
||||||
if (f_state->min_rtt == 0 || re.rtt < f_state->min_rtt)
|
if (f_state->min_rtt == 0 || re.rtt < f_state->min_rtt)
|
||||||
f_state->min_rtt = re.rtt;
|
f_state->min_rtt = re.rtt;
|
||||||
@@ -836,8 +843,13 @@ int tsmap_cleanup(struct bpf_iter__bpf_map_elem *ctx)
|
|||||||
|
|
||||||
if ((rtt && now - *timestamp > rtt * TIMESTAMP_RTT_LIFETIME) ||
|
if ((rtt && now - *timestamp > rtt * TIMESTAMP_RTT_LIFETIME) ||
|
||||||
now - *timestamp > TIMESTAMP_LIFETIME) {
|
now - *timestamp > TIMESTAMP_LIFETIME) {
|
||||||
if (bpf_map_delete_elem(&packet_ts, &local_pid) == 0)
|
if (bpf_map_delete_elem(&packet_ts, &local_pid) == 0) {
|
||||||
debug_increment_timeoutdel(PPING_MAP_PACKETTS);
|
debug_increment_timeoutdel(PPING_MAP_PACKETTS);
|
||||||
|
|
||||||
|
if (f_state)
|
||||||
|
__sync_fetch_and_add(
|
||||||
|
&f_state->outstanding_timestamps, -1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|||||||
Reference in New Issue
Block a user