drivers/spi/spi-axiado.c
Source file repositories/reference/linux-study-clean/drivers/spi/spi-axiado.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/spi/spi-axiado.c- Extension
.c- Size
- 30468 bytes
- Lines
- 1005
- Domain
- Driver Families
- Bucket
- drivers/spi
- Inferred role
- Driver Families: implementation source
- Status
- source implementation candidate
Why This File Exists
Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Touches IRQ or DMA behavior; this matters for the representative real-device path.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/clk.hlinux/delay.hlinux/gpio/consumer.hlinux/interrupt.hlinux/io.hlinux/module.hlinux/of_irq.hlinux/of_address.hlinux/platform_device.hlinux/pm_runtime.hlinux/spi/spi.hlinux/spi/spi-mem.hlinux/sizes.hspi-axiado.h
Detected Declarations
function ax_spi_readfunction ax_spi_writefunction ax_spi_write_bfunction ax_spi_init_hwfunction ax_spi_chipselectfunction ax_spi_config_clock_modefunction frequencyfunction ax_spi_setup_transferfunction ax_spi_fill_tx_fifofunction processedfunction ax_spi_process_rx_and_finalizefunction ax_spi_irqfunction ax_prepare_messagefunction ax_transfer_onefunction ax_prepare_transfer_hardwarefunction ax_unprepare_transfer_hardwarefunction ax_spi_detect_fifo_depthfunction processedfunction ax_spi_mem_exec_opfunction ax_spi_mem_adjust_op_sizefunction ax_spi_probefunction ax_spi_removefunction ax_spi_suspendfunction ax_spi_resumefunction ax_spi_runtime_resumefunction ax_spi_runtime_suspend
Annotated Snippet
if (xspi->rx_discard) {
xspi->rx_discard--;
} else {
*xspi->rx_buf++ = b;
xspi->rx_copy_remaining--;
}
}
/* This loop processes new words directly from the FIFO */
while (avail_bytes >= 4 && (xspi->rx_copy_remaining || xspi->rx_discard)) {
/* This function should handle reading from the FIFO */
u8 b = ax_spi_get_rx_byte_for_irq(xspi);
if (xspi->rx_discard) {
xspi->rx_discard--;
} else {
*xspi->rx_buf++ = b;
xspi->rx_copy_remaining--;
}
/* ax_spi_get_rx_byte_for_irq fetches a new word when needed
* and updates internal state.
*/
if (xspi->bytes_left_in_current_rx_word_for_irq == 3)
avail_bytes -= 4;
}
/* Completion Check: The transfer is truly complete if all expected
* RX bytes have been copied or discarded.
*/
if (xspi->rx_copy_remaining == 0 && xspi->rx_discard == 0) {
/* Defensive drain: If for some reason there are leftover bytes
* in the HW FIFO after we've logically finished,
* read and discard them to prevent them from corrupting the next transfer.
* This should be a bounded operation.
*/
int safety_words = AX_SPI_RX_FIFO_DRAIN_LIMIT; // Limit to avoid getting stuck
while (ax_spi_read(xspi, AX_SPI_RX_FBCAR) > 0 && safety_words-- > 0)
ax_spi_read(xspi, AX_SPI_RXFIFO);
/* Disable all interrupts for this transfer and finalize. */
ax_spi_write(xspi, AX_SPI_IMR, 0x00);
spi_finalize_current_transfer(ctlr);
return true;
}
return false;
}
/**
* ax_spi_irq - Interrupt service routine of the SPI controller
* @irq: IRQ number
* @dev_id: Pointer to the xspi structure
*
* This function handles RX FIFO almost full and Host Transfer Completed interrupts only.
* On RX FIFO amlost full interrupt this function reads the received data from RX FIFO and
* fills the TX FIFO if there is any data remaining to be transferred.
* On Host Transfer Completed interrupt this function indicates that transfer is completed,
* the SPI subsystem will clear MTC bit.
*
* Return: IRQ_HANDLED when handled; IRQ_NONE otherwise.
*/
static irqreturn_t ax_spi_irq(int irq, void *dev_id)
{
struct spi_controller *ctlr = dev_id;
struct ax_spi *xspi = spi_controller_get_devdata(ctlr);
u32 intr_status;
intr_status = ax_spi_read(xspi, AX_SPI_IVR);
if (!intr_status)
return IRQ_NONE;
/* Handle "Message Transfer Complete" interrupt.
* This means all bytes have been shifted out of the TX FIFO.
* It's time to harvest the final incoming bytes from the RX FIFO.
*/
if (intr_status & AX_SPI_IVR_MTCV) {
/* Clear the MTC interrupt flag immediately. */
ax_spi_write(xspi, AX_SPI_ISR, AX_SPI_ISR_MTC);
/* For a TX-only transfer, rx_buf would be NULL.
* In the spi-core, rx_copy_remaining would be 0.
* So we can finalize immediately.
*/
if (!xspi->rx_buf) {
ax_spi_write(xspi, AX_SPI_IMR, 0x00);
spi_finalize_current_transfer(ctlr);
return IRQ_HANDLED;
}
/* For a full-duplex transfer, process any remaining RX data.
Annotation
- Immediate include surface: `linux/clk.h`, `linux/delay.h`, `linux/gpio/consumer.h`, `linux/interrupt.h`, `linux/io.h`, `linux/module.h`, `linux/of_irq.h`, `linux/of_address.h`.
- Detected declarations: `function ax_spi_read`, `function ax_spi_write`, `function ax_spi_write_b`, `function ax_spi_init_hw`, `function ax_spi_chipselect`, `function ax_spi_config_clock_mode`, `function frequency`, `function ax_spi_setup_transfer`, `function ax_spi_fill_tx_fifo`, `function processed`.
- Atlas domain: Driver Families / drivers/spi.
- Implementation status: source implementation candidate.
- IRQ or DMA behavior appears here, which is relevant to the selected PCIe/NVMe device path.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.