選択できるのは25トピックまでです。 トピックは、先頭が英数字で、英数字とダッシュ('-')を使用した35文字以内のものにしてください。

arbel.h 9.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345
  1. #ifndef _ARBEL_H
  2. #define _ARBEL_H
  3. /** @file
  4. *
  5. * Mellanox Arbel Infiniband HCA driver
  6. *
  7. */
  8. /*
  9. * Hardware constants
  10. *
  11. */
  12. /* UAR context table (UCE) resource types */
  13. #define ARBEL_UAR_RES_NONE 0x00
  14. #define ARBEL_UAR_RES_CQ_CI 0x01
  15. #define ARBEL_UAR_RES_CQ_ARM 0x02
  16. #define ARBEL_UAR_RES_SQ 0x03
  17. #define ARBEL_UAR_RES_RQ 0x04
  18. #define ARBEL_UAR_RES_GROUP_SEP 0x07
  19. /* Work queue entry and completion queue entry opcodes */
  20. #define ARBEL_OPCODE_SEND 0x0a
  21. #define ARBEL_OPCODE_RECV_ERROR 0xfe
  22. #define ARBEL_OPCODE_SEND_ERROR 0xff
  23. /* HCA command register opcodes */
  24. #define ARBEL_HCR_QUERY_DEV_LIM 0x0003
  25. #define ARBEL_HCR_SW2HW_CQ 0x0016
  26. #define ARBEL_HCR_HW2SW_CQ 0x0017
  27. #define ARBEL_HCR_RST2INIT_QPEE 0x0019
  28. #define ARBEL_HCR_INIT2RTR_QPEE 0x001a
  29. #define ARBEL_HCR_RTR2RTS_QPEE 0x001b
  30. #define ARBEL_HCR_2RST_QPEE 0x0021
  31. /* Service types */
  32. #define ARBEL_ST_UD 0x03
  33. /* MTUs */
  34. #define ARBEL_MTU_2048 0x04
  35. #define ARBEL_INVALID_LKEY 0x00000100UL
  36. /*
  37. * Wrapper structures for hardware datatypes
  38. *
  39. */
  40. struct MLX_DECLARE_STRUCT ( arbelprm_completion_queue_context );
  41. struct MLX_DECLARE_STRUCT ( arbelprm_completion_queue_entry );
  42. struct MLX_DECLARE_STRUCT ( arbelprm_completion_with_error );
  43. struct MLX_DECLARE_STRUCT ( arbelprm_cq_arm_db_record );
  44. struct MLX_DECLARE_STRUCT ( arbelprm_cq_ci_db_record );
  45. struct MLX_DECLARE_STRUCT ( arbelprm_hca_command_register );
  46. struct MLX_DECLARE_STRUCT ( arbelprm_qp_db_record );
  47. struct MLX_DECLARE_STRUCT ( arbelprm_qp_ee_state_transitions );
  48. struct MLX_DECLARE_STRUCT ( arbelprm_query_dev_lim );
  49. struct MLX_DECLARE_STRUCT ( arbelprm_queue_pair_ee_context_entry );
  50. struct MLX_DECLARE_STRUCT ( arbelprm_recv_wqe_segment_next );
  51. struct MLX_DECLARE_STRUCT ( arbelprm_send_doorbell );
  52. struct MLX_DECLARE_STRUCT ( arbelprm_ud_address_vector );
  53. struct MLX_DECLARE_STRUCT ( arbelprm_wqe_segment_ctrl_send );
  54. struct MLX_DECLARE_STRUCT ( arbelprm_wqe_segment_data_ptr );
  55. struct MLX_DECLARE_STRUCT ( arbelprm_wqe_segment_next );
  56. struct MLX_DECLARE_STRUCT ( arbelprm_wqe_segment_ud );
  57. /*
  58. * Composite hardware datatypes
  59. *
  60. */
  61. #define ARBEL_MAX_GATHER 1
  62. struct arbelprm_ud_send_wqe {
  63. struct arbelprm_wqe_segment_next next;
  64. struct arbelprm_wqe_segment_ctrl_send ctrl;
  65. struct arbelprm_wqe_segment_ud ud;
  66. struct arbelprm_wqe_segment_data_ptr data[ARBEL_MAX_GATHER];
  67. } __attribute__ (( packed ));
  68. #define ARBEL_MAX_SCATTER 1
  69. struct arbelprm_recv_wqe {
  70. /* The autogenerated header is inconsistent between send and
  71. * receive WQEs. The "ctrl" structure for receive WQEs is
  72. * defined to include the "next" structure. Since the "ctrl"
  73. * part of the "ctrl" structure contains only "reserved, must
  74. * be zero" bits, we ignore its definition and provide
  75. * something more usable.
  76. */
  77. struct arbelprm_recv_wqe_segment_next next;
  78. uint32_t ctrl[2]; /* All "reserved, must be zero" */
  79. struct arbelprm_wqe_segment_data_ptr data[ARBEL_MAX_SCATTER];
  80. } __attribute__ (( packed ));
  81. union arbelprm_completion_entry {
  82. struct arbelprm_completion_queue_entry normal;
  83. struct arbelprm_completion_with_error error;
  84. } __attribute__ (( packed ));
  85. union arbelprm_doorbell_record {
  86. struct arbelprm_cq_arm_db_record cq_arm;
  87. struct arbelprm_cq_ci_db_record cq_ci;
  88. struct arbelprm_qp_db_record qp;
  89. } __attribute__ (( packed ));
  90. union arbelprm_doorbell_register {
  91. struct arbelprm_send_doorbell send;
  92. uint32_t dword[2];
  93. } __attribute__ (( packed ));
  94. /*
  95. * gPXE-specific definitions
  96. *
  97. */
  98. /** Arbel device limits */
  99. struct arbel_dev_limits {
  100. /** Number of reserver UARs */
  101. unsigned long reserved_uars;
  102. /** Number of reserved CQs */
  103. unsigned long reserved_cqs;
  104. /** Number of reserved QPs */
  105. unsigned long reserved_qps;
  106. };
  107. /** Alignment of Arbel send work queue entries */
  108. #define ARBEL_SEND_WQE_ALIGN 128
  109. /** An Arbel send work queue entry */
  110. union arbel_send_wqe {
  111. struct arbelprm_ud_send_wqe ud;
  112. uint8_t force_align[ARBEL_SEND_WQE_ALIGN];
  113. } __attribute__ (( packed ));
  114. /** An Arbel send work queue */
  115. struct arbel_send_work_queue {
  116. /** Doorbell record number */
  117. unsigned int doorbell_idx;
  118. /** Work queue entries */
  119. union arbel_send_wqe *wqe;
  120. /** Size of work queue */
  121. size_t wqe_size;
  122. };
  123. /** Alignment of Arbel receive work queue entries */
  124. #define ARBEL_RECV_WQE_ALIGN 64
  125. /** An Arbel receive work queue entry */
  126. union arbel_recv_wqe {
  127. struct arbelprm_recv_wqe recv;
  128. uint8_t force_align[ARBEL_RECV_WQE_ALIGN];
  129. } __attribute__ (( packed ));
  130. /** An Arbel receive work queue */
  131. struct arbel_recv_work_queue {
  132. /** Doorbell record number */
  133. unsigned int doorbell_idx;
  134. /** Work queue entries */
  135. union arbel_recv_wqe *wqe;
  136. /** Size of work queue */
  137. size_t wqe_size;
  138. };
  139. /** Maximum number of allocatable queue pairs
  140. *
  141. * This is a policy decision, not a device limit.
  142. */
  143. #define ARBEL_MAX_QPS 8
  144. /** Base queue pair number */
  145. #define ARBEL_QPN_BASE 0x550000
  146. /** An Arbel queue pair */
  147. struct arbel_queue_pair {
  148. /** Send work queue */
  149. struct arbel_send_work_queue send;
  150. /** Receive work queue */
  151. struct arbel_recv_work_queue recv;
  152. };
  153. /** Maximum number of allocatable completion queues
  154. *
  155. * This is a policy decision, not a device limit.
  156. */
  157. #define ARBEL_MAX_CQS 8
  158. /** An Arbel completion queue */
  159. struct arbel_completion_queue {
  160. /** Consumer counter doorbell record number */
  161. unsigned int ci_doorbell_idx;
  162. /** Arm queue doorbell record number */
  163. unsigned int arm_doorbell_idx;
  164. /** Completion queue entries */
  165. union arbelprm_completion_entry *cqe;
  166. /** Size of completion queue */
  167. size_t cqe_size;
  168. };
  169. /** An Arbel resource bitmask */
  170. typedef uint32_t arbel_bitmask_t;
  171. /** Size of an Arbel resource bitmask */
  172. #define ARBEL_BITMASK_SIZE(max_entries) \
  173. ( ( (max_entries) + ( 8 * sizeof ( arbel_bitmask_t ) ) - 1 ) / \
  174. ( 8 * sizeof ( arbel_bitmask_t ) ) )
  175. /** An Arbel device */
  176. struct arbel {
  177. /** Configuration registers */
  178. void *config;
  179. /** Command input mailbox */
  180. void *mailbox_in;
  181. /** Command output mailbox */
  182. void *mailbox_out;
  183. /** User Access Region */
  184. void *uar;
  185. /** Doorbell records */
  186. union arbelprm_doorbell_record *db_rec;
  187. /** Reserved LKey
  188. *
  189. * Used to get unrestricted memory access.
  190. */
  191. unsigned long reserved_lkey;
  192. /** Event queue number */
  193. unsigned long eqn;
  194. /** Completion queue in-use bitmask */
  195. arbel_bitmask_t cq_inuse[ ARBEL_BITMASK_SIZE ( ARBEL_MAX_CQS ) ];
  196. /** Queue pair in-use bitmask */
  197. arbel_bitmask_t qp_inuse[ ARBEL_BITMASK_SIZE ( ARBEL_MAX_QPS ) ];
  198. /** Device limits */
  199. struct arbel_dev_limits limits;
  200. };
  201. /** Global protection domain */
  202. #define ARBEL_GLOBAL_PD 0x123456
  203. /*
  204. * HCA commands
  205. *
  206. */
  207. #define ARBEL_HCR_BASE 0x80680
  208. #define ARBEL_HCR_REG(x) ( ARBEL_HCR_BASE + 4 * (x) )
  209. #define ARBEL_HCR_MAX_WAIT_MS 2000
  210. /* HCA command is split into
  211. *
  212. * bits 11:0 Opcode
  213. * bit 12 Input uses mailbox
  214. * bit 13 Output uses mailbox
  215. * bits 22:14 Input parameter length (in dwords)
  216. * bits 31:23 Output parameter length (in dwords)
  217. *
  218. * Encoding the information in this way allows us to cut out several
  219. * parameters to the arbel_command() call.
  220. */
  221. #define ARBEL_HCR_IN_MBOX 0x00001000UL
  222. #define ARBEL_HCR_OUT_MBOX 0x00002000UL
  223. #define ARBEL_HCR_OPCODE( _command ) ( (_command) & 0xfff )
  224. #define ARBEL_HCR_IN_LEN( _command ) ( ( (_command) >> 12 ) & 0x7fc )
  225. #define ARBEL_HCR_OUT_LEN( _command ) ( ( (_command) >> 21 ) & 0x7fc )
  226. /** Build HCR command from component parts */
  227. #define ARBEL_HCR_CMD( _opcode, _in_mbox, _in_len, _out_mbox, _out_len ) \
  228. ( (_opcode) | \
  229. ( (_in_mbox) ? ARBEL_HCR_IN_MBOX : 0 ) | \
  230. ( ( (_in_len) / 4 ) << 14 ) | \
  231. ( (_out_mbox) ? ARBEL_HCR_OUT_MBOX : 0 ) | \
  232. ( ( (_out_len) / 4 ) << 23 ) )
  233. #define ARBEL_HCR_IN_CMD( _opcode, _in_mbox, _in_len ) \
  234. ARBEL_HCR_CMD ( _opcode, _in_mbox, _in_len, 0, 0 )
  235. #define ARBEL_HCR_OUT_CMD( _opcode, _out_mbox, _out_len ) \
  236. ARBEL_HCR_CMD ( _opcode, 0, 0, _out_mbox, _out_len )
  237. #define ARBEL_HCR_VOID_CMD( _opcode ) \
  238. ARBEL_HCR_CMD ( _opcode, 0, 0, 0, 0 )
  239. /*
  240. * Doorbell record allocation
  241. *
  242. * The doorbell record map looks like:
  243. *
  244. * ARBEL_MAX_CQS * Arm completion queue doorbell
  245. * ARBEL_MAX_QPS * Send work request doorbell
  246. * Group separator
  247. * ...(empty space)...
  248. * ARBEL_MAX_QPS * Receive work request doorbell
  249. * ARBEL_MAX_CQS * Completion queue consumer counter update doorbell
  250. */
  251. #define ARBEL_MAX_DOORBELL_RECORDS 512
  252. #define ARBEL_GROUP_SEPARATOR_DOORBELL ( ARBEL_MAX_CQS + ARBEL_MAX_QPS )
  253. /**
  254. * Get arm completion queue doorbell index
  255. *
  256. * @v cqn_offset Completion queue number offset
  257. * @ret doorbell_idx Doorbell index
  258. */
  259. static inline unsigned int
  260. arbel_cq_arm_doorbell_idx ( unsigned int cqn_offset ) {
  261. return cqn_offset;
  262. }
  263. /**
  264. * Get send work request doorbell index
  265. *
  266. * @v qpn_offset Queue pair number offset
  267. * @ret doorbell_idx Doorbell index
  268. */
  269. static inline unsigned int
  270. arbel_send_doorbell_idx ( unsigned int qpn_offset ) {
  271. return ( ARBEL_MAX_CQS + qpn_offset );
  272. }
  273. /**
  274. * Get receive work request doorbell index
  275. *
  276. * @v qpn_offset Queue pair number offset
  277. * @ret doorbell_idx Doorbell index
  278. */
  279. static inline unsigned int
  280. arbel_recv_doorbell_idx ( unsigned int qpn_offset ) {
  281. return ( ARBEL_MAX_DOORBELL_RECORDS - ARBEL_MAX_CQS - qpn_offset - 1 );
  282. }
  283. /**
  284. * Get completion queue consumer counter doorbell index
  285. *
  286. * @v cqn_offset Completion queue number offset
  287. * @ret doorbell_idx Doorbell index
  288. */
  289. static inline unsigned int
  290. arbel_cq_ci_doorbell_idx ( unsigned int cqn_offset ) {
  291. return ( ARBEL_MAX_DOORBELL_RECORDS - cqn_offset - 1 );
  292. }
  293. #endif /* _ARBEL_H */