Back to home page

OSCL-LXR

 
 

    


0001 /* SPDX-License-Identifier: GPL-2.0 */
0002 /*
0003  *    Copyright IBM Corp. 2002, 2007
0004  *    Author(s): Ingo Adlung <adlung@de.ibm.com>
0005  *       Cornelia Huck <cornelia.huck@de.ibm.com>
0006  *       Arnd Bergmann <arndb@de.ibm.com>
0007  *       Peter Oberparleiter <peter.oberparleiter@de.ibm.com>
0008  */
0009 
0010 #ifndef _ASM_S390_AIRQ_H
0011 #define _ASM_S390_AIRQ_H
0012 
0013 #include <linux/bit_spinlock.h>
0014 #include <linux/dma-mapping.h>
0015 #include <asm/tpi.h>
0016 
0017 struct airq_struct {
0018     struct hlist_node list;     /* Handler queueing. */
0019     void (*handler)(struct airq_struct *airq, struct tpi_info *tpi_info);
0020     u8 *lsi_ptr;            /* Local-Summary-Indicator pointer */
0021     u8 lsi_mask;            /* Local-Summary-Indicator mask */
0022     u8 isc;             /* Interrupt-subclass */
0023     u8 flags;
0024 };
0025 
0026 #define AIRQ_PTR_ALLOCATED  0x01
0027 
0028 int register_adapter_interrupt(struct airq_struct *airq);
0029 void unregister_adapter_interrupt(struct airq_struct *airq);
0030 
0031 /* Adapter interrupt bit vector */
0032 struct airq_iv {
0033     unsigned long *vector;  /* Adapter interrupt bit vector */
0034     dma_addr_t vector_dma; /* Adapter interrupt bit vector dma */
0035     unsigned long *avail;   /* Allocation bit mask for the bit vector */
0036     unsigned long *bitlock; /* Lock bit mask for the bit vector */
0037     unsigned long *ptr; /* Pointer associated with each bit */
0038     unsigned int *data; /* 32 bit value associated with each bit */
0039     unsigned long bits; /* Number of bits in the vector */
0040     unsigned long end;  /* Number of highest allocated bit + 1 */
0041     unsigned long flags;    /* Allocation flags */
0042     spinlock_t lock;    /* Lock to protect alloc & free */
0043 };
0044 
0045 #define AIRQ_IV_ALLOC       1   /* Use an allocation bit mask */
0046 #define AIRQ_IV_BITLOCK     2   /* Allocate the lock bit mask */
0047 #define AIRQ_IV_PTR     4   /* Allocate the ptr array */
0048 #define AIRQ_IV_DATA        8   /* Allocate the data array */
0049 #define AIRQ_IV_CACHELINE   16  /* Cacheline alignment for the vector */
0050 #define AIRQ_IV_GUESTVEC    32  /* Vector is a pinned guest page */
0051 
0052 struct airq_iv *airq_iv_create(unsigned long bits, unsigned long flags,
0053                    unsigned long *vec);
0054 void airq_iv_release(struct airq_iv *iv);
0055 unsigned long airq_iv_alloc(struct airq_iv *iv, unsigned long num);
0056 void airq_iv_free(struct airq_iv *iv, unsigned long bit, unsigned long num);
0057 unsigned long airq_iv_scan(struct airq_iv *iv, unsigned long start,
0058                unsigned long end);
0059 
0060 static inline unsigned long airq_iv_alloc_bit(struct airq_iv *iv)
0061 {
0062     return airq_iv_alloc(iv, 1);
0063 }
0064 
0065 static inline void airq_iv_free_bit(struct airq_iv *iv, unsigned long bit)
0066 {
0067     airq_iv_free(iv, bit, 1);
0068 }
0069 
0070 static inline unsigned long airq_iv_end(struct airq_iv *iv)
0071 {
0072     return iv->end;
0073 }
0074 
0075 static inline void airq_iv_lock(struct airq_iv *iv, unsigned long bit)
0076 {
0077     const unsigned long be_to_le = BITS_PER_LONG - 1;
0078     bit_spin_lock(bit ^ be_to_le, iv->bitlock);
0079 }
0080 
0081 static inline void airq_iv_unlock(struct airq_iv *iv, unsigned long bit)
0082 {
0083     const unsigned long be_to_le = BITS_PER_LONG - 1;
0084     bit_spin_unlock(bit ^ be_to_le, iv->bitlock);
0085 }
0086 
0087 static inline void airq_iv_set_data(struct airq_iv *iv, unsigned long bit,
0088                     unsigned int data)
0089 {
0090     iv->data[bit] = data;
0091 }
0092 
0093 static inline unsigned int airq_iv_get_data(struct airq_iv *iv,
0094                         unsigned long bit)
0095 {
0096     return iv->data[bit];
0097 }
0098 
0099 static inline void airq_iv_set_ptr(struct airq_iv *iv, unsigned long bit,
0100                    unsigned long ptr)
0101 {
0102     iv->ptr[bit] = ptr;
0103 }
0104 
0105 static inline unsigned long airq_iv_get_ptr(struct airq_iv *iv,
0106                         unsigned long bit)
0107 {
0108     return iv->ptr[bit];
0109 }
0110 
0111 #endif /* _ASM_S390_AIRQ_H */