File Index
Files and directories
Sign in
FILE

pds_intr.h

File preview with syntax highlighting.

linux-6.19.14/include/linux/pds/pds_intr.h C
  1/* SPDX-License-Identifier: (GPL-2.0 OR Linux-OpenIB) OR BSD-2-Clause */
  2/* Copyright(c) 2023 Advanced Micro Devices, Inc. */
  3
  4#ifndef _PDS_INTR_H_
  5#define _PDS_INTR_H_
  6
  7/*
  8 * Interrupt control register
  9 * @coal_init:        Coalescing timer initial value, in
 10 *                    device units.  Use @identity->intr_coal_mult
 11 *                    and @identity->intr_coal_div to convert from
 12 *                    usecs to device units:
 13 *
 14 *                      coal_init = coal_usecs * coal_mutl / coal_div
 15 *
 16 *                    When an interrupt is sent the interrupt
 17 *                    coalescing timer current value
 18 *                    (@coalescing_curr) is initialized with this
 19 *                    value and begins counting down.  No more
 20 *                    interrupts are sent until the coalescing
 21 *                    timer reaches 0.  When @coalescing_init=0
 22 *                    interrupt coalescing is effectively disabled
 23 *                    and every interrupt assert results in an
 24 *                    interrupt.  Reset value: 0
 25 * @mask:             Interrupt mask.  When @mask=1 the interrupt
 26 *                    resource will not send an interrupt.  When
 27 *                    @mask=0 the interrupt resource will send an
 28 *                    interrupt if an interrupt event is pending
 29 *                    or on the next interrupt assertion event.
 30 *                    Reset value: 1
 31 * @credits:          Interrupt credits.  This register indicates
 32 *                    how many interrupt events the hardware has
 33 *                    sent.  When written by software this
 34 *                    register atomically decrements @int_credits
 35 *                    by the value written.  When @int_credits
 36 *                    becomes 0 then the "pending interrupt" bit
 37 *                    in the Interrupt Status register is cleared
 38 *                    by the hardware and any pending but unsent
 39 *                    interrupts are cleared.
 40 *                    !!!IMPORTANT!!! This is a signed register.
 41 * @flags:            Interrupt control flags
 42 *                       @unmask -- When this bit is written with a 1
 43 *                       the interrupt resource will set mask=0.
 44 *                       @coal_timer_reset -- When this
 45 *                       bit is written with a 1 the
 46 *                       @coalescing_curr will be reloaded with
 47 *                       @coalescing_init to reset the coalescing
 48 *                       timer.
 49 * @mask_on_assert:   Automatically mask on assertion.  When
 50 *                    @mask_on_assert=1 the interrupt resource
 51 *                    will set @mask=1 whenever an interrupt is
 52 *                    sent.  When using interrupts in Legacy
 53 *                    Interrupt mode the driver must select
 54 *                    @mask_on_assert=0 for proper interrupt
 55 *                    operation.
 56 * @coalescing_curr:  Coalescing timer current value, in
 57 *                    microseconds.  When this value reaches 0
 58 *                    the interrupt resource is again eligible to
 59 *                    send an interrupt.  If an interrupt event
 60 *                    is already pending when @coalescing_curr
 61 *                    reaches 0 the pending interrupt will be
 62 *                    sent, otherwise an interrupt will be sent
 63 *                    on the next interrupt assertion event.
 64 */
 65struct pds_core_intr {
 66	u32 coal_init;
 67	u32 mask;
 68	u16 credits;
 69	u16 flags;
 70#define PDS_CORE_INTR_F_UNMASK		0x0001
 71#define PDS_CORE_INTR_F_TIMER_RESET	0x0002
 72	u32 mask_on_assert;
 73	u32 coalescing_curr;
 74	u32 rsvd6[3];
 75};
 76
 77#ifndef __CHECKER__
 78static_assert(sizeof(struct pds_core_intr) == 32);
 79#endif /* __CHECKER__ */
 80
 81#define PDS_CORE_INTR_CTRL_REGS_MAX		2048
 82#define PDS_CORE_INTR_CTRL_COAL_MAX		0x3F
 83#define PDS_CORE_INTR_INDEX_NOT_ASSIGNED	-1
 84
 85struct pds_core_intr_status {
 86	u32 status[2];
 87};
 88
 89/**
 90 * enum pds_core_intr_mask_vals - valid values for mask and mask_assert.
 91 * @PDS_CORE_INTR_MASK_CLEAR:	unmask interrupt.
 92 * @PDS_CORE_INTR_MASK_SET:	mask interrupt.
 93 */
 94enum pds_core_intr_mask_vals {
 95	PDS_CORE_INTR_MASK_CLEAR	= 0,
 96	PDS_CORE_INTR_MASK_SET		= 1,
 97};
 98
 99/**
100 * enum pds_core_intr_credits_bits - Bitwise composition of credits values.
101 * @PDS_CORE_INTR_CRED_COUNT:	bit mask of credit count, no shift needed.
102 * @PDS_CORE_INTR_CRED_COUNT_SIGNED: bit mask of credit count, including sign bit.
103 * @PDS_CORE_INTR_CRED_UNMASK:	unmask the interrupt.
104 * @PDS_CORE_INTR_CRED_RESET_COALESCE: reset the coalesce timer.
105 * @PDS_CORE_INTR_CRED_REARM:	unmask the and reset the timer.
106 */
107enum pds_core_intr_credits_bits {
108	PDS_CORE_INTR_CRED_COUNT		= 0x7fffu,
109	PDS_CORE_INTR_CRED_COUNT_SIGNED		= 0xffffu,
110	PDS_CORE_INTR_CRED_UNMASK		= 0x10000u,
111	PDS_CORE_INTR_CRED_RESET_COALESCE	= 0x20000u,
112	PDS_CORE_INTR_CRED_REARM		= (PDS_CORE_INTR_CRED_UNMASK |
113					   PDS_CORE_INTR_CRED_RESET_COALESCE),
114};
115
116static inline void
117pds_core_intr_coal_init(struct pds_core_intr __iomem *intr_ctrl, u32 coal)
118{
119	iowrite32(coal, &intr_ctrl->coal_init);
120}
121
122static inline void
123pds_core_intr_mask(struct pds_core_intr __iomem *intr_ctrl, u32 mask)
124{
125	iowrite32(mask, &intr_ctrl->mask);
126}
127
128static inline void
129pds_core_intr_credits(struct pds_core_intr __iomem *intr_ctrl,
130		      u32 cred, u32 flags)
131{
132	if (WARN_ON_ONCE(cred > PDS_CORE_INTR_CRED_COUNT)) {
133		cred = ioread32(&intr_ctrl->credits);
134		cred &= PDS_CORE_INTR_CRED_COUNT_SIGNED;
135	}
136
137	iowrite32(cred | flags, &intr_ctrl->credits);
138}
139
140static inline void
141pds_core_intr_clean_flags(struct pds_core_intr __iomem *intr_ctrl, u32 flags)
142{
143	u32 cred;
144
145	cred = ioread32(&intr_ctrl->credits);
146	cred &= PDS_CORE_INTR_CRED_COUNT_SIGNED;
147	cred |= flags;
148	iowrite32(cred, &intr_ctrl->credits);
149}
150
151static inline void
152pds_core_intr_clean(struct pds_core_intr __iomem *intr_ctrl)
153{
154	pds_core_intr_clean_flags(intr_ctrl, PDS_CORE_INTR_CRED_RESET_COALESCE);
155}
156
157static inline void
158pds_core_intr_mask_assert(struct pds_core_intr __iomem *intr_ctrl, u32 mask)
159{
160	iowrite32(mask, &intr_ctrl->mask_on_assert);
161}
162
163#endif /* _PDS_INTR_H_ */
~/ Read-only file preview.