Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge branch '100GbE' of git://git.kernel.org/pub/scm/linux/kernel/git/tnguy/next-queue

Tony Nguyen says:

====================
ice: add support for devlink health events

Przemek Kitszel says:

Reports for two kinds of events are implemented, Malicious Driver
Detection (MDD) and Tx hang.

Patches 1, 2, 3: core improvements (checkpatch.pl, devlink extension)
Patch 4: rename current ice devlink/ files
Patches 5, 6, 7: ice devlink health infra + reporters

Mateusz did good job caring for this series, and hardening the code.

* '100GbE' of git://git.kernel.org/pub/scm/linux/kernel/git/tnguy/next-queue:
ice: Add MDD logging via devlink health
ice: add Tx hang devlink health reporter
ice: rename devlink_port.[ch] to port.[ch]
devlink: add devlink_fmsg_dump_skb() function
devlink: add devlink_fmsg_put() macro
checkpatch: don't complain on _Generic() use
====================

Link: https://patch.msgid.link/20241217210835.3702003-1-anthony.l.nguyen@intel.com
Signed-off-by: Jakub Kicinski <kuba@kernel.org>

+438 -12
+2 -1
drivers/net/ethernet/intel/ice/Makefile
··· 32 32 ice_parser_rt.o \ 33 33 ice_idc.o \ 34 34 devlink/devlink.o \ 35 - devlink/devlink_port.o \ 35 + devlink/health.o \ 36 + devlink/port.o \ 36 37 ice_sf_eth.o \ 37 38 ice_sf_vsi_vlan_ops.o \ 38 39 ice_ddp.o \
+1 -1
drivers/net/ethernet/intel/ice/devlink/devlink.c
··· 6 6 #include "ice.h" 7 7 #include "ice_lib.h" 8 8 #include "devlink.h" 9 - #include "devlink_port.h" 9 + #include "port.h" 10 10 #include "ice_eswitch.h" 11 11 #include "ice_fw_update.h" 12 12 #include "ice_dcb_lib.h"
+1 -1
drivers/net/ethernet/intel/ice/devlink/devlink_port.c drivers/net/ethernet/intel/ice/devlink/port.c
··· 5 5 6 6 #include "ice.h" 7 7 #include "devlink.h" 8 - #include "devlink_port.h" 8 + #include "port.h" 9 9 #include "ice_lib.h" 10 10 #include "ice_fltr.h" 11 11
drivers/net/ethernet/intel/ice/devlink/devlink_port.h drivers/net/ethernet/intel/ice/devlink/port.h
+269
drivers/net/ethernet/intel/ice/devlink/health.c
··· 1 + // SPDX-License-Identifier: GPL-2.0 2 + /* Copyright (c) 2024, Intel Corporation. */ 3 + 4 + #include "health.h" 5 + #include "ice.h" 6 + 7 + #define ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, obj, name) \ 8 + devlink_fmsg_put(fmsg, #name, (obj)->name) 9 + 10 + /** 11 + * ice_devlink_health_report - boilerplate to call given @reporter 12 + * 13 + * @reporter: devlink health reporter to call, do nothing on NULL 14 + * @msg: message to pass up, "event name" is fine 15 + * @priv_ctx: typically some event struct 16 + */ 17 + static void ice_devlink_health_report(struct devlink_health_reporter *reporter, 18 + const char *msg, void *priv_ctx) 19 + { 20 + if (!reporter) 21 + return; 22 + 23 + /* We do not do auto recovering, so return value of the below function 24 + * will always be 0, thus we do ignore it. 25 + */ 26 + devlink_health_report(reporter, msg, priv_ctx); 27 + } 28 + 29 + struct ice_mdd_event { 30 + enum ice_mdd_src src; 31 + u16 vf_num; 32 + u16 queue; 33 + u8 pf_num; 34 + u8 event; 35 + }; 36 + 37 + static const char *ice_mdd_src_to_str(enum ice_mdd_src src) 38 + { 39 + switch (src) { 40 + case ICE_MDD_SRC_TX_PQM: 41 + return "tx_pqm"; 42 + case ICE_MDD_SRC_TX_TCLAN: 43 + return "tx_tclan"; 44 + case ICE_MDD_SRC_TX_TDPU: 45 + return "tx_tdpu"; 46 + case ICE_MDD_SRC_RX: 47 + return "rx"; 48 + default: 49 + return "invalid"; 50 + } 51 + } 52 + 53 + static int 54 + ice_mdd_reporter_dump(struct devlink_health_reporter *reporter, 55 + struct devlink_fmsg *fmsg, void *priv_ctx, 56 + struct netlink_ext_ack *extack) 57 + { 58 + struct ice_mdd_event *mdd_event = priv_ctx; 59 + const char *src; 60 + 61 + if (!mdd_event) 62 + return 0; 63 + 64 + src = ice_mdd_src_to_str(mdd_event->src); 65 + 66 + devlink_fmsg_obj_nest_start(fmsg); 67 + devlink_fmsg_put(fmsg, "src", src); 68 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, mdd_event, pf_num); 69 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, mdd_event, vf_num); 70 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, mdd_event, event); 71 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, mdd_event, queue); 72 + devlink_fmsg_obj_nest_end(fmsg); 73 + 74 + return 0; 75 + } 76 + 77 + /** 78 + * ice_report_mdd_event - Report an MDD event through devlink health 79 + * @pf: the PF device structure 80 + * @src: the HW block that was the source of this MDD event 81 + * @pf_num: the pf_num on which the MDD event occurred 82 + * @vf_num: the vf_num on which the MDD event occurred 83 + * @event: the event type of the MDD event 84 + * @queue: the queue on which the MDD event occurred 85 + * 86 + * Report an MDD event that has occurred on this PF. 87 + */ 88 + void ice_report_mdd_event(struct ice_pf *pf, enum ice_mdd_src src, u8 pf_num, 89 + u16 vf_num, u8 event, u16 queue) 90 + { 91 + struct ice_mdd_event ev = { 92 + .src = src, 93 + .pf_num = pf_num, 94 + .vf_num = vf_num, 95 + .event = event, 96 + .queue = queue, 97 + }; 98 + 99 + ice_devlink_health_report(pf->health_reporters.mdd, "MDD event", &ev); 100 + } 101 + 102 + /** 103 + * ice_fmsg_put_ptr - put hex value of pointer into fmsg 104 + * 105 + * @fmsg: devlink fmsg under construction 106 + * @name: name to pass 107 + * @ptr: 64 bit value to print as hex and put into fmsg 108 + */ 109 + static void ice_fmsg_put_ptr(struct devlink_fmsg *fmsg, const char *name, 110 + void *ptr) 111 + { 112 + char buf[sizeof(ptr) * 3]; 113 + 114 + sprintf(buf, "%p", ptr); 115 + devlink_fmsg_put(fmsg, name, buf); 116 + } 117 + 118 + struct ice_tx_hang_event { 119 + u32 head; 120 + u32 intr; 121 + u16 vsi_num; 122 + u16 queue; 123 + u16 next_to_clean; 124 + u16 next_to_use; 125 + struct ice_tx_ring *tx_ring; 126 + }; 127 + 128 + static int ice_tx_hang_reporter_dump(struct devlink_health_reporter *reporter, 129 + struct devlink_fmsg *fmsg, void *priv_ctx, 130 + struct netlink_ext_ack *extack) 131 + { 132 + struct ice_tx_hang_event *event = priv_ctx; 133 + struct sk_buff *skb; 134 + 135 + if (!event) 136 + return 0; 137 + 138 + skb = event->tx_ring->tx_buf->skb; 139 + devlink_fmsg_obj_nest_start(fmsg); 140 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, event, head); 141 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, event, intr); 142 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, event, vsi_num); 143 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, event, queue); 144 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, event, next_to_clean); 145 + ICE_DEVLINK_FMSG_PUT_FIELD(fmsg, event, next_to_use); 146 + devlink_fmsg_put(fmsg, "irq-mapping", event->tx_ring->q_vector->name); 147 + ice_fmsg_put_ptr(fmsg, "desc-ptr", event->tx_ring->desc); 148 + ice_fmsg_put_ptr(fmsg, "dma-ptr", (void *)(long)event->tx_ring->dma); 149 + ice_fmsg_put_ptr(fmsg, "skb-ptr", skb); 150 + devlink_fmsg_binary_pair_put(fmsg, "desc", event->tx_ring->desc, 151 + event->tx_ring->count * sizeof(struct ice_tx_desc)); 152 + devlink_fmsg_dump_skb(fmsg, skb); 153 + devlink_fmsg_obj_nest_end(fmsg); 154 + 155 + return 0; 156 + } 157 + 158 + void ice_prep_tx_hang_report(struct ice_pf *pf, struct ice_tx_ring *tx_ring, 159 + u16 vsi_num, u32 head, u32 intr) 160 + { 161 + struct ice_health_tx_hang_buf *buf = &pf->health_reporters.tx_hang_buf; 162 + 163 + buf->tx_ring = tx_ring; 164 + buf->vsi_num = vsi_num; 165 + buf->head = head; 166 + buf->intr = intr; 167 + } 168 + 169 + void ice_report_tx_hang(struct ice_pf *pf) 170 + { 171 + struct ice_health_tx_hang_buf *buf = &pf->health_reporters.tx_hang_buf; 172 + struct ice_tx_ring *tx_ring = buf->tx_ring; 173 + 174 + struct ice_tx_hang_event ev = { 175 + .head = buf->head, 176 + .intr = buf->intr, 177 + .vsi_num = buf->vsi_num, 178 + .queue = tx_ring->q_index, 179 + .next_to_clean = tx_ring->next_to_clean, 180 + .next_to_use = tx_ring->next_to_use, 181 + .tx_ring = tx_ring, 182 + }; 183 + 184 + ice_devlink_health_report(pf->health_reporters.tx_hang, "Tx hang", &ev); 185 + } 186 + 187 + static struct devlink_health_reporter * 188 + ice_init_devlink_rep(struct ice_pf *pf, 189 + const struct devlink_health_reporter_ops *ops) 190 + { 191 + struct devlink *devlink = priv_to_devlink(pf); 192 + struct devlink_health_reporter *rep; 193 + const u64 graceful_period = 0; 194 + 195 + rep = devl_health_reporter_create(devlink, ops, graceful_period, pf); 196 + if (IS_ERR(rep)) { 197 + struct device *dev = ice_pf_to_dev(pf); 198 + 199 + dev_err(dev, "failed to create devlink %s health report er", 200 + ops->name); 201 + return NULL; 202 + } 203 + return rep; 204 + } 205 + 206 + #define ICE_DEFINE_HEALTH_REPORTER_OPS(_name) \ 207 + static const struct devlink_health_reporter_ops ice_ ## _name ## _reporter_ops = { \ 208 + .name = #_name, \ 209 + .dump = ice_ ## _name ## _reporter_dump, \ 210 + } 211 + 212 + ICE_DEFINE_HEALTH_REPORTER_OPS(mdd); 213 + ICE_DEFINE_HEALTH_REPORTER_OPS(tx_hang); 214 + 215 + /** 216 + * ice_health_init - allocate and init all ice devlink health reporters and 217 + * accompanied data 218 + * 219 + * @pf: PF struct 220 + */ 221 + void ice_health_init(struct ice_pf *pf) 222 + { 223 + struct ice_health *reps = &pf->health_reporters; 224 + 225 + reps->mdd = ice_init_devlink_rep(pf, &ice_mdd_reporter_ops); 226 + reps->tx_hang = ice_init_devlink_rep(pf, &ice_tx_hang_reporter_ops); 227 + } 228 + 229 + /** 230 + * ice_deinit_devl_reporter - destroy given devlink health reporter 231 + * @reporter: reporter to destroy 232 + */ 233 + static void ice_deinit_devl_reporter(struct devlink_health_reporter *reporter) 234 + { 235 + if (reporter) 236 + devl_health_reporter_destroy(reporter); 237 + } 238 + 239 + /** 240 + * ice_health_deinit - deallocate all ice devlink health reporters and 241 + * accompanied data 242 + * 243 + * @pf: PF struct 244 + */ 245 + void ice_health_deinit(struct ice_pf *pf) 246 + { 247 + ice_deinit_devl_reporter(pf->health_reporters.mdd); 248 + ice_deinit_devl_reporter(pf->health_reporters.tx_hang); 249 + } 250 + 251 + static 252 + void ice_health_assign_healthy_state(struct devlink_health_reporter *reporter) 253 + { 254 + if (reporter) 255 + devlink_health_reporter_state_update(reporter, 256 + DEVLINK_HEALTH_REPORTER_STATE_HEALTHY); 257 + } 258 + 259 + /** 260 + * ice_health_clear - clear devlink health issues after a reset 261 + * @pf: the PF device structure 262 + * 263 + * Mark the PF in healthy state again after a reset has completed. 264 + */ 265 + void ice_health_clear(struct ice_pf *pf) 266 + { 267 + ice_health_assign_healthy_state(pf->health_reporters.mdd); 268 + ice_health_assign_healthy_state(pf->health_reporters.tx_hang); 269 + }
+58
drivers/net/ethernet/intel/ice/devlink/health.h
··· 1 + /* SPDX-License-Identifier: GPL-2.0 */ 2 + /* Copyright (c) 2024, Intel Corporation. */ 3 + 4 + #ifndef _HEALTH_H_ 5 + #define _HEALTH_H_ 6 + 7 + #include <linux/types.h> 8 + 9 + /** 10 + * DOC: health.h 11 + * 12 + * This header file stores everything that is needed for broadly understood 13 + * devlink health mechanism for ice driver. 14 + */ 15 + 16 + struct ice_pf; 17 + struct ice_tx_ring; 18 + 19 + enum ice_mdd_src { 20 + ICE_MDD_SRC_TX_PQM, 21 + ICE_MDD_SRC_TX_TCLAN, 22 + ICE_MDD_SRC_TX_TDPU, 23 + ICE_MDD_SRC_RX, 24 + }; 25 + 26 + /** 27 + * struct ice_health - stores ice devlink health reporters and accompanied data 28 + * @tx_hang: devlink health reporter for tx_hang event 29 + * @mdd: devlink health reporter for MDD detection event 30 + * @tx_hang_buf: pre-allocated place to put info for Tx hang reporter from 31 + * non-sleeping context 32 + * @tx_ring: ring that the hang occurred on 33 + * @head: descriptor head 34 + * @intr: interrupt register value 35 + * @vsi_num: VSI owning the queue that the hang occurred on 36 + */ 37 + struct ice_health { 38 + struct devlink_health_reporter *mdd; 39 + struct devlink_health_reporter *tx_hang; 40 + struct_group_tagged(ice_health_tx_hang_buf, tx_hang_buf, 41 + struct ice_tx_ring *tx_ring; 42 + u32 head; 43 + u32 intr; 44 + u16 vsi_num; 45 + ); 46 + }; 47 + 48 + void ice_health_init(struct ice_pf *pf); 49 + void ice_health_deinit(struct ice_pf *pf); 50 + void ice_health_clear(struct ice_pf *pf); 51 + 52 + void ice_prep_tx_hang_report(struct ice_pf *pf, struct ice_tx_ring *tx_ring, 53 + u16 vsi_num, u32 head, u32 intr); 54 + void ice_report_mdd_event(struct ice_pf *pf, enum ice_mdd_src src, u8 pf_num, 55 + u16 vf_num, u8 event, u16 queue); 56 + void ice_report_tx_hang(struct ice_pf *pf); 57 + 58 + #endif /* _HEALTH_H_ */
+2
drivers/net/ethernet/intel/ice/ice.h
··· 78 78 #include "ice_irq.h" 79 79 #include "ice_dpll.h" 80 80 #include "ice_adapter.h" 81 + #include "devlink/health.h" 81 82 82 83 #define ICE_BAR0 0 83 84 #define ICE_REQ_DESC_MULTIPLE 32 ··· 666 665 struct ice_agg_node vf_agg_node[ICE_MAX_VF_AGG_NODES]; 667 666 struct ice_dplls dplls; 668 667 struct device *hwmon_dev; 668 + struct ice_health health_reporters; 669 669 670 670 u8 num_quanta_prof_used; 671 671 };
+1 -1
drivers/net/ethernet/intel/ice/ice_eswitch.h
··· 5 5 #define _ICE_ESWITCH_H_ 6 6 7 7 #include <net/devlink.h> 8 - #include "devlink/devlink_port.h" 8 + #include "devlink/port.h" 9 9 10 10 #ifdef CONFIG_ICE_SWITCHDEV 11 11 void ice_eswitch_detach_vf(struct ice_pf *pf, struct ice_vf *vf);
+20 -6
drivers/net/ethernet/intel/ice/ice_main.c
··· 14 14 #include "ice_dcb_lib.h" 15 15 #include "ice_dcb_nl.h" 16 16 #include "devlink/devlink.h" 17 - #include "devlink/devlink_port.h" 17 + #include "devlink/port.h" 18 18 #include "ice_sf_eth.h" 19 19 #include "ice_hwmon.h" 20 20 /* Including ice_trace.h with CREATE_TRACE_POINTS defined will generate the ··· 1816 1816 if (netif_msg_tx_err(pf)) 1817 1817 dev_info(dev, "Malicious Driver Detection event %d on TX queue %d PF# %d VF# %d\n", 1818 1818 event, queue, pf_num, vf_num); 1819 + ice_report_mdd_event(pf, ICE_MDD_SRC_TX_PQM, pf_num, vf_num, 1820 + event, queue); 1819 1821 wr32(hw, GL_MDET_TX_PQM, 0xffffffff); 1820 1822 } 1821 1823 ··· 1831 1829 if (netif_msg_tx_err(pf)) 1832 1830 dev_info(dev, "Malicious Driver Detection event %d on TX queue %d PF# %d VF# %d\n", 1833 1831 event, queue, pf_num, vf_num); 1832 + ice_report_mdd_event(pf, ICE_MDD_SRC_TX_TCLAN, pf_num, vf_num, 1833 + event, queue); 1834 1834 wr32(hw, GL_MDET_TX_TCLAN_BY_MAC(hw), U32_MAX); 1835 1835 } 1836 1836 ··· 1846 1842 if (netif_msg_rx_err(pf)) 1847 1843 dev_info(dev, "Malicious Driver Detection event %d on RX queue %d PF# %d VF# %d\n", 1848 1844 event, queue, pf_num, vf_num); 1845 + ice_report_mdd_event(pf, ICE_MDD_SRC_RX, pf_num, vf_num, event, 1846 + queue); 1849 1847 wr32(hw, GL_MDET_RX, 0xffffffff); 1850 1848 } 1851 1849 ··· 2370 2364 struct ice_pf *pf = container_of(work, struct ice_pf, serv_task); 2371 2365 unsigned long start_time = jiffies; 2372 2366 2373 - /* subtasks */ 2367 + if (pf->health_reporters.tx_hang_buf.tx_ring) { 2368 + ice_report_tx_hang(pf); 2369 + pf->health_reporters.tx_hang_buf.tx_ring = NULL; 2370 + } 2374 2371 2375 - /* process reset requests first */ 2376 2372 ice_reset_subtask(pf); 2377 2373 2378 2374 /* bail if a reset/recovery cycle is pending or rebuild failed */ ··· 5095 5087 return err; 5096 5088 5097 5089 ice_devlink_init_regions(pf); 5090 + ice_health_init(pf); 5098 5091 ice_devlink_register(pf); 5099 5092 5100 5093 return 0; ··· 5104 5095 static void ice_deinit_devlink(struct ice_pf *pf) 5105 5096 { 5106 5097 ice_devlink_unregister(pf); 5098 + ice_health_deinit(pf); 5107 5099 ice_devlink_destroy_regions(pf); 5108 5100 ice_devlink_unregister_params(pf); 5109 5101 } ··· 7803 7793 /* if we get here, reset flow is successful */ 7804 7794 clear_bit(ICE_RESET_FAILED, pf->state); 7805 7795 7796 + ice_health_clear(pf); 7797 + 7806 7798 ice_plug_aux_dev(pf); 7807 7799 if (ice_is_feature_supported(pf, ICE_F_SRIOV_LAG)) 7808 7800 ice_lag_rebuild(pf); ··· 8295 8283 8296 8284 if (tx_ring) { 8297 8285 struct ice_hw *hw = &pf->hw; 8298 - u32 head, val = 0; 8286 + u32 head, intr = 0; 8299 8287 8300 8288 head = FIELD_GET(QTX_COMM_HEAD_HEAD_M, 8301 8289 rd32(hw, QTX_COMM_HEAD(vsi->txq_map[txqueue]))); 8302 8290 /* Read interrupt register */ 8303 - val = rd32(hw, GLINT_DYN_CTL(tx_ring->q_vector->reg_idx)); 8291 + intr = rd32(hw, GLINT_DYN_CTL(tx_ring->q_vector->reg_idx)); 8304 8292 8305 8293 netdev_info(netdev, "tx_timeout: VSI_num: %d, Q %u, NTC: 0x%x, HW_HEAD: 0x%x, NTU: 0x%x, INT: 0x%x\n", 8306 8294 vsi->vsi_num, txqueue, tx_ring->next_to_clean, 8307 - head, tx_ring->next_to_use, val); 8295 + head, tx_ring->next_to_use, intr); 8296 + 8297 + ice_prep_tx_hang_report(pf, tx_ring, vsi->vsi_num, head, intr); 8308 8298 } 8309 8299 8310 8300 pf->tx_timeout_last_recovery = jiffies;
+1 -1
drivers/net/ethernet/intel/ice/ice_repr.c
··· 4 4 #include "ice.h" 5 5 #include "ice_eswitch.h" 6 6 #include "devlink/devlink.h" 7 - #include "devlink/devlink_port.h" 7 + #include "devlink/port.h" 8 8 #include "ice_sriov.h" 9 9 #include "ice_tc_lib.h" 10 10 #include "ice_dcb_lib.h"
+1 -1
drivers/net/ethernet/intel/ice/ice_sf_eth.c
··· 5 5 #include "ice_txrx.h" 6 6 #include "ice_fltr.h" 7 7 #include "ice_sf_eth.h" 8 - #include "devlink/devlink_port.h" 9 8 #include "devlink/devlink.h" 9 + #include "devlink/port.h" 10 10 11 11 static const struct net_device_ops ice_sf_netdev_ops = { 12 12 .ndo_open = ice_open,
+13
include/net/devlink.h
··· 1261 1261 .min_burst = _min_burst, \ 1262 1262 } 1263 1263 1264 + #define devlink_fmsg_put(fmsg, name, value) ( \ 1265 + _Generic((value), \ 1266 + bool : devlink_fmsg_bool_pair_put, \ 1267 + u8 : devlink_fmsg_u8_pair_put, \ 1268 + u16 : devlink_fmsg_u32_pair_put, \ 1269 + u32 : devlink_fmsg_u32_pair_put, \ 1270 + u64 : devlink_fmsg_u64_pair_put, \ 1271 + int : devlink_fmsg_u32_pair_put, \ 1272 + char * : devlink_fmsg_string_pair_put, \ 1273 + const char * : devlink_fmsg_string_pair_put) \ 1274 + (fmsg, name, (value))) 1275 + 1264 1276 enum { 1265 1277 /* device supports reload operations */ 1266 1278 DEVLINK_F_RELOAD = 1UL << 0, ··· 2006 1994 2007 1995 int devlink_nl_port_handle_fill(struct sk_buff *msg, struct devlink_port *devlink_port); 2008 1996 size_t devlink_nl_port_handle_size(struct devlink_port *devlink_port); 1997 + void devlink_fmsg_dump_skb(struct devlink_fmsg *fmsg, const struct sk_buff *skb); 2009 1998 2010 1999 #else 2011 2000
+67
net/devlink/health.c
··· 1238 1238 1239 1239 return reporter->ops->test(reporter, info->extack); 1240 1240 } 1241 + 1242 + /** 1243 + * devlink_fmsg_dump_skb - Dump sk_buffer structure 1244 + * @fmsg: devlink formatted message pointer 1245 + * @skb: pointer to skb 1246 + * 1247 + * Dump diagnostic information about sk_buff structure, like headroom, length, 1248 + * tailroom, MAC, etc. 1249 + */ 1250 + void devlink_fmsg_dump_skb(struct devlink_fmsg *fmsg, const struct sk_buff *skb) 1251 + { 1252 + struct skb_shared_info *sh = skb_shinfo(skb); 1253 + struct sock *sk = skb->sk; 1254 + bool has_mac, has_trans; 1255 + 1256 + has_mac = skb_mac_header_was_set(skb); 1257 + has_trans = skb_transport_header_was_set(skb); 1258 + 1259 + devlink_fmsg_pair_nest_start(fmsg, "skb"); 1260 + devlink_fmsg_obj_nest_start(fmsg); 1261 + devlink_fmsg_put(fmsg, "actual len", skb->len); 1262 + devlink_fmsg_put(fmsg, "head len", skb_headlen(skb)); 1263 + devlink_fmsg_put(fmsg, "data len", skb->data_len); 1264 + devlink_fmsg_put(fmsg, "tail len", skb_tailroom(skb)); 1265 + devlink_fmsg_put(fmsg, "MAC", has_mac ? skb->mac_header : -1); 1266 + devlink_fmsg_put(fmsg, "MAC len", 1267 + has_mac ? skb_mac_header_len(skb) : -1); 1268 + devlink_fmsg_put(fmsg, "network hdr", skb->network_header); 1269 + devlink_fmsg_put(fmsg, "network hdr len", 1270 + has_trans ? skb_network_header_len(skb) : -1); 1271 + devlink_fmsg_put(fmsg, "transport hdr", 1272 + has_trans ? skb->transport_header : -1); 1273 + devlink_fmsg_put(fmsg, "csum", (__force u32)skb->csum); 1274 + devlink_fmsg_put(fmsg, "csum_ip_summed", (u8)skb->ip_summed); 1275 + devlink_fmsg_put(fmsg, "csum_complete_sw", !!skb->csum_complete_sw); 1276 + devlink_fmsg_put(fmsg, "csum_valid", !!skb->csum_valid); 1277 + devlink_fmsg_put(fmsg, "csum_level", (u8)skb->csum_level); 1278 + devlink_fmsg_put(fmsg, "sw_hash", !!skb->sw_hash); 1279 + devlink_fmsg_put(fmsg, "l4_hash", !!skb->l4_hash); 1280 + devlink_fmsg_put(fmsg, "proto", ntohs(skb->protocol)); 1281 + devlink_fmsg_put(fmsg, "pkt_type", (u8)skb->pkt_type); 1282 + devlink_fmsg_put(fmsg, "iif", skb->skb_iif); 1283 + 1284 + if (sk) { 1285 + devlink_fmsg_pair_nest_start(fmsg, "sk"); 1286 + devlink_fmsg_obj_nest_start(fmsg); 1287 + devlink_fmsg_put(fmsg, "family", sk->sk_type); 1288 + devlink_fmsg_put(fmsg, "type", sk->sk_type); 1289 + devlink_fmsg_put(fmsg, "proto", sk->sk_protocol); 1290 + devlink_fmsg_obj_nest_end(fmsg); 1291 + devlink_fmsg_pair_nest_end(fmsg); 1292 + } 1293 + 1294 + devlink_fmsg_obj_nest_end(fmsg); 1295 + devlink_fmsg_pair_nest_end(fmsg); 1296 + 1297 + devlink_fmsg_pair_nest_start(fmsg, "shinfo"); 1298 + devlink_fmsg_obj_nest_start(fmsg); 1299 + devlink_fmsg_put(fmsg, "tx_flags", sh->tx_flags); 1300 + devlink_fmsg_put(fmsg, "nr_frags", sh->nr_frags); 1301 + devlink_fmsg_put(fmsg, "gso_size", sh->gso_size); 1302 + devlink_fmsg_put(fmsg, "gso_type", sh->gso_type); 1303 + devlink_fmsg_put(fmsg, "gso_segs", sh->gso_segs); 1304 + devlink_fmsg_obj_nest_end(fmsg); 1305 + devlink_fmsg_pair_nest_end(fmsg); 1306 + } 1307 + EXPORT_SYMBOL_GPL(devlink_fmsg_dump_skb);
+2
scripts/checkpatch.pl
··· 5843 5843 #CamelCase 5844 5844 if ($var !~ /^$Constant$/ && 5845 5845 $var =~ /[A-Z][a-z]|[a-z][A-Z]/ && 5846 + #Ignore C keywords 5847 + $var !~ /^_Generic$/ && 5846 5848 #Ignore some autogenerated defines and enum values 5847 5849 $var !~ /^(?:[A-Z]+_){1,5}[A-Z]{1,3}[a-z]/ && 5848 5850 #Ignore Page<foo> variants