/* * Thunderbolt Cactus Ridge driver - NHI driver * * Copyright (c) 2014 Andreas Noever */ #ifndef DSL3510_H_ #define DSL3510_H_ #include #include /** * struct tb_nhi - thunderbolt native host interface */ struct tb_nhi { struct mutex lock; /* * Must be held during ring creation/destruction. * Is acquired by interrupt_work when dispatching * interrupts to individual rings. **/ struct pci_dev *pdev; void __iomem *iobase; struct tb_ring **tx_rings; struct tb_ring **rx_rings; struct work_struct interrupt_work; u32 hop_count; /* Number of rings (end point hops) supported by NHI. */ }; /** * struct tb_ring - thunderbolt TX or RX ring associated with a NHI */ struct tb_ring { struct mutex lock; /* must be acquired after nhi->lock */ struct tb_nhi *nhi; int size; int hop; int head; /* write next descriptor here */ int tail; /* complete next descriptor here */ struct ring_desc *descriptors; dma_addr_t descriptors_dma; struct list_head queue; struct list_head in_flight; struct work_struct work; bool is_tx:1; /* rx otherwise */ bool running:1; }; struct ring_frame; typedef void (*ring_cb)(struct tb_ring*, struct ring_frame*, bool canceled); /** * struct ring_frame - for use with ring_rx/ring_tx */ struct ring_frame { dma_addr_t buffer_phy; ring_cb callback; struct list_head list; u32 size:12; /* TX: in, RX: out*/ u32 flags:12; /* RX: out */ u32 eof:4; /* TX:in, RX: out */ u32 sof:4; /* TX:in, RX: out */ }; #define TB_FRAME_SIZE 0x100 /* minimum size for ring_rx */ struct tb_ring *ring_alloc_tx(struct tb_nhi *nhi, int hop, int size); struct tb_ring *ring_alloc_rx(struct tb_nhi *nhi, int hop, int size); void ring_start(struct tb_ring *ring); void ring_stop(struct tb_ring *ring); void ring_free(struct tb_ring *ring); int __ring_enqueue(struct tb_ring *ring, struct ring_frame *frame); /** * ring_rx() - enqueue a frame on an RX ring * * frame->buffer, frame->buffer_phy and frame->callback have to be set. The * buffer must contain at least TB_FRAME_SIZE bytes. * * frame->callback will be invoked with frame->size, frame->flags, frame->eof, * frame->sof set once the frame has been received. * * If ring_stop is called after the packet has been enqueued frame->callback * will be called with canceled set to true. * * Return: Returns ESHUTDOWN if ring_stop has been called. Zero otherwise. */ static inline int ring_rx(struct tb_ring *ring, struct ring_frame *frame) { WARN_ON(ring->is_tx); return __ring_enqueue(ring, frame); } /** * ring_tx() - enqueue a frame on an TX ring * * frame->buffer, frame->buffer_phy, frame->callback, frame->size, frame->eof * and frame->sof have to be set. * * frame->callback will be invoked with once the frame has been transmitted. * * If ring_stop is called after the packet has been enqueued frame->callback * will be called with canceled set to true. * * Return: Returns ESHUTDOWN if ring_stop has been called. Zero otherwise. */ static inline int ring_tx(struct tb_ring *ring, struct ring_frame *frame) { WARN_ON(!ring->is_tx); return __ring_enqueue(ring, frame); } #endif git/commit/include/net?h=nds-private-remove&id=08d85f3ea99f1eeafc4e8507936190e86a16ee8c'>net/iucv/iucv.h
diff options
context:
space:
mode:
authorMarc Zyngier <marc.zyngier@arm.com>2017-01-17 16:00:48 +0000
committerThomas Gleixner <tglx@linutronix.de>2017-01-30 15:18:56 +0100
commit08d85f3ea99f1eeafc4e8507936190e86a16ee8c (patch)
tree410bb1acd0cd7dcfaad37ae7b63ff243b7fa4bee /include/net/iucv/iucv.h
parent566cf877a1fcb6d6dc0126b076aad062054c2637 (diff)
irqdomain: Avoid activating interrupts more than once
Since commit f3b0946d629c ("genirq/msi: Make sure PCI MSIs are activated early"), we can end-up activating a PCI/MSI twice (once at allocation time, and once at startup time). This is normally of no consequences, except that there is some HW out there that may misbehave if activate is used more than once (the GICv3 ITS, for example, uses the activate callback to issue the MAPVI command, and the architecture spec says that "If there is an existing mapping for the EventID-DeviceID combination, behavior is UNPREDICTABLE"). While this could be worked around in each individual driver, it may make more sense to tackle the issue at the core level. In order to avoid getting in that situation, let's have a per-interrupt flag to remember if we have already activated that interrupt or not. Fixes: f3b0946d629c ("genirq/msi: Make sure PCI MSIs are activated early") Reported-and-tested-by: Andre Przywara <andre.przywara@arm.com> Signed-off-by: Marc Zyngier <marc.zyngier@arm.com> Cc: stable@vger.kernel.org Link: http://lkml.kernel.org/r/1484668848-24361-1-git-send-email-marc.zyngier@arm.com Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
Diffstat (limited to 'include/net/iucv/iucv.h')