1/* 2 * Copyright (c) 2004 Topspin Communications. All rights reserved. 3 * Copyright (c) 2005 Voltaire, Inc. All rights reserved. 4 * Copyright (c) 2006 Intel Corporation. All rights reserved. 5 * 6 * This software is available to you under a choice of one of two 7 * licenses. You may choose to be licensed under the terms of the GNU 8 * General Public License (GPL) Version 2, available from the file 9 * COPYING in the main directory of this source tree, or the 10 * OpenIB.org BSD license below: 11 * 12 * Redistribution and use in source and binary forms, with or 13 * without modification, are permitted provided that the following 14 * conditions are met: 15 * 16 * - Redistributions of source code must retain the above 17 * copyright notice, this list of conditions and the following 18 * disclaimer. 19 * 20 * - Redistributions in binary form must reproduce the above 21 * copyright notice, this list of conditions and the following 22 * disclaimer in the documentation and/or other materials 23 * provided with the distribution. 24 * 25 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 26 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS 29 * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN 30 * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 31 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 32 * SOFTWARE. 33 */ 34 35#include <linux/module.h> 36#include <linux/err.h> 37#include <linux/random.h> 38#include <linux/spinlock.h> 39#include <linux/slab.h> 40#include <linux/dma-mapping.h> 41#include <linux/kref.h> 42#include <linux/idr.h> 43#include <linux/workqueue.h> 44 45#include <rdma/ib_pack.h> 46#include <rdma/ib_cache.h> 47#include "sa.h" 48 49MODULE_AUTHOR("Roland Dreier"); 50MODULE_DESCRIPTION("InfiniBand subnet administration query support"); 51MODULE_LICENSE("Dual BSD/GPL"); 52 53struct ib_sa_sm_ah { 54 struct ib_ah *ah; 55 struct kref ref; 56 u16 pkey_index; 57 u8 src_path_mask; 58}; 59 60struct ib_sa_port { 61 struct ib_mad_agent *agent; 62 struct ib_mad_agent *notice_agent; 63 struct ib_sa_sm_ah *sm_ah; 64 struct work_struct update_task; 65 spinlock_t ah_lock; 66 u8 port_num; 67 struct ib_device *device; 68}; 69 70struct ib_sa_device { 71 int start_port, end_port; 72 struct ib_event_handler event_handler; 73 struct ib_sa_port port[0]; 74}; 75 76struct ib_sa_query { 77 void (*callback)(struct ib_sa_query *, int, struct ib_sa_mad *); 78 void (*release)(struct ib_sa_query *); 79 struct ib_sa_client *client; 80 struct ib_sa_port *port; 81 struct ib_mad_send_buf *mad_buf; 82 struct ib_sa_sm_ah *sm_ah; 83 int id; 84}; 85 86struct ib_sa_service_query { 87 void (*callback)(int, struct ib_sa_service_rec *, void *); 88 void *context; 89 struct ib_sa_query sa_query; 90}; 91 92struct ib_sa_path_query { 93 void (*callback)(int, struct ib_sa_path_rec *, void *); 94 void *context; 95 struct ib_sa_query sa_query; 96}; 97 98struct ib_sa_mcmember_query { 99 void (*callback)(int, struct ib_sa_mcmember_rec *, void *); 100 void *context; 101 struct ib_sa_query sa_query; 102}; 103 104struct ib_sa_inform_query { 105 void (*callback)(int, struct ib_sa_inform *, void *); 106 void *context; 107 struct ib_sa_query sa_query; 108}; 109 110static void ib_sa_add_one(struct ib_device *device); 111static void ib_sa_remove_one(struct ib_device *device); 112 113static struct ib_client sa_client = { 114 .name = "sa", 115 .add = ib_sa_add_one, 116 .remove = ib_sa_remove_one 117}; 118 119static spinlock_t idr_lock; 120static DEFINE_IDR(query_idr); 121 122static spinlock_t tid_lock; 123static u32 tid; 124 125#define PATH_REC_FIELD(field) \ 126 .struct_offset_bytes = offsetof(struct ib_sa_path_rec, field), \ 127 .struct_size_bytes = sizeof ((struct ib_sa_path_rec *) 0)->field, \ 128 .field_name = "sa_path_rec:" #field 129 130static const struct ib_field path_rec_table[] = { 131 { PATH_REC_FIELD(service_id), 132 .offset_words = 0, 133 .offset_bits = 0, 134 .size_bits = 64 }, 135 { PATH_REC_FIELD(dgid), 136 .offset_words = 2, 137 .offset_bits = 0, 138 .size_bits = 128 }, 139 { PATH_REC_FIELD(sgid), 140 .offset_words = 6, 141 .offset_bits = 0, 142 .size_bits = 128 }, 143 { PATH_REC_FIELD(dlid), 144 .offset_words = 10, 145 .offset_bits = 0, 146 .size_bits = 16 }, 147 { PATH_REC_FIELD(slid), 148 .offset_words = 10, 149 .offset_bits = 16, 150 .size_bits = 16 }, 151 { PATH_REC_FIELD(raw_traffic), 152 .offset_words = 11, 153 .offset_bits = 0, 154 .size_bits = 1 }, 155 { RESERVED, 156 .offset_words = 11, 157 .offset_bits = 1, 158 .size_bits = 3 }, 159 { PATH_REC_FIELD(flow_label), 160 .offset_words = 11, 161 .offset_bits = 4, 162 .size_bits = 20 }, 163 { PATH_REC_FIELD(hop_limit), 164 .offset_words = 11, 165 .offset_bits = 24, 166 .size_bits = 8 }, 167 { PATH_REC_FIELD(traffic_class), 168 .offset_words = 12, 169 .offset_bits = 0, 170 .size_bits = 8 }, 171 { PATH_REC_FIELD(reversible), 172 .offset_words = 12, 173 .offset_bits = 8, 174 .size_bits = 1 }, 175 { PATH_REC_FIELD(numb_path), 176 .offset_words = 12, 177 .offset_bits = 9, 178 .size_bits = 7 }, 179 { PATH_REC_FIELD(pkey), 180 .offset_words = 12, 181 .offset_bits = 16, 182 .size_bits = 16 }, 183 { PATH_REC_FIELD(qos_class), 184 .offset_words = 13, 185 .offset_bits = 0, 186 .size_bits = 12 }, 187 { PATH_REC_FIELD(sl), 188 .offset_words = 13, 189 .offset_bits = 12, 190 .size_bits = 4 }, 191 { PATH_REC_FIELD(mtu_selector), 192 .offset_words = 13, 193 .offset_bits = 16, 194 .size_bits = 2 }, 195 { PATH_REC_FIELD(mtu), 196 .offset_words = 13, 197 .offset_bits = 18, 198 .size_bits = 6 }, 199 { PATH_REC_FIELD(rate_selector), 200 .offset_words = 13, 201 .offset_bits = 24, 202 .size_bits = 2 }, 203 { PATH_REC_FIELD(rate), 204 .offset_words = 13, 205 .offset_bits = 26, 206 .size_bits = 6 }, 207 { PATH_REC_FIELD(packet_life_time_selector), 208 .offset_words = 14, 209 .offset_bits = 0, 210 .size_bits = 2 }, 211 { PATH_REC_FIELD(packet_life_time), 212 .offset_words = 14, 213 .offset_bits = 2, 214 .size_bits = 6 }, 215 { PATH_REC_FIELD(preference), 216 .offset_words = 14, 217 .offset_bits = 8, 218 .size_bits = 8 }, 219 { RESERVED, 220 .offset_words = 14, 221 .offset_bits = 16, 222 .size_bits = 48 }, 223}; 224 225#define MCMEMBER_REC_FIELD(field) \ 226 .struct_offset_bytes = offsetof(struct ib_sa_mcmember_rec, field), \ 227 .struct_size_bytes = sizeof ((struct ib_sa_mcmember_rec *) 0)->field, \ 228 .field_name = "sa_mcmember_rec:" #field 229 230static const struct ib_field mcmember_rec_table[] = { 231 { MCMEMBER_REC_FIELD(mgid), 232 .offset_words = 0, 233 .offset_bits = 0, 234 .size_bits = 128 }, 235 { MCMEMBER_REC_FIELD(port_gid), 236 .offset_words = 4, 237 .offset_bits = 0, 238 .size_bits = 128 }, 239 { MCMEMBER_REC_FIELD(qkey), 240 .offset_words = 8, 241 .offset_bits = 0, 242 .size_bits = 32 }, 243 { MCMEMBER_REC_FIELD(mlid), 244 .offset_words = 9, 245 .offset_bits = 0, 246 .size_bits = 16 }, 247 { MCMEMBER_REC_FIELD(mtu_selector), 248 .offset_words = 9, 249 .offset_bits = 16, 250 .size_bits = 2 }, 251 { MCMEMBER_REC_FIELD(mtu), 252 .offset_words = 9, 253 .offset_bits = 18, 254 .size_bits = 6 }, 255 { MCMEMBER_REC_FIELD(traffic_class), 256 .offset_words = 9, 257 .offset_bits = 24, 258 .size_bits = 8 }, 259 { MCMEMBER_REC_FIELD(pkey), 260 .offset_words = 10, 261 .offset_bits = 0, 262 .size_bits = 16 }, 263 { MCMEMBER_REC_FIELD(rate_selector), 264 .offset_words = 10, 265 .offset_bits = 16, 266 .size_bits = 2 }, 267 { MCMEMBER_REC_FIELD(rate), 268 .offset_words = 10, 269 .offset_bits = 18, 270 .size_bits = 6 }, 271 { MCMEMBER_REC_FIELD(packet_life_time_selector), 272 .offset_words = 10, 273 .offset_bits = 24, 274 .size_bits = 2 }, 275 { MCMEMBER_REC_FIELD(packet_life_time), 276 .offset_words = 10, 277 .offset_bits = 26, 278 .size_bits = 6 }, 279 { MCMEMBER_REC_FIELD(sl), 280 .offset_words = 11, 281 .offset_bits = 0, 282 .size_bits = 4 }, 283 { MCMEMBER_REC_FIELD(flow_label), 284 .offset_words = 11, 285 .offset_bits = 4, 286 .size_bits = 20 }, 287 { MCMEMBER_REC_FIELD(hop_limit), 288 .offset_words = 11, 289 .offset_bits = 24, 290 .size_bits = 8 }, 291 { MCMEMBER_REC_FIELD(scope), 292 .offset_words = 12, 293 .offset_bits = 0, 294 .size_bits = 4 }, 295 { MCMEMBER_REC_FIELD(join_state), 296 .offset_words = 12, 297 .offset_bits = 4, 298 .size_bits = 4 }, 299 { MCMEMBER_REC_FIELD(proxy_join), 300 .offset_words = 12, 301 .offset_bits = 8, 302 .size_bits = 1 }, 303 { RESERVED, 304 .offset_words = 12, 305 .offset_bits = 9, 306 .size_bits = 23 }, 307}; 308 309#define SERVICE_REC_FIELD(field) \ 310 .struct_offset_bytes = offsetof(struct ib_sa_service_rec, field), \ 311 .struct_size_bytes = sizeof ((struct ib_sa_service_rec *) 0)->field, \ 312 .field_name = "sa_service_rec:" #field 313 314static const struct ib_field service_rec_table[] = { 315 { SERVICE_REC_FIELD(id), 316 .offset_words = 0, 317 .offset_bits = 0, 318 .size_bits = 64 }, 319 { SERVICE_REC_FIELD(gid), 320 .offset_words = 2, 321 .offset_bits = 0, 322 .size_bits = 128 }, 323 { SERVICE_REC_FIELD(pkey), 324 .offset_words = 6, 325 .offset_bits = 0, 326 .size_bits = 16 }, 327 { SERVICE_REC_FIELD(lease), 328 .offset_words = 7, 329 .offset_bits = 0, 330 .size_bits = 32 }, 331 { SERVICE_REC_FIELD(key), 332 .offset_words = 8, 333 .offset_bits = 0, 334 .size_bits = 128 }, 335 { SERVICE_REC_FIELD(name), 336 .offset_words = 12, 337 .offset_bits = 0, 338 .size_bits = 64*8 }, 339 { SERVICE_REC_FIELD(data8), 340 .offset_words = 28, 341 .offset_bits = 0, 342 .size_bits = 16*8 }, 343 { SERVICE_REC_FIELD(data16), 344 .offset_words = 32, 345 .offset_bits = 0, 346 .size_bits = 8*16 }, 347 { SERVICE_REC_FIELD(data32), 348 .offset_words = 36, 349 .offset_bits = 0, 350 .size_bits = 4*32 }, 351 { SERVICE_REC_FIELD(data64), 352 .offset_words = 40, 353 .offset_bits = 0, 354 .size_bits = 2*64 }, 355}; 356 357#define INFORM_FIELD(field) \ 358 .struct_offset_bytes = offsetof(struct ib_sa_inform, field), \ 359 .struct_size_bytes = sizeof ((struct ib_sa_inform *) 0)->field, \ 360 .field_name = "sa_inform:" #field 361 362static const struct ib_field inform_table[] = { 363 { INFORM_FIELD(gid), 364 .offset_words = 0, 365 .offset_bits = 0, 366 .size_bits = 128 }, 367 { INFORM_FIELD(lid_range_begin), 368 .offset_words = 4, 369 .offset_bits = 0, 370 .size_bits = 16 }, 371 { INFORM_FIELD(lid_range_end), 372 .offset_words = 4, 373 .offset_bits = 16, 374 .size_bits = 16 }, 375 { RESERVED, 376 .offset_words = 5, 377 .offset_bits = 0, 378 .size_bits = 16 }, 379 { INFORM_FIELD(is_generic), 380 .offset_words = 5, 381 .offset_bits = 16, 382 .size_bits = 8 }, 383 { INFORM_FIELD(subscribe), 384 .offset_words = 5, 385 .offset_bits = 24, 386 .size_bits = 8 }, 387 { INFORM_FIELD(type), 388 .offset_words = 6, 389 .offset_bits = 0, 390 .size_bits = 16 }, 391 { INFORM_FIELD(trap.generic.trap_num), 392 .offset_words = 6, 393 .offset_bits = 16, 394 .size_bits = 16 }, 395 { INFORM_FIELD(trap.generic.qpn), 396 .offset_words = 7, 397 .offset_bits = 0, 398 .size_bits = 24 }, 399 { RESERVED, 400 .offset_words = 7, 401 .offset_bits = 24, 402 .size_bits = 3 }, 403 { INFORM_FIELD(trap.generic.resp_time), 404 .offset_words = 7, 405 .offset_bits = 27, 406 .size_bits = 5 }, 407 { RESERVED, 408 .offset_words = 8, 409 .offset_bits = 0, 410 .size_bits = 8 }, 411 { INFORM_FIELD(trap.generic.producer_type), 412 .offset_words = 8, 413 .offset_bits = 8, 414 .size_bits = 24 }, 415}; 416 417#define NOTICE_FIELD(field) \ 418 .struct_offset_bytes = offsetof(struct ib_sa_notice, field), \ 419 .struct_size_bytes = sizeof ((struct ib_sa_notice *) 0)->field, \ 420 .field_name = "sa_notice:" #field 421 422static const struct ib_field notice_table[] = { 423 { NOTICE_FIELD(is_generic), 424 .offset_words = 0, 425 .offset_bits = 0, 426 .size_bits = 1 }, 427 { NOTICE_FIELD(type), 428 .offset_words = 0, 429 .offset_bits = 1, 430 .size_bits = 7 }, 431 { NOTICE_FIELD(trap.generic.producer_type), 432 .offset_words = 0, 433 .offset_bits = 8, 434 .size_bits = 24 }, 435 { NOTICE_FIELD(trap.generic.trap_num), 436 .offset_words = 1, 437 .offset_bits = 0, 438 .size_bits = 16 }, 439 { NOTICE_FIELD(issuer_lid), 440 .offset_words = 1, 441 .offset_bits = 16, 442 .size_bits = 16 }, 443 { NOTICE_FIELD(notice_toggle), 444 .offset_words = 2, 445 .offset_bits = 0, 446 .size_bits = 1 }, 447 { NOTICE_FIELD(notice_count), 448 .offset_words = 2, 449 .offset_bits = 1, 450 .size_bits = 15 }, 451 { NOTICE_FIELD(data_details), 452 .offset_words = 2, 453 .offset_bits = 16, 454 .size_bits = 432 }, 455 { NOTICE_FIELD(issuer_gid), 456 .offset_words = 16, 457 .offset_bits = 0, 458 .size_bits = 128 }, 459}; 460 461int ib_sa_check_selector(ib_sa_comp_mask comp_mask, 462 ib_sa_comp_mask selector_mask, 463 ib_sa_comp_mask value_mask, 464 u8 selector, u8 src_value, u8 dst_value) 465{ 466 int err; 467 468 if (!(comp_mask & selector_mask) || !(comp_mask & value_mask)) 469 return 0; 470 471 switch (selector) { 472 case IB_SA_GT: 473 err = (src_value <= dst_value); 474 break; 475 case IB_SA_LT: 476 err = (src_value >= dst_value); 477 break; 478 case IB_SA_EQ: 479 err = (src_value != dst_value); 480 break; 481 default: 482 err = 0; 483 break; 484 } 485 486 return err; 487} 488 489int ib_sa_pack_attr(void *dst, void *src, int attr_id) 490{ 491 switch (attr_id) { 492 case IB_SA_ATTR_PATH_REC: 493 ib_pack(path_rec_table, ARRAY_SIZE(path_rec_table), src, dst); 494 break; 495 default: 496 return -EINVAL; 497 } 498 return 0; 499} 500 501int ib_sa_unpack_attr(void *dst, void *src, int attr_id) 502{ 503 switch (attr_id) { 504 case IB_SA_ATTR_PATH_REC: 505 ib_unpack(path_rec_table, ARRAY_SIZE(path_rec_table), src, dst); 506 break; 507 default: 508 return -EINVAL; 509 } 510 return 0; 511} 512 513static void free_sm_ah(struct kref *kref) 514{ 515 struct ib_sa_sm_ah *sm_ah = container_of(kref, struct ib_sa_sm_ah, ref); 516 517 ib_destroy_ah(sm_ah->ah); 518 kfree(sm_ah); 519} 520 521static void update_sm_ah(struct work_struct *work) 522{ 523 struct ib_sa_port *port = 524 container_of(work, struct ib_sa_port, update_task); 525 struct ib_sa_sm_ah *new_ah; 526 struct ib_port_attr port_attr; 527 struct ib_ah_attr ah_attr; 528 529 if (ib_query_port(port->agent->device, port->port_num, &port_attr)) { 530 printk(KERN_WARNING "Couldn't query port\n"); 531 return; 532 } 533 534 new_ah = kmalloc(sizeof *new_ah, GFP_KERNEL); 535 if (!new_ah) { 536 printk(KERN_WARNING "Couldn't allocate new SM AH\n"); 537 return; 538 } 539 540 kref_init(&new_ah->ref); 541 new_ah->src_path_mask = (1 << port_attr.lmc) - 1; 542 543 new_ah->pkey_index = 0; 544 if (ib_find_pkey(port->agent->device, port->port_num, 545 IB_DEFAULT_PKEY_FULL, &new_ah->pkey_index)) 546 printk(KERN_ERR "Couldn't find index for default PKey\n"); 547 548 memset(&ah_attr, 0, sizeof ah_attr); 549 ah_attr.dlid = port_attr.sm_lid; 550 ah_attr.sl = port_attr.sm_sl; 551 ah_attr.port_num = port->port_num; 552 553 new_ah->ah = ib_create_ah(port->agent->qp->pd, &ah_attr); 554 if (IS_ERR(new_ah->ah)) { 555 printk(KERN_WARNING "Couldn't create new SM AH\n"); 556 kfree(new_ah); 557 return; 558 } 559 560 spin_lock_irq(&port->ah_lock); 561 if (port->sm_ah) 562 kref_put(&port->sm_ah->ref, free_sm_ah); 563 port->sm_ah = new_ah; 564 spin_unlock_irq(&port->ah_lock); 565 566} 567 568static void ib_sa_event(struct ib_event_handler *handler, struct ib_event *event) 569{ 570 if (event->event == IB_EVENT_PORT_ERR || 571 event->event == IB_EVENT_PORT_ACTIVE || 572 event->event == IB_EVENT_LID_CHANGE || 573 event->event == IB_EVENT_PKEY_CHANGE || 574 event->event == IB_EVENT_SM_CHANGE || 575 event->event == IB_EVENT_CLIENT_REREGISTER) { 576 unsigned long flags; 577 struct ib_sa_device *sa_dev = 578 container_of(handler, typeof(*sa_dev), event_handler); 579 struct ib_sa_port *port = 580 &sa_dev->port[event->element.port_num - sa_dev->start_port]; 581 582 if (rdma_port_get_link_layer(handler->device, port->port_num) != IB_LINK_LAYER_INFINIBAND) 583 return; 584 585 spin_lock_irqsave(&port->ah_lock, flags); 586 if (port->sm_ah) 587 kref_put(&port->sm_ah->ref, free_sm_ah); 588 port->sm_ah = NULL; 589 spin_unlock_irqrestore(&port->ah_lock, flags); 590 591 schedule_work(&sa_dev->port[event->element.port_num - 592 sa_dev->start_port].update_task); 593 } 594} 595 596void ib_sa_register_client(struct ib_sa_client *client) 597{ 598 atomic_set(&client->users, 1); 599 init_completion(&client->comp); 600} 601EXPORT_SYMBOL(ib_sa_register_client); 602 603void ib_sa_unregister_client(struct ib_sa_client *client) 604{ 605 ib_sa_client_put(client); 606 wait_for_completion(&client->comp); 607} 608EXPORT_SYMBOL(ib_sa_unregister_client); 609 610/** 611 * ib_sa_cancel_query - try to cancel an SA query 612 * @id:ID of query to cancel 613 * @query:query pointer to cancel 614 * 615 * Try to cancel an SA query. If the id and query don't match up or 616 * the query has already completed, nothing is done. Otherwise the 617 * query is canceled and will complete with a status of -EINTR. 618 */ 619void ib_sa_cancel_query(int id, struct ib_sa_query *query) 620{ 621 unsigned long flags; 622 struct ib_mad_agent *agent; 623 struct ib_mad_send_buf *mad_buf; 624 625 spin_lock_irqsave(&idr_lock, flags); 626 if (idr_find(&query_idr, id) != query) { 627 spin_unlock_irqrestore(&idr_lock, flags); 628 return; 629 } 630 agent = query->port->agent; 631 mad_buf = query->mad_buf; 632 spin_unlock_irqrestore(&idr_lock, flags); 633 634 ib_cancel_mad(agent, mad_buf); 635} 636EXPORT_SYMBOL(ib_sa_cancel_query); 637 638static u8 get_src_path_mask(struct ib_device *device, u8 port_num) 639{ 640 struct ib_sa_device *sa_dev; 641 struct ib_sa_port *port; 642 unsigned long flags; 643 u8 src_path_mask; 644 645 sa_dev = ib_get_client_data(device, &sa_client); 646 if (!sa_dev) 647 return 0x7f; 648 649 port = &sa_dev->port[port_num - sa_dev->start_port]; 650 spin_lock_irqsave(&port->ah_lock, flags); 651 src_path_mask = port->sm_ah ? port->sm_ah->src_path_mask : 0x7f; 652 spin_unlock_irqrestore(&port->ah_lock, flags); 653 654 return src_path_mask; 655} 656 657int ib_init_ah_from_path(struct ib_device *device, u8 port_num, 658 struct ib_sa_path_rec *rec, struct ib_ah_attr *ah_attr) 659{ 660 int ret; 661 u16 gid_index; 662 int force_grh; 663 664 memset(ah_attr, 0, sizeof *ah_attr); 665 ah_attr->dlid = be16_to_cpu(rec->dlid); 666 ah_attr->sl = rec->sl; 667 ah_attr->src_path_bits = be16_to_cpu(rec->slid) & 668 get_src_path_mask(device, port_num); 669 ah_attr->port_num = port_num; 670 ah_attr->static_rate = rec->rate; 671 672 force_grh = rdma_port_get_link_layer(device, port_num) == IB_LINK_LAYER_ETHERNET; 673 674 if (rec->hop_limit > 1 || force_grh) { 675 ah_attr->ah_flags = IB_AH_GRH; 676 ah_attr->grh.dgid = rec->dgid; 677 678 ret = ib_find_cached_gid(device, &rec->sgid, &port_num, 679 &gid_index); 680 if (ret) 681 return ret; 682 683 ah_attr->grh.sgid_index = gid_index; 684 ah_attr->grh.flow_label = be32_to_cpu(rec->flow_label); 685 ah_attr->grh.hop_limit = rec->hop_limit; 686 ah_attr->grh.traffic_class = rec->traffic_class; 687 } 688 return 0; 689} 690EXPORT_SYMBOL(ib_init_ah_from_path); 691 692static int alloc_mad(struct ib_sa_query *query, gfp_t gfp_mask) 693{ 694 unsigned long flags; 695 696 spin_lock_irqsave(&query->port->ah_lock, flags); 697 if (!query->port->sm_ah) { 698 spin_unlock_irqrestore(&query->port->ah_lock, flags); 699 return -EAGAIN; 700 } 701 kref_get(&query->port->sm_ah->ref); 702 query->sm_ah = query->port->sm_ah; 703 spin_unlock_irqrestore(&query->port->ah_lock, flags); 704 705 query->mad_buf = ib_create_send_mad(query->port->agent, 1, 706 query->sm_ah->pkey_index, 707 0, IB_MGMT_SA_HDR, IB_MGMT_SA_DATA, 708 gfp_mask); 709 if (IS_ERR(query->mad_buf)) { 710 kref_put(&query->sm_ah->ref, free_sm_ah); 711 return -ENOMEM; 712 } 713 714 query->mad_buf->ah = query->sm_ah->ah; 715 716 return 0; 717} 718 719static void free_mad(struct ib_sa_query *query) 720{ 721 ib_free_send_mad(query->mad_buf); 722 kref_put(&query->sm_ah->ref, free_sm_ah); 723} 724 725static void init_mad(struct ib_sa_mad *mad, struct ib_mad_agent *agent) 726{ 727 unsigned long flags; 728 729 memset(mad, 0, sizeof *mad); 730 731 mad->mad_hdr.base_version = IB_MGMT_BASE_VERSION; 732 mad->mad_hdr.mgmt_class = IB_MGMT_CLASS_SUBN_ADM; 733 mad->mad_hdr.class_version = IB_SA_CLASS_VERSION; 734 735 spin_lock_irqsave(&tid_lock, flags); 736 mad->mad_hdr.tid = 737 cpu_to_be64(((u64) agent->hi_tid) << 32 | tid++); 738 spin_unlock_irqrestore(&tid_lock, flags); 739} 740 741static int send_mad(struct ib_sa_query *query, int timeout_ms, gfp_t gfp_mask) 742{ 743 unsigned long flags; 744 int ret, id; 745 746retry: 747 if (!idr_pre_get(&query_idr, gfp_mask)) 748 return -ENOMEM; 749 spin_lock_irqsave(&idr_lock, flags); 750 ret = idr_get_new(&query_idr, query, &id); 751 spin_unlock_irqrestore(&idr_lock, flags); 752 if (ret == -EAGAIN) 753 goto retry; 754 if (ret) 755 return ret; 756 757 query->mad_buf->timeout_ms = timeout_ms; 758 query->mad_buf->context[0] = query; 759 query->id = id; 760 761 ret = ib_post_send_mad(query->mad_buf, NULL); 762 if (ret) { 763 spin_lock_irqsave(&idr_lock, flags); 764 idr_remove(&query_idr, id); 765 spin_unlock_irqrestore(&idr_lock, flags); 766 } 767 768 /* 769 * It's not safe to dereference query any more, because the 770 * send may already have completed and freed the query in 771 * another context. 772 */ 773 return ret ? ret : id; 774} 775 776void ib_sa_unpack_path(void *attribute, struct ib_sa_path_rec *rec) 777{ 778 ib_unpack(path_rec_table, ARRAY_SIZE(path_rec_table), attribute, rec); 779} 780EXPORT_SYMBOL(ib_sa_unpack_path); 781 782static void ib_sa_path_rec_callback(struct ib_sa_query *sa_query, 783 int status, 784 struct ib_sa_mad *mad) 785{ 786 struct ib_sa_path_query *query = 787 container_of(sa_query, struct ib_sa_path_query, sa_query); 788 789 if (mad) { 790 struct ib_sa_path_rec rec; 791 792 ib_unpack(path_rec_table, ARRAY_SIZE(path_rec_table), 793 mad->data, &rec); 794 query->callback(status, &rec, query->context); 795 } else 796 query->callback(status, NULL, query->context); 797} 798 799static void ib_sa_path_rec_release(struct ib_sa_query *sa_query) 800{ 801 kfree(container_of(sa_query, struct ib_sa_path_query, sa_query)); 802} 803 804int ib_sa_path_rec_query(struct ib_sa_client *client, 805 struct ib_device *device, u8 port_num, 806 struct ib_sa_path_rec *rec, 807 ib_sa_comp_mask comp_mask, 808 int timeout_ms, gfp_t gfp_mask, 809 void (*callback)(int status, 810 struct ib_sa_path_rec *resp, 811 void *context), 812 void *context, 813 struct ib_sa_query **sa_query) 814{ 815 struct ib_sa_path_query *query; 816 struct ib_sa_device *sa_dev = ib_get_client_data(device, &sa_client); 817 struct ib_sa_port *port; 818 struct ib_mad_agent *agent; 819 struct ib_sa_mad *mad; 820 int ret; 821 822 if (!sa_dev) 823 return -ENODEV; 824 825 port = &sa_dev->port[port_num - sa_dev->start_port]; 826 agent = port->agent; 827 828 query = kmalloc(sizeof *query, gfp_mask); 829 if (!query) 830 return -ENOMEM; 831 832 query->sa_query.port = port; 833 ret = alloc_mad(&query->sa_query, gfp_mask); 834 if (ret) 835 goto err1; 836 837 ib_sa_client_get(client); 838 query->sa_query.client = client; 839 query->callback = callback; 840 query->context = context; 841 842 mad = query->sa_query.mad_buf->mad; 843 init_mad(mad, agent); 844 845 query->sa_query.callback = callback ? ib_sa_path_rec_callback : NULL; 846 query->sa_query.release = ib_sa_path_rec_release; 847 mad->mad_hdr.method = IB_MGMT_METHOD_GET; 848 mad->mad_hdr.attr_id = cpu_to_be16(IB_SA_ATTR_PATH_REC); 849 mad->sa_hdr.comp_mask = comp_mask; 850 851 ib_pack(path_rec_table, ARRAY_SIZE(path_rec_table), rec, mad->data); 852 853 *sa_query = &query->sa_query; 854 855 ret = send_mad(&query->sa_query, timeout_ms, gfp_mask); 856 if (ret < 0) 857 goto err2; 858 859 return ret; 860 861err2: 862 *sa_query = NULL; 863 ib_sa_client_put(query->sa_query.client); 864 free_mad(&query->sa_query); 865 866err1: 867 kfree(query); 868 return ret; 869} 870 871static void ib_sa_service_rec_callback(struct ib_sa_query *sa_query, 872 int status, 873 struct ib_sa_mad *mad) 874{ 875 struct ib_sa_service_query *query = 876 container_of(sa_query, struct ib_sa_service_query, sa_query); 877 878 if (mad) { 879 struct ib_sa_service_rec rec; 880 881 ib_unpack(service_rec_table, ARRAY_SIZE(service_rec_table), 882 mad->data, &rec); 883 query->callback(status, &rec, query->context); 884 } else 885 query->callback(status, NULL, query->context); 886} 887 888static void ib_sa_service_rec_release(struct ib_sa_query *sa_query) 889{ 890 kfree(container_of(sa_query, struct ib_sa_service_query, sa_query)); 891} 892 893/** 894 * ib_sa_service_rec_query - Start Service Record operation 895 * @client:SA client 896 * @device:device to send request on 897 * @port_num: port number to send request on 898 * @method:SA method - should be get, set, or delete 899 * @rec:Service Record to send in request 900 * @comp_mask:component mask to send in request 901 * @timeout_ms:time to wait for response 902 * @gfp_mask:GFP mask to use for internal allocations 903 * @callback:function called when request completes, times out or is 904 * canceled 905 * @context:opaque user context passed to callback 906 * @sa_query:request context, used to cancel request 907 * 908 * Send a Service Record set/get/delete to the SA to register, 909 * unregister or query a service record. 910 * The callback function will be called when the request completes (or 911 * fails); status is 0 for a successful response, -EINTR if the query 912 * is canceled, -ETIMEDOUT is the query timed out, or -EIO if an error 913 * occurred sending the query. The resp parameter of the callback is 914 * only valid if status is 0. 915 * 916 * If the return value of ib_sa_service_rec_query() is negative, it is an 917 * error code. Otherwise it is a request ID that can be used to cancel 918 * the query. 919 */ 920int ib_sa_service_rec_query(struct ib_sa_client *client, 921 struct ib_device *device, u8 port_num, u8 method, 922 struct ib_sa_service_rec *rec, 923 ib_sa_comp_mask comp_mask, 924 int timeout_ms, gfp_t gfp_mask, 925 void (*callback)(int status, 926 struct ib_sa_service_rec *resp, 927 void *context), 928 void *context, 929 struct ib_sa_query **sa_query) 930{ 931 struct ib_sa_service_query *query; 932 struct ib_sa_device *sa_dev = ib_get_client_data(device, &sa_client); 933 struct ib_sa_port *port; 934 struct ib_mad_agent *agent; 935 struct ib_sa_mad *mad; 936 int ret; 937 938 if (!sa_dev) 939 return -ENODEV; 940 941 port = &sa_dev->port[port_num - sa_dev->start_port]; 942 agent = port->agent; 943 944 if (method != IB_MGMT_METHOD_GET && 945 method != IB_MGMT_METHOD_SET && 946 method != IB_SA_METHOD_DELETE) 947 return -EINVAL; 948 949 query = kmalloc(sizeof *query, gfp_mask); 950 if (!query) 951 return -ENOMEM; 952 953 query->sa_query.port = port; 954 ret = alloc_mad(&query->sa_query, gfp_mask); 955 if (ret) 956 goto err1; 957 958 ib_sa_client_get(client); 959 query->sa_query.client = client; 960 query->callback = callback; 961 query->context = context; 962 963 mad = query->sa_query.mad_buf->mad; 964 init_mad(mad, agent); 965 966 query->sa_query.callback = callback ? ib_sa_service_rec_callback : NULL; 967 query->sa_query.release = ib_sa_service_rec_release; 968 mad->mad_hdr.method = method; 969 mad->mad_hdr.attr_id = cpu_to_be16(IB_SA_ATTR_SERVICE_REC); 970 mad->sa_hdr.comp_mask = comp_mask; 971 972 ib_pack(service_rec_table, ARRAY_SIZE(service_rec_table), 973 rec, mad->data); 974 975 *sa_query = &query->sa_query; 976 977 ret = send_mad(&query->sa_query, timeout_ms, gfp_mask); 978 if (ret < 0) 979 goto err2; 980 981 return ret; 982 983err2: 984 *sa_query = NULL; 985 ib_sa_client_put(query->sa_query.client); 986 free_mad(&query->sa_query); 987 988err1: 989 kfree(query); 990 return ret; 991} 992EXPORT_SYMBOL(ib_sa_service_rec_query); 993 994static void ib_sa_mcmember_rec_callback(struct ib_sa_query *sa_query, 995 int status, 996 struct ib_sa_mad *mad) 997{ 998 struct ib_sa_mcmember_query *query = 999 container_of(sa_query, struct ib_sa_mcmember_query, sa_query); 1000 1001 if (mad) { 1002 struct ib_sa_mcmember_rec rec; 1003 1004 ib_unpack(mcmember_rec_table, ARRAY_SIZE(mcmember_rec_table), 1005 mad->data, &rec); 1006 query->callback(status, &rec, query->context); 1007 } else 1008 query->callback(status, NULL, query->context); 1009} 1010 1011static void ib_sa_mcmember_rec_release(struct ib_sa_query *sa_query) 1012{ 1013 kfree(container_of(sa_query, struct ib_sa_mcmember_query, sa_query)); 1014} 1015 1016int ib_sa_mcmember_rec_query(struct ib_sa_client *client, 1017 struct ib_device *device, u8 port_num, 1018 u8 method, 1019 struct ib_sa_mcmember_rec *rec, 1020 ib_sa_comp_mask comp_mask, 1021 int timeout_ms, gfp_t gfp_mask, 1022 void (*callback)(int status, 1023 struct ib_sa_mcmember_rec *resp, 1024 void *context), 1025 void *context, 1026 struct ib_sa_query **sa_query) 1027{ 1028 struct ib_sa_mcmember_query *query; 1029 struct ib_sa_device *sa_dev = ib_get_client_data(device, &sa_client); 1030 struct ib_sa_port *port; 1031 struct ib_mad_agent *agent; 1032 struct ib_sa_mad *mad; 1033 int ret; 1034 1035 if (!sa_dev) 1036 return -ENODEV; 1037 1038 port = &sa_dev->port[port_num - sa_dev->start_port]; 1039 agent = port->agent; 1040 1041 query = kmalloc(sizeof *query, gfp_mask); 1042 if (!query) 1043 return -ENOMEM; 1044 1045 query->sa_query.port = port; 1046 ret = alloc_mad(&query->sa_query, gfp_mask); 1047 if (ret) 1048 goto err1; 1049 1050 ib_sa_client_get(client); 1051 query->sa_query.client = client; 1052 query->callback = callback; 1053 query->context = context; 1054 1055 mad = query->sa_query.mad_buf->mad; 1056 init_mad(mad, agent); 1057 1058 query->sa_query.callback = callback ? ib_sa_mcmember_rec_callback : NULL; 1059 query->sa_query.release = ib_sa_mcmember_rec_release; 1060 mad->mad_hdr.method = method; 1061 mad->mad_hdr.attr_id = cpu_to_be16(IB_SA_ATTR_MC_MEMBER_REC); 1062 mad->sa_hdr.comp_mask = comp_mask; 1063 1064 ib_pack(mcmember_rec_table, ARRAY_SIZE(mcmember_rec_table), 1065 rec, mad->data); 1066 1067 *sa_query = &query->sa_query; 1068 1069 ret = send_mad(&query->sa_query, timeout_ms, gfp_mask); 1070 if (ret < 0) 1071 goto err2; 1072 1073 return ret; 1074 1075err2: 1076 *sa_query = NULL; 1077 ib_sa_client_put(query->sa_query.client); 1078 free_mad(&query->sa_query); 1079 1080err1: 1081 kfree(query); 1082 return ret; 1083} 1084 1085static void ib_sa_inform_callback(struct ib_sa_query *sa_query, 1086 int status, 1087 struct ib_sa_mad *mad) 1088{ 1089 struct ib_sa_inform_query *query = 1090 container_of(sa_query, struct ib_sa_inform_query, sa_query); 1091 1092 if (mad) { 1093 struct ib_sa_inform rec; 1094 1095 ib_unpack(inform_table, ARRAY_SIZE(inform_table), 1096 mad->data, &rec); 1097 query->callback(status, &rec, query->context); 1098 } else 1099 query->callback(status, NULL, query->context); 1100} 1101 1102static void ib_sa_inform_release(struct ib_sa_query *sa_query) 1103{ 1104 kfree(container_of(sa_query, struct ib_sa_inform_query, sa_query)); 1105} 1106 1107int ib_sa_guid_info_rec_query(struct ib_sa_client *client, 1108 struct ib_device *device, u8 port_num, 1109 struct ib_sa_guidinfo_rec *rec, 1110 ib_sa_comp_mask comp_mask, u8 method, 1111 int timeout_ms, gfp_t gfp_mask, 1112 void (*callback)(int status, 1113 struct ib_sa_guidinfo_rec *resp, 1114 void *context), 1115 void *context, 1116 struct ib_sa_query **sa_query) 1117{ 1118 // stub function - 1119 // called originally from mad.c under mlx4_ib_init_sriov() 1120 // which calls mlx4_ib_init_alias_guid_service() in alias_GUID.c 1121 // which goes down to this function 1122 1123 printk("ERROR: function should be called only in SRIOV flow!!!"); 1124 1125 return 0; 1126} 1127 1128/** 1129 * ib_sa_informinfo_query - Start an InformInfo registration. 1130 * @client:SA client 1131 * @device:device to send query on 1132 * @port_num: port number to send query on 1133 * @rec:Inform record to send in query 1134 * @timeout_ms:time to wait for response 1135 * @gfp_mask:GFP mask to use for internal allocations 1136 * @callback:function called when notice handler registration completes, 1137 * times out or is canceled 1138 * @context:opaque user context passed to callback 1139 * @sa_query:query context, used to cancel query 1140 * 1141 * This function sends inform info to register with SA to receive 1142 * in-service notice. 1143 * The callback function will be called when the query completes (or 1144 * fails); status is 0 for a successful response, -EINTR if the query 1145 * is canceled, -ETIMEDOUT is the query timed out, or -EIO if an error 1146 * occurred sending the query. The resp parameter of the callback is 1147 * only valid if status is 0. 1148 * 1149 * If the return value of ib_sa_inform_query() is negative, it is an 1150 * error code. Otherwise it is a query ID that can be used to cancel 1151 * the query. 1152 */ 1153int ib_sa_informinfo_query(struct ib_sa_client *client, 1154 struct ib_device *device, u8 port_num, 1155 struct ib_sa_inform *rec, 1156 int timeout_ms, gfp_t gfp_mask, 1157 void (*callback)(int status, 1158 struct ib_sa_inform *resp, 1159 void *context), 1160 void *context, 1161 struct ib_sa_query **sa_query) 1162{ 1163 struct ib_sa_inform_query *query; 1164 struct ib_sa_device *sa_dev = ib_get_client_data(device, &sa_client); 1165 struct ib_sa_port *port; 1166 struct ib_mad_agent *agent; 1167 struct ib_sa_mad *mad; 1168 int ret; 1169 1170 if (!sa_dev) 1171 return -ENODEV; 1172 1173 port = &sa_dev->port[port_num - sa_dev->start_port]; 1174 agent = port->agent; 1175 1176 query = kmalloc(sizeof *query, gfp_mask); 1177 if (!query) 1178 return -ENOMEM; 1179 1180 query->sa_query.port = port; 1181 ret = alloc_mad(&query->sa_query, gfp_mask); 1182 if (ret) 1183 goto err1; 1184 1185 ib_sa_client_get(client); 1186 query->sa_query.client = client; 1187 query->callback = callback; 1188 query->context = context; 1189 1190 mad = query->sa_query.mad_buf->mad; 1191 init_mad(mad, agent); 1192 1193 query->sa_query.callback = callback ? ib_sa_inform_callback : NULL; 1194 query->sa_query.release = ib_sa_inform_release; 1195 query->sa_query.port = port; 1196 mad->mad_hdr.method = IB_MGMT_METHOD_SET; 1197 mad->mad_hdr.attr_id = cpu_to_be16(IB_SA_ATTR_INFORM_INFO); 1198 1199 ib_pack(inform_table, ARRAY_SIZE(inform_table), rec, mad->data); 1200 1201 *sa_query = &query->sa_query; 1202 ret = send_mad(&query->sa_query, timeout_ms, gfp_mask); 1203 if (ret < 0) 1204 goto err2; 1205 1206 return ret; 1207 1208err2: 1209 *sa_query = NULL; 1210 ib_sa_client_put(query->sa_query.client); 1211 free_mad(&query->sa_query); 1212err1: 1213 kfree(query); 1214 return ret; 1215} 1216 1217static void ib_sa_notice_resp(struct ib_sa_port *port, 1218 struct ib_mad_recv_wc *mad_recv_wc) 1219{ 1220 struct ib_mad_send_buf *mad_buf; 1221 struct ib_sa_mad *mad; 1222 int ret; 1223 unsigned long flags; 1224 1225 mad_buf = ib_create_send_mad(port->notice_agent, 1, 0, 0, 1226 IB_MGMT_SA_HDR, IB_MGMT_SA_DATA, 1227 GFP_KERNEL); 1228 if (IS_ERR(mad_buf)) 1229 return; 1230 1231 mad = mad_buf->mad; 1232 memcpy(mad, mad_recv_wc->recv_buf.mad, sizeof *mad); 1233 mad->mad_hdr.method = IB_MGMT_METHOD_REPORT_RESP; 1234 1235 spin_lock_irqsave(&port->ah_lock, flags); 1236 if (!port->sm_ah) { 1237 spin_unlock_irqrestore(&port->ah_lock, flags); 1238 ib_free_send_mad(mad_buf); 1239 return; 1240 } 1241 kref_get(&port->sm_ah->ref); 1242 mad_buf->context[0] = &port->sm_ah->ref; 1243 mad_buf->ah = port->sm_ah->ah; 1244 spin_unlock_irqrestore(&port->ah_lock, flags); 1245 1246 ret = ib_post_send_mad(mad_buf, NULL); 1247 if (ret) 1248 goto err; 1249 1250 return; 1251err: 1252 kref_put(mad_buf->context[0], free_sm_ah); 1253 ib_free_send_mad(mad_buf); 1254} 1255 1256static void send_handler(struct ib_mad_agent *agent, 1257 struct ib_mad_send_wc *mad_send_wc) 1258{ 1259 struct ib_sa_query *query = mad_send_wc->send_buf->context[0]; 1260 unsigned long flags; 1261 1262 if (query->callback) 1263 switch (mad_send_wc->status) { 1264 case IB_WC_SUCCESS: 1265 /* No callback -- already got recv */ 1266 break; 1267 case IB_WC_RESP_TIMEOUT_ERR: 1268 query->callback(query, -ETIMEDOUT, NULL); 1269 break; 1270 case IB_WC_WR_FLUSH_ERR: 1271 query->callback(query, -EINTR, NULL); 1272 break; 1273 default: 1274 query->callback(query, -EIO, NULL); 1275 break; 1276 } 1277 1278 spin_lock_irqsave(&idr_lock, flags); 1279 idr_remove(&query_idr, query->id); 1280 spin_unlock_irqrestore(&idr_lock, flags); 1281 1282 free_mad(query); 1283 ib_sa_client_put(query->client); 1284 query->release(query); 1285} 1286 1287static void recv_handler(struct ib_mad_agent *mad_agent, 1288 struct ib_mad_recv_wc *mad_recv_wc) 1289{ 1290 struct ib_sa_query *query; 1291 struct ib_mad_send_buf *mad_buf; 1292 1293 mad_buf = (void *) (unsigned long) mad_recv_wc->wc->wr_id; 1294 query = mad_buf->context[0]; 1295 1296 if (query->callback) { 1297 if (mad_recv_wc->wc->status == IB_WC_SUCCESS) 1298 query->callback(query, 1299 mad_recv_wc->recv_buf.mad->mad_hdr.status ? 1300 -EINVAL : 0, 1301 (struct ib_sa_mad *) mad_recv_wc->recv_buf.mad); 1302 else 1303 query->callback(query, -EIO, NULL); 1304 } 1305 1306 ib_free_recv_mad(mad_recv_wc); 1307} 1308 1309static void notice_resp_handler(struct ib_mad_agent *agent, 1310 struct ib_mad_send_wc *mad_send_wc) 1311{ 1312 kref_put(mad_send_wc->send_buf->context[0], free_sm_ah); 1313 ib_free_send_mad(mad_send_wc->send_buf); 1314} 1315 1316static void notice_handler(struct ib_mad_agent *mad_agent, 1317 struct ib_mad_recv_wc *mad_recv_wc) 1318{ 1319 struct ib_sa_port *port; 1320 struct ib_sa_mad *mad; 1321 struct ib_sa_notice notice; 1322 1323 port = mad_agent->context; 1324 mad = (struct ib_sa_mad *) mad_recv_wc->recv_buf.mad; 1325 ib_unpack(notice_table, ARRAY_SIZE(notice_table), mad->data, ¬ice); 1326 1327 if (!notice_dispatch(port->device, port->port_num, ¬ice)) 1328 ib_sa_notice_resp(port, mad_recv_wc); 1329 ib_free_recv_mad(mad_recv_wc); 1330} 1331 1332static void ib_sa_add_one(struct ib_device *device) 1333{ 1334 struct ib_sa_device *sa_dev; 1335 struct ib_mad_reg_req reg_req = { 1336 .mgmt_class = IB_MGMT_CLASS_SUBN_ADM, 1337 .mgmt_class_version = 2 1338 }; 1339 int s, e, i; 1340 1341 if (rdma_node_get_transport(device->node_type) != RDMA_TRANSPORT_IB) 1342 return; 1343 1344 if (device->node_type == RDMA_NODE_IB_SWITCH) 1345 s = e = 0; 1346 else { 1347 s = 1; 1348 e = device->phys_port_cnt; 1349 } 1350 1351 sa_dev = kzalloc(sizeof *sa_dev + 1352 (e - s + 1) * sizeof (struct ib_sa_port), 1353 GFP_KERNEL); 1354 if (!sa_dev) 1355 return; 1356 1357 sa_dev->start_port = s; 1358 sa_dev->end_port = e; 1359 1360 for (i = 0; i <= e - s; ++i) { 1361 spin_lock_init(&sa_dev->port[i].ah_lock); 1362 if (rdma_port_get_link_layer(device, i + 1) != IB_LINK_LAYER_INFINIBAND) 1363 continue; 1364 1365 sa_dev->port[i].sm_ah = NULL; 1366 sa_dev->port[i].port_num = i + s; 1367 1368 sa_dev->port[i].agent = 1369 ib_register_mad_agent(device, i + s, IB_QPT_GSI, 1370 NULL, 0, send_handler, 1371 recv_handler, sa_dev); 1372 if (IS_ERR(sa_dev->port[i].agent)) 1373 goto err; 1374 1375 sa_dev->port[i].device = device; 1376 set_bit(IB_MGMT_METHOD_REPORT, reg_req.method_mask); 1377 sa_dev->port[i].notice_agent = 1378 ib_register_mad_agent(device, i + s, IB_QPT_GSI, 1379 ®_req, 0, notice_resp_handler, 1380 notice_handler, &sa_dev->port[i]); 1381 1382 if (IS_ERR(sa_dev->port[i].notice_agent)) 1383 goto err; 1384 1385 INIT_WORK(&sa_dev->port[i].update_task, update_sm_ah); 1386 } 1387 1388 ib_set_client_data(device, &sa_client, sa_dev); 1389 1390 /* 1391 * We register our event handler after everything is set up, 1392 * and then update our cached info after the event handler is 1393 * registered to avoid any problems if a port changes state 1394 * during our initialization. 1395 */ 1396 1397 INIT_IB_EVENT_HANDLER(&sa_dev->event_handler, device, ib_sa_event); 1398 if (ib_register_event_handler(&sa_dev->event_handler)) 1399 goto err; 1400 1401 for (i = 0; i <= e - s; ++i) 1402 if (rdma_port_get_link_layer(device, i + 1) == IB_LINK_LAYER_INFINIBAND) 1403 update_sm_ah(&sa_dev->port[i].update_task); 1404 1405 return; 1406 1407err: 1408 while (--i >= 0) 1409 if (rdma_port_get_link_layer(device, i + 1) == IB_LINK_LAYER_INFINIBAND) { 1410 if (!IS_ERR(sa_dev->port[i].notice_agent)) 1411 ib_unregister_mad_agent(sa_dev->port[i].notice_agent); 1412 if (!IS_ERR(sa_dev->port[i].agent)) 1413 ib_unregister_mad_agent(sa_dev->port[i].agent); 1414 } 1415 1416 kfree(sa_dev); 1417 1418 return; 1419} 1420 1421static void ib_sa_remove_one(struct ib_device *device) 1422{ 1423 struct ib_sa_device *sa_dev = ib_get_client_data(device, &sa_client); 1424 int i; 1425 1426 if (!sa_dev) 1427 return; 1428 1429 ib_unregister_event_handler(&sa_dev->event_handler); 1430 1431 flush_scheduled_work(); 1432 1433 for (i = 0; i <= sa_dev->end_port - sa_dev->start_port; ++i) { 1434 if (rdma_port_get_link_layer(device, i + 1) == IB_LINK_LAYER_INFINIBAND) { 1435 ib_unregister_mad_agent(sa_dev->port[i].notice_agent); 1436 ib_unregister_mad_agent(sa_dev->port[i].agent); 1437 if (sa_dev->port[i].sm_ah) 1438 kref_put(&sa_dev->port[i].sm_ah->ref, free_sm_ah); 1439 } 1440 1441 } 1442 1443 kfree(sa_dev); 1444} 1445 1446static int __init ib_sa_init(void) 1447{ 1448 int ret; 1449 1450 spin_lock_init(&idr_lock); 1451 spin_lock_init(&tid_lock); 1452 1453 get_random_bytes(&tid, sizeof tid); 1454 1455 ret = ib_register_client(&sa_client); 1456 if (ret) { 1457 printk(KERN_ERR "Couldn't register ib_sa client\n"); 1458 goto err1; 1459 } 1460 1461 ret = mcast_init(); 1462 if (ret) { 1463 printk(KERN_ERR "Couldn't initialize multicast handling\n"); 1464 goto err2; 1465 } 1466 1467 ret = notice_init(); 1468 if (ret) { 1469 printk(KERN_ERR "Couldn't initialize notice handling\n"); 1470 goto err3; 1471 } 1472 1473 ret = sa_db_init(); 1474 if (ret) { 1475 printk(KERN_ERR "Couldn't initialize local SA\n"); 1476 goto err4; 1477 } 1478 1479 return 0; 1480err4: 1481 notice_cleanup(); 1482err3: 1483 mcast_cleanup(); 1484err2: 1485 ib_unregister_client(&sa_client); 1486err1: 1487 return ret; 1488} 1489 1490static void __exit ib_sa_cleanup(void) 1491{ 1492 sa_db_cleanup(); 1493 mcast_cleanup(); 1494 notice_cleanup(); 1495 ib_unregister_client(&sa_client); 1496 idr_destroy(&query_idr); 1497} 1498 1499module_init_order(ib_sa_init, SI_ORDER_SECOND); 1500module_exit(ib_sa_cleanup); 1501