Hi @Qiming Yang, @Jacob Keller Good day! I am seeing a crash in ice/base running DPDK-2111-stable. We use VPP. While looking at DPDK-emails, I see some relevant changes here. Can you please take a look at the back-trace and suggest/point if this has been found and fixed ? (gdb) bt #0 __pthread_kill_implementation (threadid=, signo=signo@entry=6, no_tid=no_tid@entry=0) at pthread_kill.c:44 #1 0x00007fb6f9983773 in __pthread_kill_internal (signo=6, threadid=) at pthread_kill.c:78 #2 0x00007fb6f9938876 in __GI_raise (sig=sig@entry=6) at ../sysdeps/posix/raise.c:26 #3 0x00007fb6f99237e3 in __GI_abort () at abort.c:79 #4 0x00000000004083fa in os_exit (code=code@entry=1) at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/vpp/vnet/main.c:434 #5 0x00007fb6f9c6b8d1 in unix_signal_handler (signum=11, si=, uc=) at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/vlib/unix/main.c:190 #6 #7 0x00007fb6b37e5850 in ice_sq_send_cmd_nolock (hw=0xac0318700, cq=0xac031a1c0, desc=0x7fb6b643c5e0, buf=0xac2a78200, buf_size=6, cd=0x0) at ../git/drivers/net/ice/base/ice_controlq.c:1058 #8 0x00007fb6b37f428a in ice_sq_send_cmd (hw=0xac0318700, cq=0xac031a1c0, desc=0x7fb6b643c5e0, buf=0xac2a78200, buf_size=6, cd=0x0) at ../git/drivers/net/ice/base/ice_controlq.c:1126 #9 0x00007fb6b3824ddb in ice_sq_send_cmd_retry (hw=0xac0318700, cq=0xac031a1c0, desc=0x7fb6b643c5e0, buf=0xac2a78200, buf_size=6, cd=0x0) at ../git/drivers/net/ice/base/ice_common.c:1729 #10 0x00007fb6b38335ee in ice_aq_send_cmd (hw=0xac0318700, desc=0x7fb6b643c5e0, buf=0xac2a78200, buf_size=6, cd=0x0) at ../git/drivers/net/ice/base/ice_common.c:1788 #11 0x00007fb6b3833fca in ice_aq_alloc_free_res (hw=0xac0318700, num_entries=1, buf=0xac2a78200, buf_size=6, opc=ice_aqc_opc_alloc_res, cd=0x0) at ../git/drivers/net/ice/base/ice_common.c:2124 #12 0x00007fb6b38340a1 in ice_alloc_hw_res (hw=0xac0318700, type=96, num=1, btm=false, res=0x7fb6b643f348) at ../git/drivers/net/ice/base/ice_common.c:2154 #13 0x00007fb6b39e25e8 in ice_alloc_prof_id (hw=0xac0318700, blk=ICE_BLK_RSS, prof_id=0x7fb6b643f39f "") at ../git/drivers/net/ice/base/ice_flex_pipe.c:3309 #14 0x00007fb6b3a03659 in ice_add_prof (hw=0xac0318700, blk=ICE_BLK_RSS, id=17179875328, ptypes=0xac2a790fc "", attr=0x0, attr_cnt=0, es=0xac2a78fd0, masks=0xac2a7909a, fd_swap=true) at ../git/drivers/net/ice/base/ice_flex_pipe.c:5028 #15 0x00007fb6b3a20210 in ice_flow_add_prof_sync (hw=0xac0318700, blk=ICE_BLK_RSS, dir=ICE_FLOW_RX, prof_id=17179875328, segs=0xac2a79200, segs_cnt=1 '\001', acts=0x0, acts_cnt=0 '\000', prof=0x7fb6b6444f10) at ../git/drivers/net/ice/base/ice_flow.c:2245 #16 0x00007fb6b3a20f9a in ice_flow_add_prof (hw=0xac0318700, blk=ICE_BLK_RSS, dir=ICE_FLOW_RX, prof_id=17179875328, segs=0xac2a79200, segs_cnt=1 '\001', acts=0x0, acts_cnt=0 '\000', prof=0x7fb6b6444f10) at ../git/drivers/net/ice/base/ice_flow.c:2646 #17 0x00007fb6b3a483af in ice_add_rss_cfg_sync (hw=0xac0318700, vsi_handle=0, cfg=0x7fb6b6444f60) at ../git/drivers/net/ice/base/ice_flow.c:4276 #18 0x00007fb6b3a48503 in ice_add_rss_cfg (hw=0xac0318700, vsi_handle=0, cfg=0x7fb6b6444fe0) at ../git/drivers/net/ice/base/ice_flow.c:4329 #19 0x00007fb6b3c18577 in ice_add_rss_cfg_wrap (pf=0xac031b718, vsi_id=0, cfg=0x7fb6b6444fe0) at ../git/drivers/net/ice/ice_ethdev.c:2998 #20 0x00007fb6b3c186cc in ice_rss_hash_set (pf=0xac031b718, rss_hf=12220) at ../git/drivers/net/ice/ice_ethdev.c:3038 #21 0x00007fb6b3c2eba9 in ice_init_rss (pf=0xac031b718) at ../git/drivers/net/ice/ice_ethdev.c:3289 #22 0x00007fb6b3c2eccd in ice_dev_configure (dev=0x7fb6b8dc04c0 ) at ../git/drivers/net/ice/ice_ethdev.c:3323 #23 0x00007fb6b8ca82a3 in rte_eth_dev_configure (port_id=0, nb_rx_q=2, nb_tx_q=3, dev_conf=0x7fb6bbde3820) at ../git/lib/ethdev/rte_ethdev.c:1633 #24 0x00007fb6b8fb7fef in dpdk_device_setup (xd=xd@entry=0x7fb6bbde37c0) at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/plugins/dpdk/device/common.c:92 #25 0x00007fb6b8fcbe37 in dpdk_lib_init (dm=0x7fb6b901d260 ) at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/plugins/dpdk/device/init.c:759 #26 0x00007fb6b8fd0936 in dpdk_process (vm=0x4aef40 , rt=, f=) at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/plugins/dpdk/device/init.c:1684 #27 0x00007fb6f9c1c7b7 in vlib_process_bootstrap (_a=) at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/vlib/main.c:1477 #28 0x00007fb6f9b24ea8 in clib_calljmp () at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/vppinfra/longjmp.S:123 #29 0x00007fb6b8656d10 in ?? () #30 0x00007fb6f9c2075c in vlib_process_startup (f=0x0, p=0x7fb6b966e080, vm=0x4aef40 ) at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/vlib/main.c:1502 #31 dispatch_process (vm=0x4aef40 , p=0x7fb6b966e080, last_time_stamp=, f=0x0) at /usr/src/debug/vpp/21.01+gitAUTOINC+fdd8bd2f89-r0/git/src/vlib/main.c:1558 #32 0x0000000000000000 in ?? () Thanks, Leela sankar From: Qiming Yang Date: Thursday, April 27, 2023 at 1:38 AM To: dev@dpdk.org Cc: qi.z.zhang@intel.com , Qiming Yang , Jacob Keller Subject: [**EXTERNAL**] [PATCH 03/30] net/ice/base: remove unnecessary control queue array The driver allocates a cmd_buf array in addition to the desc_buf array. This array stores an ice_sq_cd command details structure for each entry in the control queue ring. And improve debug print for control queue messages. Signed-off-by: Jacob Keller Signed-off-by: Qiming Yang --- drivers/net/ice/base/ice_controlq.c | 107 +++++++++++++++------------- drivers/net/ice/base/ice_controlq.h | 3 - 2 files changed, 56 insertions(+), 54 deletions(-) diff --git a/drivers/net/ice/base/ice_controlq.c b/drivers/net/ice/base/ice_controlq.c index c34407b48c..acd6ad249b 100644 --- a/drivers/net/ice/base/ice_controlq.c +++ b/drivers/net/ice/base/ice_controlq.c @@ -101,13 +101,6 @@ ice_alloc_ctrlq_sq_ring(struct ice_hw *hw, struct ice_ctl_q_info *cq) if (!cq->sq.desc_buf.va) return ICE_ERR_NO_MEMORY; - cq->sq.cmd_buf = ice_calloc(hw, cq->num_sq_entries, - sizeof(struct ice_sq_cd)); - if (!cq->sq.cmd_buf) { - ice_free_dma_mem(hw, &cq->sq.desc_buf); - return ICE_ERR_NO_MEMORY; - } - return ICE_SUCCESS; } @@ -176,7 +169,7 @@ ice_alloc_rq_bufs(struct ice_hw *hw, struct ice_ctl_q_info *cq) if (cq->rq_buf_size > ICE_AQ_LG_BUF) desc->flags |= CPU_TO_LE16(ICE_AQ_FLAG_LB); desc->opcode = 0; - /* This is in accordance with Admin queue design, there is no + /* This is in accordance with control queue design, there is no * register for buffer size configuration */ desc->datalen = CPU_TO_LE16(bi->size); @@ -309,9 +302,6 @@ do { \ ice_free_dma_mem((hw), \ &(qi)->ring.r.ring##_bi[i]); \ } \ - /* free the buffer info list */ \ - if ((qi)->ring.cmd_buf) \ - ice_free(hw, (qi)->ring.cmd_buf); \ /* free DMA head */ \ ice_free(hw, (qi)->ring.dma_head); \ } while (0) @@ -379,11 +369,11 @@ static enum ice_status ice_init_sq(struct ice_hw *hw, struct ice_ctl_q_info *cq) } /** - * ice_init_rq - initialize ARQ + * ice_init_rq - initialize receive side of a control queue * @hw: pointer to the hardware structure * @cq: pointer to the specific Control queue * - * The main initialization routine for the Admin Receive (Event) Queue. + * The main initialization routine for Receive side of a control queue. * Prior to calling this function, the driver *MUST* set the following fields * in the cq->structure: * - cq->num_rq_entries @@ -441,7 +431,7 @@ static enum ice_status ice_init_rq(struct ice_hw *hw, struct ice_ctl_q_info *cq) } /** - * ice_shutdown_sq - shutdown the Control ATQ + * ice_shutdown_sq - shutdown the transmit side of a control queue * @hw: pointer to the hardware structure * @cq: pointer to the specific Control queue * @@ -461,7 +451,7 @@ ice_shutdown_sq(struct ice_hw *hw, struct ice_ctl_q_info *cq) goto shutdown_sq_out; } - /* Stop firmware AdminQ processing */ + /* Stop processing of the control queue */ wr32(hw, cq->sq.head, 0); wr32(hw, cq->sq.tail, 0); wr32(hw, cq->sq.len, 0); @@ -834,7 +824,7 @@ void ice_destroy_all_ctrlq(struct ice_hw *hw) } /** - * ice_clean_sq - cleans Admin send queue (ATQ) + * ice_clean_sq - cleans send side of a control queue * @hw: pointer to the hardware structure * @cq: pointer to the specific Control queue * @@ -844,21 +834,17 @@ static u16 ice_clean_sq(struct ice_hw *hw, struct ice_ctl_q_info *cq) { struct ice_ctl_q_ring *sq = &cq->sq; u16 ntc = sq->next_to_clean; - struct ice_sq_cd *details; struct ice_aq_desc *desc; desc = ICE_CTL_Q_DESC(*sq, ntc); - details = ICE_CTL_Q_DETAILS(*sq, ntc); while (rd32(hw, cq->sq.head) != ntc) { ice_debug(hw, ICE_DBG_AQ_MSG, "ntc %d head %d.\n", ntc, rd32(hw, cq->sq.head)); ice_memset(desc, 0, sizeof(*desc), ICE_DMA_MEM); - ice_memset(details, 0, sizeof(*details), ICE_NONDMA_MEM); ntc++; if (ntc == sq->count) ntc = 0; desc = ICE_CTL_Q_DESC(*sq, ntc); - details = ICE_CTL_Q_DETAILS(*sq, ntc); } sq->next_to_clean = ntc; @@ -866,16 +852,42 @@ static u16 ice_clean_sq(struct ice_hw *hw, struct ice_ctl_q_info *cq) return ICE_CTL_Q_DESC_UNUSED(sq); } +/** + * ice_ctl_q_str - Convert control queue type to string + * @qtype: the control queue type + * + * Returns: A string name for the given control queue type. + */ +static const char *ice_ctl_q_str(enum ice_ctl_q qtype) +{ + switch (qtype) { + case ICE_CTL_Q_UNKNOWN: + return "Unknown CQ"; + case ICE_CTL_Q_ADMIN: + return "AQ"; + case ICE_CTL_Q_MAILBOX: + return "MBXQ"; + case ICE_CTL_Q_SB: + return "SBQ"; + default: + return "Unrecognized CQ"; + } +} + /** * ice_debug_cq * @hw: pointer to the hardware structure + * @cq: pointer to the specific Control queue * @desc: pointer to control queue descriptor * @buf: pointer to command buffer * @buf_len: max length of buf + * @response: true if this is the writeback response * * Dumps debug log about control command with descriptor contents. */ -static void ice_debug_cq(struct ice_hw *hw, void *desc, void *buf, u16 buf_len) +static void +ice_debug_cq(struct ice_hw *hw, struct ice_ctl_q_info *cq, + void *desc, void *buf, u16 buf_len, bool response) { struct ice_aq_desc *cq_desc = (struct ice_aq_desc *)desc; u16 datalen, flags; @@ -889,7 +901,8 @@ static void ice_debug_cq(struct ice_hw *hw, void *desc, void *buf, u16 buf_len) datalen = LE16_TO_CPU(cq_desc->datalen); flags = LE16_TO_CPU(cq_desc->flags); - ice_debug(hw, ICE_DBG_AQ_DESC, "CQ CMD: opcode 0x%04X, flags 0x%04X, datalen 0x%04X, retval 0x%04X\n", + ice_debug(hw, ICE_DBG_AQ_DESC, "%s %s: opcode 0x%04X, flags 0x%04X, datalen 0x%04X, retval 0x%04X\n", + ice_ctl_q_str(cq->qtype), response ? "Response" : "Command", LE16_TO_CPU(cq_desc->opcode), flags, datalen, LE16_TO_CPU(cq_desc->retval)); ice_debug(hw, ICE_DBG_AQ_DESC, "\tcookie (h,l) 0x%08X 0x%08X\n", @@ -914,23 +927,23 @@ static void ice_debug_cq(struct ice_hw *hw, void *desc, void *buf, u16 buf_len) } /** - * ice_sq_done - check if FW has processed the Admin Send Queue (ATQ) + * ice_sq_done - check if the last send on a control queue has completed * @hw: pointer to the HW struct * @cq: pointer to the specific Control queue * - * Returns true if the firmware has processed all descriptors on the - * admin send queue. Returns false if there are still requests pending. + * Returns: true if all the descriptors on the send side of a control queue + * are finished processing, false otherwise. */ static bool ice_sq_done(struct ice_hw *hw, struct ice_ctl_q_info *cq) { - /* AQ designers suggest use of head for better + /* control queue designers suggest use of head for better * timing reliability than DD bit */ return rd32(hw, cq->sq.head) == cq->sq.next_to_use; } /** - * ice_sq_send_cmd_nolock - send command to Control Queue (ATQ) + * ice_sq_send_cmd_nolock - send command to a control queue * @hw: pointer to the HW struct * @cq: pointer to the specific Control queue * @desc: prefilled descriptor describing the command (non DMA mem) @@ -938,8 +951,9 @@ static bool ice_sq_done(struct ice_hw *hw, struct ice_ctl_q_info *cq) * @buf_size: size of buffer for indirect commands (or 0 for direct commands) * @cd: pointer to command details structure * - * This is the main send command routine for the ATQ. It runs the queue, - * cleans the queue, etc. + * This is the main send command routine for a control queue. It prepares the + * command into a descriptor, bumps the send queue tail, waits for the command + * to complete, captures status and data for the command, etc. */ enum ice_status ice_sq_send_cmd_nolock(struct ice_hw *hw, struct ice_ctl_q_info *cq, @@ -950,7 +964,6 @@ ice_sq_send_cmd_nolock(struct ice_hw *hw, struct ice_ctl_q_info *cq, struct ice_aq_desc *desc_on_ring; bool cmd_completed = false; enum ice_status status = ICE_SUCCESS; - struct ice_sq_cd *details; u32 total_delay = 0; u16 retval = 0; u32 val = 0; @@ -993,12 +1006,6 @@ ice_sq_send_cmd_nolock(struct ice_hw *hw, struct ice_ctl_q_info *cq, goto sq_send_command_error; } - details = ICE_CTL_Q_DETAILS(cq->sq, cq->sq.next_to_use); - if (cd) - *details = *cd; - else - ice_memset(details, 0, sizeof(*details), ICE_NONDMA_MEM); - /* Call clean and check queue available function to reclaim the * descriptors that were processed by FW/MBX; the function returns the * number of desc available. The clean function called here could be @@ -1035,8 +1042,7 @@ ice_sq_send_cmd_nolock(struct ice_hw *hw, struct ice_ctl_q_info *cq, /* Debug desc and buffer */ ice_debug(hw, ICE_DBG_AQ_DESC, "ATQ: Control Send queue desc and buffer:\n"); - - ice_debug_cq(hw, (void *)desc_on_ring, buf, buf_size); + ice_debug_cq(hw, cq, (void *)desc_on_ring, buf, buf_size, false); (cq->sq.next_to_use)++; if (cq->sq.next_to_use == cq->sq.count) @@ -1084,13 +1090,12 @@ ice_sq_send_cmd_nolock(struct ice_hw *hw, struct ice_ctl_q_info *cq, } ice_debug(hw, ICE_DBG_AQ_MSG, "ATQ: desc and buffer writeback:\n"); - - ice_debug_cq(hw, (void *)desc, buf, buf_size); + ice_debug_cq(hw, cq, (void *)desc, buf, buf_size, true); /* save writeback AQ if requested */ - if (details->wb_desc) - ice_memcpy(details->wb_desc, desc_on_ring, - sizeof(*details->wb_desc), ICE_DMA_TO_NONDMA); + if (cd && cd->wb_desc) + ice_memcpy(cd->wb_desc, desc_on_ring, + sizeof(*cd->wb_desc), ICE_DMA_TO_NONDMA); /* update the error if time out occurred */ if (!cmd_completed) { @@ -1109,7 +1114,7 @@ ice_sq_send_cmd_nolock(struct ice_hw *hw, struct ice_ctl_q_info *cq, } /** - * ice_sq_send_cmd - send command to Control Queue (ATQ) + * ice_sq_send_cmd - send command to a control queue * @hw: pointer to the HW struct * @cq: pointer to the specific Control queue * @desc: prefilled descriptor describing the command @@ -1117,8 +1122,9 @@ ice_sq_send_cmd_nolock(struct ice_hw *hw, struct ice_ctl_q_info *cq, * @buf_size: size of buffer for indirect commands (or 0 for direct commands) * @cd: pointer to command details structure * - * This is the main send command routine for the ATQ. It runs the queue, - * cleans the queue, etc. + * Main command for the transmit side of a control queue. It puts the command + * on the queue, bumps the tail, waits for processing of the command, captures + * command status and results, etc. */ enum ice_status ice_sq_send_cmd(struct ice_hw *hw, struct ice_ctl_q_info *cq, @@ -1160,9 +1166,9 @@ void ice_fill_dflt_direct_cmd_desc(struct ice_aq_desc *desc, u16 opcode) * @e: event info from the receive descriptor, includes any buffers * @pending: number of events that could be left to process * - * This function cleans one Admin Receive Queue element and returns - * the contents through e. It can also return how many events are - * left to process through 'pending'. + * Clean one element from the receive side of a control queue. On return 'e' + * contains contents of the message, and 'pending' contains the number of + * events left to process. */ enum ice_status ice_clean_rq_elem(struct ice_hw *hw, struct ice_ctl_q_info *cq, @@ -1218,8 +1224,7 @@ ice_clean_rq_elem(struct ice_hw *hw, struct ice_ctl_q_info *cq, e->msg_len, ICE_DMA_TO_NONDMA); ice_debug(hw, ICE_DBG_AQ_DESC, "ARQ: desc and buffer:\n"); - - ice_debug_cq(hw, (void *)desc, e->msg_buf, cq->rq_buf_size); + ice_debug_cq(hw, cq, (void *)desc, e->msg_buf, cq->rq_buf_size, true); /* Restore the original datalen and buffer address in the desc, * FW updates datalen to indicate the event message size diff --git a/drivers/net/ice/base/ice_controlq.h b/drivers/net/ice/base/ice_controlq.h index 986604ec3c..5c60469693 100644 --- a/drivers/net/ice/base/ice_controlq.h +++ b/drivers/net/ice/base/ice_controlq.h @@ -43,7 +43,6 @@ enum ice_ctl_q { struct ice_ctl_q_ring { void *dma_head; /* Virtual address to DMA head */ struct ice_dma_mem desc_buf; /* descriptor ring memory */ - void *cmd_buf; /* command buffer memory */ union { struct ice_dma_mem *sq_bi; @@ -73,8 +72,6 @@ struct ice_sq_cd { struct ice_aq_desc *wb_desc; }; -#define ICE_CTL_Q_DETAILS(R, i) (&(((struct ice_sq_cd *)((R).cmd_buf))[i])) - /* rq event information */ struct ice_rq_event_info { struct ice_aq_desc desc; -- 2.25.1