#include <gpxe/list.h>
#include <gpxe/retry.h>
#include <gpxe/tables.h>
#include <gpxe/infiniband.h>
Go to the source code of this file.
Data Structures | |
| struct | ib_mad_agent |
| An Infiniband management agent. More... | |
| struct | ib_mad_transaction_operations |
| Infiniband management transaction operations. More... | |
| struct | ib_mad_transaction |
| An Infiniband management transaction. More... | |
| struct | ib_mad_interface |
| An Infiniband management interface. More... | |
Defines | |
| #define | IB_MAD_AGENTS __table ( struct ib_mad_agent, "ib_mad_agents" ) |
| Infiniband management agents. | |
| #define | __ib_mad_agent __table_entry ( IB_MAD_AGENTS, 01 ) |
| Declare an Infiniband management agent. | |
Functions | |
| FILE_LICENCE (GPL2_OR_LATER) | |
| static __always_inline void | ib_madx_set_ownerdata (struct ib_mad_transaction *madx, void *priv) |
| Set Infiniband management transaction owner-private data. | |
| static __always_inline void * | ib_madx_get_ownerdata (struct ib_mad_transaction *madx) |
| Get Infiniband management transaction owner-private data. | |
| int | ib_mi_send (struct ib_device *ibdev, struct ib_mad_interface *mi, union ib_mad *mad, struct ib_address_vector *av) |
| Transmit MAD. | |
| struct ib_mad_transaction * | ib_create_madx (struct ib_device *ibdev, struct ib_mad_interface *mi, union ib_mad *mad, struct ib_address_vector *av, struct ib_mad_transaction_operations *op) |
| Create management transaction. | |
| void | ib_destroy_madx (struct ib_device *ibdev, struct ib_mad_interface *mi, struct ib_mad_transaction *madx) |
| struct ib_mad_interface * | ib_create_mi (struct ib_device *ibdev, enum ib_queue_pair_type type) |
| Create management interface. | |
| void | ib_destroy_mi (struct ib_device *ibdev, struct ib_mad_interface *mi) |
| Destroy management interface. | |
Definition in file ib_mi.h.
| #define IB_MAD_AGENTS __table ( struct ib_mad_agent, "ib_mad_agents" ) |
| #define __ib_mad_agent __table_entry ( IB_MAD_AGENTS, 01 ) |
| FILE_LICENCE | ( | GPL2_OR_LATER | ) |
| static __always_inline void ib_madx_set_ownerdata | ( | struct ib_mad_transaction * | madx, | |
| void * | priv | |||
| ) | [inline, static] |
Set Infiniband management transaction owner-private data.
| madx | Management transaction | |
| priv | Private data |
Definition at line 106 of file ib_mi.h.
References ib_mad_transaction::owner_priv.
Referenced by ib_cm_path_complete(), ib_create_path(), and ib_mcast_join().
00106 { 00107 madx->owner_priv = priv; 00108 }
| static __always_inline void* ib_madx_get_ownerdata | ( | struct ib_mad_transaction * | madx | ) | [inline, static] |
Get Infiniband management transaction owner-private data.
| madx | Management transaction |
| priv | Private data |
Definition at line 117 of file ib_mi.h.
References ib_mad_transaction::owner_priv.
Referenced by ib_cm_req_complete(), ib_mcast_complete(), and ib_path_complete().
00117 { 00118 return madx->owner_priv; 00119 }
| int ib_mi_send | ( | struct ib_device * | ibdev, | |
| struct ib_mad_interface * | mi, | |||
| union ib_mad * | mad, | |||
| struct ib_address_vector * | av | |||
| ) |
Transmit MAD.
| rc | Return status code |
Definition at line 175 of file ib_mi.c.
References alloc_iob(), assert, ib_mad_hdr::attr_id, ib_mad_hdr::base_version, ib_mad_hdr::class_specific, ib_mad_hdr::class_version, DBGC, DBGC2_HDA, EINVAL, ENOMEM, free_iob(), ib_mad::hdr, ib_smp_class_specific::hop_count, ib_smp_class_specific::hop_pointer, ib_smp_dr_path::hops, htonl, htons, IB_MGMT_BASE_VERSION, IB_MGMT_CLASS_SUBN_DIRECTED_ROUTE, IB_MI_TID_MAGIC, ib_post_send(), IB_SMP_STATUS_D_INBOUND, iob_put, ib_mad_smp::mad_hdr, memcpy, ib_mad_hdr::method, ib_mad_hdr::mgmt_class, next_tid, ntohl, ntohs, ib_device::port, ib_mad_interface::qp, ib_mad_smp::return_path, ib_mad_class_specific::smp, ib_mad::smp, ib_mad_hdr::status, strerror(), and ib_mad_hdr::tid.
Referenced by ib_cm_send_rtu(), ib_mcast_leave(), ib_mi_timer_expired(), ib_sma_guid_info(), ib_sma_node_desc(), ib_sma_node_info(), ib_sma_pkey_table(), and ib_sma_port_info().
00176 { 00177 struct ib_mad_hdr *hdr = &mad->hdr; 00178 struct io_buffer *iobuf; 00179 int rc; 00180 00181 /* Set common fields */ 00182 hdr->base_version = IB_MGMT_BASE_VERSION; 00183 if ( ( hdr->tid[0] == 0 ) && ( hdr->tid[1] == 0 ) ) { 00184 hdr->tid[0] = htonl ( IB_MI_TID_MAGIC ); 00185 hdr->tid[1] = htonl ( ++next_tid ); 00186 } 00187 DBGC ( mi, "MI %p TX TID %08x%08x (%02x,%02x,%02x,%04x) status " 00188 "%04x\n", mi, ntohl ( hdr->tid[0] ), ntohl ( hdr->tid[1] ), 00189 hdr->mgmt_class, hdr->class_version, hdr->method, 00190 ntohs ( hdr->attr_id ), ntohs ( hdr->status ) ); 00191 DBGC2_HDA ( mi, 0, mad, sizeof ( *mad ) ); 00192 00193 /* Construct directed route portion of response, if necessary */ 00194 if ( hdr->mgmt_class == IB_MGMT_CLASS_SUBN_DIRECTED_ROUTE ) { 00195 struct ib_mad_smp *smp = &mad->smp; 00196 unsigned int hop_pointer; 00197 unsigned int hop_count; 00198 00199 smp->mad_hdr.status |= htons ( IB_SMP_STATUS_D_INBOUND ); 00200 hop_pointer = smp->mad_hdr.class_specific.smp.hop_pointer; 00201 hop_count = smp->mad_hdr.class_specific.smp.hop_count; 00202 assert ( hop_count == hop_pointer ); 00203 if ( hop_pointer < ( sizeof ( smp->return_path.hops ) / 00204 sizeof ( smp->return_path.hops[0] ) ) ) { 00205 smp->return_path.hops[hop_pointer] = ibdev->port; 00206 } else { 00207 DBGC ( mi, "MI %p TX TID %08x%08x invalid hop pointer " 00208 "%d\n", mi, ntohl ( hdr->tid[0] ), 00209 ntohl ( hdr->tid[1] ), hop_pointer ); 00210 return -EINVAL; 00211 } 00212 } 00213 00214 /* Construct I/O buffer */ 00215 iobuf = alloc_iob ( sizeof ( *mad ) ); 00216 if ( ! iobuf ) { 00217 DBGC ( mi, "MI %p could not allocate buffer for TID " 00218 "%08x%08x\n", 00219 mi, ntohl ( hdr->tid[0] ), ntohl ( hdr->tid[1] ) ); 00220 return -ENOMEM; 00221 } 00222 memcpy ( iob_put ( iobuf, sizeof ( *mad ) ), mad, sizeof ( *mad ) ); 00223 00224 /* Send I/O buffer */ 00225 if ( ( rc = ib_post_send ( ibdev, mi->qp, av, iobuf ) ) != 0 ) { 00226 DBGC ( mi, "MI %p TX TID %08x%08x failed: %s\n", 00227 mi, ntohl ( hdr->tid[0] ), ntohl ( hdr->tid[1] ), 00228 strerror ( rc ) ); 00229 free_iob ( iobuf ); 00230 return rc; 00231 } 00232 00233 return 0; 00234 }
| struct ib_mad_transaction* ib_create_madx | ( | struct ib_device * | ibdev, | |
| struct ib_mad_interface * | mi, | |||
| union ib_mad * | mad, | |||
| struct ib_address_vector * | av, | |||
| struct ib_mad_transaction_operations * | op | |||
| ) | [read] |
Create management transaction.
| ibdev | Infiniband device | |
| mi | Management interface | |
| mad | MAD to send | |
| av | Destination address, or NULL to use SM's GSI | |
| op | Management transaction operations |
| madx | Management transaction, or NULL |
Definition at line 275 of file ib_mi.c.
References ib_mad_transaction::av, retry_timer::expired, ib_mi_timer_expired(), IB_QKEY_GSI, IB_QPN_GSI, ib_address_vector::lid, ib_mad_transaction::list, list_add, ib_mad_transaction::mad, ib_mad_interface::madx, memcpy, ib_mad_transaction::mi, NULL, ib_mad_transaction::op, ib_address_vector::qkey, ib_address_vector::qpn, ib_address_vector::sl, ib_device::sm_lid, ib_device::sm_sl, start_timer_nodelay(), ib_mad_transaction::timer, and zalloc().
Referenced by ib_cm_path_complete(), ib_create_path(), and ib_mcast_join().
00277 { 00278 struct ib_mad_transaction *madx; 00279 00280 /* Allocate and initialise structure */ 00281 madx = zalloc ( sizeof ( *madx ) ); 00282 if ( ! madx ) 00283 return NULL; 00284 madx->mi = mi; 00285 madx->timer.expired = ib_mi_timer_expired; 00286 madx->op = op; 00287 00288 /* Determine address vector */ 00289 if ( av ) { 00290 memcpy ( &madx->av, av, sizeof ( madx->av ) ); 00291 } else { 00292 madx->av.lid = ibdev->sm_lid; 00293 madx->av.sl = ibdev->sm_sl; 00294 madx->av.qpn = IB_QPN_GSI; 00295 madx->av.qkey = IB_QKEY_GSI; 00296 } 00297 00298 /* Copy MAD */ 00299 memcpy ( &madx->mad, mad, sizeof ( madx->mad ) ); 00300 00301 /* Add to list and start timer to send initial MAD */ 00302 list_add ( &madx->list, &mi->madx ); 00303 start_timer_nodelay ( &madx->timer ); 00304 00305 return madx; 00306 }
| void ib_destroy_madx | ( | struct ib_device * | ibdev, | |
| struct ib_mad_interface * | mi, | |||
| struct ib_mad_transaction * | madx | |||
| ) |
| struct ib_mad_interface* ib_create_mi | ( | struct ib_device * | ibdev, | |
| enum ib_queue_pair_type | type | |||
| ) | [read] |
Create management interface.
| ibdev | Infiniband device | |
| type | Queue pair type |
| mi | Management agent, or NULL |
Definition at line 334 of file ib_mi.c.
References ib_mad_interface::cq, DBGC, free(), ib_create_cq(), ib_create_qp(), ib_destroy_cq(), ib_destroy_qp(), IB_MI_NUM_CQES, IB_MI_NUM_RECV_WQES, IB_MI_NUM_SEND_WQES, ib_modify_qp(), IB_QKEY_GSI, IB_QKEY_SMI, ib_qp_set_ownerdata(), IB_QPT_SMI, ib_refill_recv(), ib_mad_interface::ibdev, INIT_LIST_HEAD, ib_mad_interface::madx, NULL, ib_queue_pair::qkey, ib_mad_interface::qp, ib_queue_pair::qpn, strerror(), and zalloc().
Referenced by ib_open().
00335 { 00336 struct ib_mad_interface *mi; 00337 int rc; 00338 00339 /* Allocate and initialise fields */ 00340 mi = zalloc ( sizeof ( *mi ) ); 00341 if ( ! mi ) 00342 goto err_alloc; 00343 mi->ibdev = ibdev; 00344 INIT_LIST_HEAD ( &mi->madx ); 00345 00346 /* Create completion queue */ 00347 mi->cq = ib_create_cq ( ibdev, IB_MI_NUM_CQES, &ib_mi_completion_ops ); 00348 if ( ! mi->cq ) { 00349 DBGC ( mi, "MI %p could not allocate completion queue\n", mi ); 00350 goto err_create_cq; 00351 } 00352 00353 /* Create queue pair */ 00354 mi->qp = ib_create_qp ( ibdev, type, IB_MI_NUM_SEND_WQES, mi->cq, 00355 IB_MI_NUM_RECV_WQES, mi->cq ); 00356 if ( ! mi->qp ) { 00357 DBGC ( mi, "MI %p could not allocate queue pair\n", mi ); 00358 goto err_create_qp; 00359 } 00360 ib_qp_set_ownerdata ( mi->qp, mi ); 00361 DBGC ( mi, "MI %p (%s) running on QPN %#lx\n", 00362 mi, ( ( type == IB_QPT_SMI ) ? "SMI" : "GSI" ), mi->qp->qpn ); 00363 00364 /* Set queue key */ 00365 mi->qp->qkey = ( ( type == IB_QPT_SMI ) ? IB_QKEY_SMI : IB_QKEY_GSI ); 00366 if ( ( rc = ib_modify_qp ( ibdev, mi->qp ) ) != 0 ) { 00367 DBGC ( mi, "MI %p could not set queue key: %s\n", 00368 mi, strerror ( rc ) ); 00369 goto err_modify_qp; 00370 } 00371 00372 /* Fill receive ring */ 00373 ib_refill_recv ( ibdev, mi->qp ); 00374 return mi; 00375 00376 err_modify_qp: 00377 ib_destroy_qp ( ibdev, mi->qp ); 00378 err_create_qp: 00379 ib_destroy_cq ( ibdev, mi->cq ); 00380 err_create_cq: 00381 free ( mi ); 00382 err_alloc: 00383 return NULL; 00384 }
| void ib_destroy_mi | ( | struct ib_device * | ibdev, | |
| struct ib_mad_interface * | mi | |||
| ) |
Destroy management interface.
| mi | Management interface |
Definition at line 391 of file ib_mi.c.
References ib_mad_transaction_operations::complete, ib_mad_interface::cq, DBGC, ECANCELED, free(), ib_mad::hdr, ib_destroy_cq(), ib_destroy_qp(), ib_mad_transaction::list, list_for_each_entry_safe, ib_mad_transaction::mad, ib_mad_interface::madx, ntohl, NULL, ib_mad_transaction::op, ib_mad_interface::qp, and ib_mad_hdr::tid.
Referenced by ib_close(), and ib_open().
00391 { 00392 struct ib_mad_transaction *madx; 00393 struct ib_mad_transaction *tmp; 00394 00395 /* Flush any outstanding requests */ 00396 list_for_each_entry_safe ( madx, tmp, &mi->madx, list ) { 00397 DBGC ( mi, "MI %p destroyed while TID %08x%08x in progress\n", 00398 mi, ntohl ( madx->mad.hdr.tid[0] ), 00399 ntohl ( madx->mad.hdr.tid[1] ) ); 00400 madx->op->complete ( ibdev, mi, madx, -ECANCELED, NULL, NULL ); 00401 } 00402 00403 ib_destroy_qp ( ibdev, mi->qp ); 00404 ib_destroy_cq ( ibdev, mi->cq ); 00405 free ( mi ); 00406 }
1.5.7.1