1
- #include <linux/rcupdate.h>
2
- #include <linux/list.h>
3
- #include <linux/netpoll.h>
4
- #include "netpoll_wrapper.h"
5
-
6
- /*
7
- This file contains copies of netpoll_poll_dev() and all related functions that are no longer usable
8
- in kernel 3.15.
9
- */
10
-
11
- #ifndef NETPOLL_POLL_DEV_USABLE
12
-
13
- static int poll_one_napi (struct napi_struct * napi , int budget )
14
- {
15
- int work ;
16
-
17
- /* net_rx_action's ->poll() invocations and our's are
18
- * synchronized by this test which is only made while
19
- * holding the napi->poll_lock.
20
- */
21
- if (!test_bit (NAPI_STATE_SCHED , & napi -> state ))
22
- return budget ;
23
-
24
- if (test_and_set_bit (NAPI_STATE_NPSVC , & napi -> state ))
25
- return budget ;
26
-
27
- work = napi -> poll (napi , budget );
28
- WARN_ONCE (work > budget , "%pF exceeded budget in poll\n" , napi -> poll );
29
-
30
- clear_bit (NAPI_STATE_NPSVC , & napi -> state );
31
-
32
- return budget - work ;
33
- }
34
-
1
+ #include <linux/rcupdate.h>
2
+ #include <linux/list.h>
3
+ #include <linux/netpoll.h>
4
+ #include "netpoll_wrapper.h"
5
+
6
+ /*
7
+ This file contains copies of netpoll_poll_dev() and all related functions that are no longer usable
8
+ in kernel 3.15.
9
+ */
10
+
11
+ #ifndef NETPOLL_POLL_DEV_USABLE
12
+
13
+ static int poll_one_napi (struct napi_struct * napi , int budget )
14
+ {
15
+ int work ;
16
+
17
+ /* net_rx_action's ->poll() invocations and our's are
18
+ * synchronized by this test which is only made while
19
+ * holding the napi->poll_lock.
20
+ */
21
+ if (!test_bit (NAPI_STATE_SCHED , & napi -> state ))
22
+ return budget ;
23
+
24
+ if (test_and_set_bit (NAPI_STATE_NPSVC , & napi -> state ))
25
+ return budget ;
26
+
27
+ work = napi -> poll (napi , budget );
28
+
29
+ clear_bit (NAPI_STATE_NPSVC , & napi -> state );
30
+
31
+ return budget - work ;
32
+ }
33
+
35
34
#if LINUX_VERSION_CODE < KERNEL_VERSION (4 ,10 ,0 )
36
- static void poll_napi (struct net_device * dev , int budget )
37
- {
38
- struct napi_struct * napi ;
39
-
40
- list_for_each_entry (napi , & dev -> napi_list , dev_list ) {
41
- if (napi -> poll_owner != smp_processor_id () &&
42
- spin_trylock (& napi -> poll_lock )) {
43
- budget = poll_one_napi (napi , budget );
44
- spin_unlock (& napi -> poll_lock );
45
- }
46
- }
47
- }
48
- #else
49
- static void __attribute__((optimize ("O2" , "-fno-omit-frame-pointer" ))) poll_napi (struct net_device * dev , int budget )
50
- {
51
- struct napi_struct * napi ;
52
- int cpu = smp_processor_id ();
53
-
54
- list_for_each_entry (napi , & dev -> napi_list , dev_list ) {
55
- if (cmpxchg (& napi -> poll_owner , -1 , cpu ) == -1 ) {
56
- poll_one_napi (napi , budget );
57
- smp_store_release (& napi -> poll_owner , -1 );
58
- }
59
- }
60
- }
61
- #endif
62
-
63
- void netpoll_poll_dev_copy (struct net_device * dev , void (* zap_completion_queue )(void ))
64
- {
65
- const struct net_device_ops * ops ;
66
- struct netpoll_info * ni = rcu_dereference_bh (dev -> npinfo );
67
- int budget = 16 ;
68
-
69
- /* Don't do any rx activity if the dev_lock mutex is held
70
- * the dev_open/close paths use this to block netpoll activity
71
- * while changing device state
72
- */
73
- if (down_trylock (& ni -> dev_lock ))
74
- return ;
75
-
76
- if (!netif_running (dev )) {
77
- up (& ni -> dev_lock );
78
- return ;
79
- }
80
-
81
- ops = dev -> netdev_ops ;
82
- if (!ops -> ndo_poll_controller ) {
83
- up (& ni -> dev_lock );
84
- return ;
85
- }
86
-
87
- /* Process pending work on NIC */
88
- ops -> ndo_poll_controller (dev );
89
-
90
- poll_napi (dev , budget );
91
-
92
- up (& ni -> dev_lock );
93
-
94
- zap_completion_queue ();
95
- }
35
+ static void poll_napi (struct net_device * dev , int budget )
36
+ {
37
+ struct napi_struct * napi ;
38
+
39
+ list_for_each_entry (napi , & dev -> napi_list , dev_list ) {
40
+ if (napi -> poll_owner != smp_processor_id () &&
41
+ spin_trylock (& napi -> poll_lock )) {
42
+ budget = poll_one_napi (napi , budget );
43
+ spin_unlock (& napi -> poll_lock );
44
+ }
45
+ }
46
+ }
47
+ #else
48
+ static void __attribute__((optimize ("O2" , "-fno-omit-frame-pointer" ))) poll_napi (struct net_device * dev , int budget )
49
+ {
50
+ struct napi_struct * napi ;
51
+ int cpu = smp_processor_id ();
52
+
53
+ list_for_each_entry (napi , & dev -> napi_list , dev_list ) {
54
+ if (cmpxchg (& napi -> poll_owner , -1 , cpu ) == -1 ) {
55
+ poll_one_napi (napi , budget );
56
+ smp_store_release (& napi -> poll_owner , -1 );
57
+ }
58
+ }
59
+ }
60
+ #endif
61
+
62
+ void netpoll_poll_dev_copy (struct net_device * dev , void (* zap_completion_queue )(void ))
63
+ {
64
+ const struct net_device_ops * ops ;
65
+ struct netpoll_info * ni = rcu_dereference_bh (dev -> npinfo );
66
+ int budget = 16 ;
67
+
68
+ /* Don't do any rx activity if the dev_lock mutex is held
69
+ * the dev_open/close paths use this to block netpoll activity
70
+ * while changing device state
71
+ */
72
+ if (down_trylock (& ni -> dev_lock ))
73
+ return ;
74
+
75
+ if (!netif_running (dev )) {
76
+ up (& ni -> dev_lock );
77
+ return ;
78
+ }
79
+
80
+ ops = dev -> netdev_ops ;
81
+ if (!ops -> ndo_poll_controller ) {
82
+ up (& ni -> dev_lock );
83
+ return ;
84
+ }
85
+
86
+ /* Process pending work on NIC */
87
+ ops -> ndo_poll_controller (dev );
88
+
89
+ poll_napi (dev , budget );
90
+
91
+ up (& ni -> dev_lock );
92
+
93
+ zap_completion_queue ();
94
+ }
96
95
#endif
0 commit comments