Commit 1db19db7 authored by Jesper Dangaard Brouer's avatar Jesper Dangaard Brouer Committed by David S. Miller

net: tracepoint napi:napi_poll add work and budget

An important information for the napi_poll tracepoint is knowing
the work done (packets processed) by the napi_poll() call. Add
both the work done and budget, as they are related.

Handle trace_napi_poll() param change in dropwatch/drop_monitor
and in python perf script netdev-times.py in backward compat way,
as python fortunately supports optional parameter handling.
Signed-off-by: default avatarJesper Dangaard Brouer <brouer@redhat.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 89141e1c
...@@ -12,22 +12,27 @@ ...@@ -12,22 +12,27 @@
TRACE_EVENT(napi_poll, TRACE_EVENT(napi_poll,
TP_PROTO(struct napi_struct *napi), TP_PROTO(struct napi_struct *napi, int work, int budget),
TP_ARGS(napi), TP_ARGS(napi, work, budget),
TP_STRUCT__entry( TP_STRUCT__entry(
__field( struct napi_struct *, napi) __field( struct napi_struct *, napi)
__field( int, work)
__field( int, budget)
__string( dev_name, napi->dev ? napi->dev->name : NO_DEV) __string( dev_name, napi->dev ? napi->dev->name : NO_DEV)
), ),
TP_fast_assign( TP_fast_assign(
__entry->napi = napi; __entry->napi = napi;
__entry->work = work;
__entry->budget = budget;
__assign_str(dev_name, napi->dev ? napi->dev->name : NO_DEV); __assign_str(dev_name, napi->dev ? napi->dev->name : NO_DEV);
), ),
TP_printk("napi poll on napi struct %p for device %s", TP_printk("napi poll on napi struct %p for device %s work %d budget %d",
__entry->napi, __get_str(dev_name)) __entry->napi, __get_str(dev_name),
__entry->work, __entry->budget)
); );
#undef NO_DEV #undef NO_DEV
......
...@@ -4972,7 +4972,7 @@ bool sk_busy_loop(struct sock *sk, int nonblock) ...@@ -4972,7 +4972,7 @@ bool sk_busy_loop(struct sock *sk, int nonblock)
if (test_bit(NAPI_STATE_SCHED, &napi->state)) { if (test_bit(NAPI_STATE_SCHED, &napi->state)) {
rc = napi->poll(napi, BUSY_POLL_BUDGET); rc = napi->poll(napi, BUSY_POLL_BUDGET);
trace_napi_poll(napi); trace_napi_poll(napi, rc, BUSY_POLL_BUDGET);
if (rc == BUSY_POLL_BUDGET) { if (rc == BUSY_POLL_BUDGET) {
napi_complete_done(napi, rc); napi_complete_done(napi, rc);
napi_schedule(napi); napi_schedule(napi);
...@@ -5128,7 +5128,7 @@ static int napi_poll(struct napi_struct *n, struct list_head *repoll) ...@@ -5128,7 +5128,7 @@ static int napi_poll(struct napi_struct *n, struct list_head *repoll)
work = 0; work = 0;
if (test_bit(NAPI_STATE_SCHED, &n->state)) { if (test_bit(NAPI_STATE_SCHED, &n->state)) {
work = n->poll(n, weight); work = n->poll(n, weight);
trace_napi_poll(n); trace_napi_poll(n, work, weight);
} }
WARN_ON_ONCE(work > weight); WARN_ON_ONCE(work > weight);
......
...@@ -187,7 +187,8 @@ static void trace_kfree_skb_hit(void *ignore, struct sk_buff *skb, void *locatio ...@@ -187,7 +187,8 @@ static void trace_kfree_skb_hit(void *ignore, struct sk_buff *skb, void *locatio
trace_drop_common(skb, location); trace_drop_common(skb, location);
} }
static void trace_napi_poll_hit(void *ignore, struct napi_struct *napi) static void trace_napi_poll_hit(void *ignore, struct napi_struct *napi,
int work, int budget)
{ {
struct dm_hw_stat_delta *new_stat; struct dm_hw_stat_delta *new_stat;
......
...@@ -163,7 +163,7 @@ static void poll_one_napi(struct napi_struct *napi) ...@@ -163,7 +163,7 @@ static void poll_one_napi(struct napi_struct *napi)
*/ */
work = napi->poll(napi, 0); work = napi->poll(napi, 0);
WARN_ONCE(work, "%pF exceeded budget in poll\n", napi->poll); WARN_ONCE(work, "%pF exceeded budget in poll\n", napi->poll);
trace_napi_poll(napi); trace_napi_poll(napi, work, 0);
clear_bit(NAPI_STATE_NPSVC, &napi->state); clear_bit(NAPI_STATE_NPSVC, &napi->state);
} }
......
...@@ -252,9 +252,10 @@ def irq__irq_handler_exit(name, context, cpu, sec, nsec, pid, comm, callchain, i ...@@ -252,9 +252,10 @@ def irq__irq_handler_exit(name, context, cpu, sec, nsec, pid, comm, callchain, i
event_info = (name, context, cpu, nsecs(sec, nsec), pid, comm, irq, ret) event_info = (name, context, cpu, nsecs(sec, nsec), pid, comm, irq, ret)
all_event_list.append(event_info) all_event_list.append(event_info)
def napi__napi_poll(name, context, cpu, sec, nsec, pid, comm, callchain, napi, dev_name): def napi__napi_poll(name, context, cpu, sec, nsec, pid, comm, callchain, napi,
dev_name, work=None, budget=None):
event_info = (name, context, cpu, nsecs(sec, nsec), pid, comm, event_info = (name, context, cpu, nsecs(sec, nsec), pid, comm,
napi, dev_name) napi, dev_name, work, budget)
all_event_list.append(event_info) all_event_list.append(event_info)
def net__netif_receive_skb(name, context, cpu, sec, nsec, pid, comm, callchain, skbaddr, def net__netif_receive_skb(name, context, cpu, sec, nsec, pid, comm, callchain, skbaddr,
...@@ -354,11 +355,13 @@ def handle_irq_softirq_exit(event_info): ...@@ -354,11 +355,13 @@ def handle_irq_softirq_exit(event_info):
receive_hunk_list.append(rec_data) receive_hunk_list.append(rec_data)
def handle_napi_poll(event_info): def handle_napi_poll(event_info):
(name, context, cpu, time, pid, comm, napi, dev_name) = event_info (name, context, cpu, time, pid, comm, napi, dev_name,
work, budget) = event_info
if cpu in net_rx_dic.keys(): if cpu in net_rx_dic.keys():
event_list = net_rx_dic[cpu]['event_list'] event_list = net_rx_dic[cpu]['event_list']
rec_data = {'event_name':'napi_poll', rec_data = {'event_name':'napi_poll',
'dev':dev_name, 'event_t':time} 'dev':dev_name, 'event_t':time,
'work':work, 'budget':budget}
event_list.append(rec_data) event_list.append(rec_data)
def handle_netif_rx(event_info): def handle_netif_rx(event_info):
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment