sym_misc.h 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177
  1. /* SPDX-License-Identifier: GPL-2.0-or-later */
  2. /*
  3. * Device driver for the SYMBIOS/LSILOGIC 53C8XX and 53C1010 family
  4. * of PCI-SCSI IO processors.
  5. *
  6. * Copyright (C) 1999-2001 Gerard Roudier <groudier@free.fr>
  7. *
  8. * This driver is derived from the Linux sym53c8xx driver.
  9. * Copyright (C) 1998-2000 Gerard Roudier
  10. *
  11. * The sym53c8xx driver is derived from the ncr53c8xx driver that had been
  12. * a port of the FreeBSD ncr driver to Linux-1.2.13.
  13. *
  14. * The original ncr driver has been written for 386bsd and FreeBSD by
  15. * Wolfgang Stanglmeier <wolf@cologne.de>
  16. * Stefan Esser <se@mi.Uni-Koeln.de>
  17. * Copyright (C) 1994 Wolfgang Stanglmeier
  18. *
  19. * Other major contributions:
  20. *
  21. * NVRAM detection and reading.
  22. * Copyright (C) 1997 Richard Waltham <dormouse@farsrobt.demon.co.uk>
  23. *
  24. *-----------------------------------------------------------------------------
  25. */
  26. #ifndef SYM_MISC_H
  27. #define SYM_MISC_H
  28. /*
  29. * A la VMS/CAM-3 queue management.
  30. */
  31. typedef struct sym_quehead {
  32. struct sym_quehead *flink; /* Forward pointer */
  33. struct sym_quehead *blink; /* Backward pointer */
  34. } SYM_QUEHEAD;
  35. #define sym_que_init(ptr) do { \
  36. (ptr)->flink = (ptr); (ptr)->blink = (ptr); \
  37. } while (0)
  38. static inline struct sym_quehead *sym_que_first(struct sym_quehead *head)
  39. {
  40. return (head->flink == head) ? 0 : head->flink;
  41. }
  42. static inline struct sym_quehead *sym_que_last(struct sym_quehead *head)
  43. {
  44. return (head->blink == head) ? 0 : head->blink;
  45. }
  46. static inline void __sym_que_add(struct sym_quehead * new,
  47. struct sym_quehead * blink,
  48. struct sym_quehead * flink)
  49. {
  50. flink->blink = new;
  51. new->flink = flink;
  52. new->blink = blink;
  53. blink->flink = new;
  54. }
  55. static inline void __sym_que_del(struct sym_quehead * blink,
  56. struct sym_quehead * flink)
  57. {
  58. flink->blink = blink;
  59. blink->flink = flink;
  60. }
  61. static inline int sym_que_empty(struct sym_quehead *head)
  62. {
  63. return head->flink == head;
  64. }
  65. static inline void sym_que_splice(struct sym_quehead *list,
  66. struct sym_quehead *head)
  67. {
  68. struct sym_quehead *first = list->flink;
  69. if (first != list) {
  70. struct sym_quehead *last = list->blink;
  71. struct sym_quehead *at = head->flink;
  72. first->blink = head;
  73. head->flink = first;
  74. last->flink = at;
  75. at->blink = last;
  76. }
  77. }
  78. static inline void sym_que_move(struct sym_quehead *orig,
  79. struct sym_quehead *dest)
  80. {
  81. struct sym_quehead *first, *last;
  82. first = orig->flink;
  83. if (first != orig) {
  84. first->blink = dest;
  85. dest->flink = first;
  86. last = orig->blink;
  87. last->flink = dest;
  88. dest->blink = last;
  89. orig->flink = orig;
  90. orig->blink = orig;
  91. } else {
  92. dest->flink = dest;
  93. dest->blink = dest;
  94. }
  95. }
  96. #define sym_que_entry(ptr, type, member) container_of(ptr, type, member)
  97. #define sym_insque(new, pos) __sym_que_add(new, pos, (pos)->flink)
  98. #define sym_remque(el) __sym_que_del((el)->blink, (el)->flink)
  99. #define sym_insque_head(new, head) __sym_que_add(new, head, (head)->flink)
  100. static inline struct sym_quehead *sym_remque_head(struct sym_quehead *head)
  101. {
  102. struct sym_quehead *elem = head->flink;
  103. if (elem != head)
  104. __sym_que_del(head, elem->flink);
  105. else
  106. elem = NULL;
  107. return elem;
  108. }
  109. #define sym_insque_tail(new, head) __sym_que_add(new, (head)->blink, head)
  110. static inline struct sym_quehead *sym_remque_tail(struct sym_quehead *head)
  111. {
  112. struct sym_quehead *elem = head->blink;
  113. if (elem != head)
  114. __sym_que_del(elem->blink, head);
  115. else
  116. elem = 0;
  117. return elem;
  118. }
  119. /*
  120. * This one may be useful.
  121. */
  122. #define FOR_EACH_QUEUED_ELEMENT(head, qp) \
  123. for (qp = (head)->flink; qp != (head); qp = qp->flink)
  124. /*
  125. * FreeBSD does not offer our kind of queue in the CAM CCB.
  126. * So, we have to cast.
  127. */
  128. #define sym_qptr(p) ((struct sym_quehead *) (p))
  129. /*
  130. * Simple bitmap operations.
  131. */
  132. #define sym_set_bit(p, n) (((u32 *)(p))[(n)>>5] |= (1<<((n)&0x1f)))
  133. #define sym_clr_bit(p, n) (((u32 *)(p))[(n)>>5] &= ~(1<<((n)&0x1f)))
  134. #define sym_is_bit(p, n) (((u32 *)(p))[(n)>>5] & (1<<((n)&0x1f)))
  135. /*
  136. * The below round up/down macros are to be used with a constant
  137. * as argument (sizeof(...) for example), for the compiler to
  138. * optimize the whole thing.
  139. */
  140. #define _U_(a,m) (a)<=(1<<m)?m:
  141. /*
  142. * Round up logarithm to base 2 of a 16 bit constant.
  143. */
  144. #define _LGRU16_(a) \
  145. ( \
  146. _U_(a, 0)_U_(a, 1)_U_(a, 2)_U_(a, 3)_U_(a, 4)_U_(a, 5)_U_(a, 6)_U_(a, 7) \
  147. _U_(a, 8)_U_(a, 9)_U_(a,10)_U_(a,11)_U_(a,12)_U_(a,13)_U_(a,14)_U_(a,15) \
  148. 16)
  149. #endif /* SYM_MISC_H */