Skip to content

Commit

Permalink
Merge branch 'qed-Doorbell-overflow-recovery'
Browse files Browse the repository at this point in the history
Ariel Elior says:

====================
qed*: Doorbell overflow recovery

Doorbell Overflow
If sufficient CPU cores will send doorbells at a sufficiently high rate, they
can cause an overflow in the doorbell queue block message fifo. When fill level
reaches maximum, the device stops accepting all doorbells from that PF until a
recovery procedure has taken place.

Doorbell Overflow Recovery
The recovery procedure basically means resending the last doorbell for every
doorbelling entity. A doorbelling entity is anything which may send doorbells:
L2 tx ring, rdma sq/rq/cq, light l2, vf l2 tx ring, spq, etc. This relies on
the design assumption that all doorbells are aggregative, so last doorbell
carries the information of all previous doorbells.

APIs
All doorbelling entities need to register with the mechanism before sending
doorbells. The registration entails providing the doorbell address the entity
would be using, and a virtual address where last doorbell data can be found.
Typically fastpath structures already have this construct.

Executing the recovery procedure
Handling the attentions, iterating over all the registered entities and
resending their doorbells, is all handled within qed core module.

Relevance
All doorbelling entities in all protocols need to register with the mechanism,
via the new APIs. Technically this is quite simple (just call the API). Some
protocol fastpath implementation may not have the doorbell data stored anywhere
(compute it from scratch every time) and will have to add such a place.
This is rare and is also better practice (save some cycles on the fastpath).

Performance Penalty
No performance penalty should incur as a result of this feature. If anything
performance can improve by avoiding recalcualtion of doorbell data everytime
doorbell is sent (in some flows).

Add the database used to register doorbelling entities, and APIs for adding
and deleting entries, and logic for traversing the database and doorbelling
once on behalf of all entities.
====================

Signed-off-by: David S. Miller <davem@davemloft.net>
  • Loading branch information
David S. Miller committed Nov 30, 2018
2 parents dd35420 + bd4db88 commit 734317d
Show file tree
Hide file tree
Showing 13 changed files with 756 additions and 47 deletions.
31 changes: 29 additions & 2 deletions drivers/net/ethernet/qlogic/qed/qed.h
Original file line number Diff line number Diff line change
Expand Up @@ -296,6 +296,12 @@ enum qed_wol_support {
QED_WOL_SUPPORT_PME,
};

enum qed_db_rec_exec {
DB_REC_DRY_RUN,
DB_REC_REAL_DEAL,
DB_REC_ONCE,
};

struct qed_hw_info {
/* PCI personality */
enum qed_pci_personality personality;
Expand Down Expand Up @@ -425,6 +431,14 @@ struct qed_qm_info {
u8 num_pf_rls;
};

struct qed_db_recovery_info {
struct list_head list;

/* Lock to protect the doorbell recovery mechanism list */
spinlock_t lock;
u32 db_recovery_counter;
};

struct storm_stats {
u32 address;
u32 len;
Expand Down Expand Up @@ -522,6 +536,7 @@ struct qed_simd_fp_handler {

enum qed_slowpath_wq_flag {
QED_SLOWPATH_MFW_TLV_REQ,
QED_SLOWPATH_PERIODIC_DB_REC,
};

struct qed_hwfn {
Expand Down Expand Up @@ -640,6 +655,9 @@ struct qed_hwfn {
/* L2-related */
struct qed_l2_info *p_l2_info;

/* Mechanism for recovering from doorbell drop */
struct qed_db_recovery_info db_recovery_info;

/* Nvm images number and attributes */
struct qed_nvm_image_info nvm_info;

Expand All @@ -652,11 +670,12 @@ struct qed_hwfn {
struct delayed_work iov_task;
unsigned long iov_task_flags;
#endif

struct z_stream_s *stream;
struct z_stream_s *stream;
bool slowpath_wq_active;
struct workqueue_struct *slowpath_wq;
struct delayed_work slowpath_task;
unsigned long slowpath_task_flags;
u32 periodic_db_rec_count;
};

struct pci_params {
Expand Down Expand Up @@ -897,6 +916,12 @@ u16 qed_get_cm_pq_idx_llt_mtc(struct qed_hwfn *p_hwfn, u8 tc);

#define QED_LEADING_HWFN(dev) (&dev->hwfns[0])

/* doorbell recovery mechanism */
void qed_db_recovery_dp(struct qed_hwfn *p_hwfn);
void qed_db_recovery_execute(struct qed_hwfn *p_hwfn,
enum qed_db_rec_exec db_exec);
bool qed_edpm_enabled(struct qed_hwfn *p_hwfn);

/* Other Linux specific common definitions */
#define DP_NAME(cdev) ((cdev)->name)

Expand Down Expand Up @@ -931,4 +956,6 @@ int qed_mfw_fill_tlv_data(struct qed_hwfn *hwfn,
union qed_mfw_tlv_data *tlv_data);

void qed_hw_info_set_offload_tc(struct qed_hw_info *p_info, u8 tc);

void qed_periodic_db_rec_start(struct qed_hwfn *p_hwfn);
#endif /* _QED_H */
Loading

0 comments on commit 734317d

Please sign in to comment.