.. | .. |
---|
13 | 13 | #include <linux/device.h> |
---|
14 | 14 | #include <linux/pci.h> |
---|
15 | 15 | #include <linux/err.h> |
---|
| 16 | +#include <linux/ctype.h> |
---|
| 17 | +#include <linux/processor.h> |
---|
16 | 18 | #include <net/smc.h> |
---|
17 | 19 | |
---|
18 | 20 | #include <asm/debug.h> |
---|
.. | .. |
---|
38 | 40 | struct ism_req_hdr *req = cmd; |
---|
39 | 41 | struct ism_resp_hdr *resp = cmd; |
---|
40 | 42 | |
---|
41 | | - memcpy_toio(ism->ctl + sizeof(*req), req + 1, req->len - sizeof(*req)); |
---|
42 | | - memcpy_toio(ism->ctl, req, sizeof(*req)); |
---|
| 43 | + __ism_write_cmd(ism, req + 1, sizeof(*req), req->len - sizeof(*req)); |
---|
| 44 | + __ism_write_cmd(ism, req, 0, sizeof(*req)); |
---|
43 | 45 | |
---|
44 | 46 | WRITE_ONCE(resp->ret, ISM_ERROR); |
---|
45 | 47 | |
---|
46 | | - memcpy_fromio(resp, ism->ctl, sizeof(*resp)); |
---|
| 48 | + __ism_read_cmd(ism, resp, 0, sizeof(*resp)); |
---|
47 | 49 | if (resp->ret) { |
---|
48 | 50 | debug_text_event(ism_debug_info, 0, "cmd failure"); |
---|
49 | 51 | debug_event(ism_debug_info, 0, resp, sizeof(*resp)); |
---|
50 | 52 | goto out; |
---|
51 | 53 | } |
---|
52 | | - memcpy_fromio(resp + 1, ism->ctl + sizeof(*resp), |
---|
53 | | - resp->len - sizeof(*resp)); |
---|
| 54 | + __ism_read_cmd(ism, resp + 1, sizeof(*resp), resp->len - sizeof(*resp)); |
---|
54 | 55 | out: |
---|
55 | 56 | return resp->ret; |
---|
56 | 57 | } |
---|
.. | .. |
---|
89 | 90 | dma_addr_t dma_handle; |
---|
90 | 91 | struct ism_sba *sba; |
---|
91 | 92 | |
---|
92 | | - sba = dma_zalloc_coherent(&ism->pdev->dev, PAGE_SIZE, |
---|
93 | | - &dma_handle, GFP_KERNEL); |
---|
| 93 | + sba = dma_alloc_coherent(&ism->pdev->dev, PAGE_SIZE, &dma_handle, |
---|
| 94 | + GFP_KERNEL); |
---|
94 | 95 | if (!sba) |
---|
95 | 96 | return -ENOMEM; |
---|
96 | 97 | |
---|
.. | .. |
---|
116 | 117 | dma_addr_t dma_handle; |
---|
117 | 118 | struct ism_eq *ieq; |
---|
118 | 119 | |
---|
119 | | - ieq = dma_zalloc_coherent(&ism->pdev->dev, PAGE_SIZE, |
---|
120 | | - &dma_handle, GFP_KERNEL); |
---|
| 120 | + ieq = dma_alloc_coherent(&ism->pdev->dev, PAGE_SIZE, &dma_handle, |
---|
| 121 | + GFP_KERNEL); |
---|
121 | 122 | if (!ieq) |
---|
122 | 123 | return -ENOMEM; |
---|
123 | 124 | |
---|
.. | .. |
---|
232 | 233 | bit = find_next_zero_bit(ism->sba_bitmap, ISM_NR_DMBS, |
---|
233 | 234 | ISM_DMB_BIT_OFFSET); |
---|
234 | 235 | if (bit == ISM_NR_DMBS) |
---|
235 | | - return -ENOMEM; |
---|
| 236 | + return -ENOSPC; |
---|
236 | 237 | |
---|
237 | 238 | dmb->sba_idx = bit; |
---|
238 | 239 | } |
---|
.. | .. |
---|
240 | 241 | test_and_set_bit(dmb->sba_idx, ism->sba_bitmap)) |
---|
241 | 242 | return -EINVAL; |
---|
242 | 243 | |
---|
243 | | - dmb->cpu_addr = dma_zalloc_coherent(&ism->pdev->dev, dmb->dmb_len, |
---|
244 | | - &dmb->dma_addr, GFP_KERNEL | |
---|
245 | | - __GFP_NOWARN | __GFP_NOMEMALLOC | |
---|
246 | | - __GFP_COMP | __GFP_NORETRY); |
---|
| 244 | + dmb->cpu_addr = dma_alloc_coherent(&ism->pdev->dev, dmb->dmb_len, |
---|
| 245 | + &dmb->dma_addr, |
---|
| 246 | + GFP_KERNEL | __GFP_NOWARN | __GFP_NOMEMALLOC | __GFP_COMP | __GFP_NORETRY); |
---|
247 | 247 | if (!dmb->cpu_addr) |
---|
248 | 248 | clear_bit(dmb->sba_idx, ism->sba_bitmap); |
---|
249 | 249 | |
---|
.. | .. |
---|
389 | 389 | return 0; |
---|
390 | 390 | } |
---|
391 | 391 | |
---|
| 392 | +static struct ism_systemeid SYSTEM_EID = { |
---|
| 393 | + .seid_string = "IBM-SYSZ-ISMSEID00000000", |
---|
| 394 | + .serial_number = "0000", |
---|
| 395 | + .type = "0000", |
---|
| 396 | +}; |
---|
| 397 | + |
---|
| 398 | +static void ism_create_system_eid(void) |
---|
| 399 | +{ |
---|
| 400 | + struct cpuid id; |
---|
| 401 | + u16 ident_tail; |
---|
| 402 | + char tmp[5]; |
---|
| 403 | + |
---|
| 404 | + get_cpu_id(&id); |
---|
| 405 | + ident_tail = (u16)(id.ident & ISM_IDENT_MASK); |
---|
| 406 | + snprintf(tmp, 5, "%04X", ident_tail); |
---|
| 407 | + memcpy(&SYSTEM_EID.serial_number, tmp, 4); |
---|
| 408 | + snprintf(tmp, 5, "%04X", id.machine); |
---|
| 409 | + memcpy(&SYSTEM_EID.type, tmp, 4); |
---|
| 410 | +} |
---|
| 411 | + |
---|
| 412 | +static void ism_get_system_eid(struct smcd_dev *smcd, u8 **eid) |
---|
| 413 | +{ |
---|
| 414 | + *eid = &SYSTEM_EID.seid_string[0]; |
---|
| 415 | +} |
---|
| 416 | + |
---|
| 417 | +static u16 ism_get_chid(struct smcd_dev *smcd) |
---|
| 418 | +{ |
---|
| 419 | + struct ism_dev *ismdev; |
---|
| 420 | + |
---|
| 421 | + ismdev = (struct ism_dev *)smcd->priv; |
---|
| 422 | + if (!ismdev || !ismdev->pdev) |
---|
| 423 | + return 0; |
---|
| 424 | + |
---|
| 425 | + return to_zpci(ismdev->pdev)->pchid; |
---|
| 426 | +} |
---|
| 427 | + |
---|
392 | 428 | static void ism_handle_event(struct ism_dev *ism) |
---|
393 | 429 | { |
---|
394 | 430 | struct smcd_event *entry; |
---|
.. | .. |
---|
445 | 481 | .reset_vlan_required = ism_reset_vlan_required, |
---|
446 | 482 | .signal_event = ism_signal_ieq, |
---|
447 | 483 | .move_data = ism_move, |
---|
| 484 | + .get_system_eid = ism_get_system_eid, |
---|
| 485 | + .get_chid = ism_get_chid, |
---|
448 | 486 | }; |
---|
449 | 487 | |
---|
450 | 488 | static int ism_dev_init(struct ism_dev *ism) |
---|
.. | .. |
---|
472 | 510 | ret = ism_read_local_gid(ism); |
---|
473 | 511 | if (ret) |
---|
474 | 512 | goto unreg_ieq; |
---|
| 513 | + |
---|
| 514 | + if (!ism_add_vlan_id(ism->smcd, ISM_RESERVED_VLANID)) |
---|
| 515 | + /* hardware is V2 capable */ |
---|
| 516 | + ism_create_system_eid(); |
---|
475 | 517 | |
---|
476 | 518 | ret = smcd_register_dev(ism->smcd); |
---|
477 | 519 | if (ret) |
---|
.. | .. |
---|
513 | 555 | if (ret) |
---|
514 | 556 | goto err_disable; |
---|
515 | 557 | |
---|
516 | | - ism->ctl = pci_iomap(pdev, 2, 0); |
---|
517 | | - if (!ism->ctl) |
---|
518 | | - goto err_resource; |
---|
519 | | - |
---|
520 | 558 | ret = pci_set_dma_mask(pdev, DMA_BIT_MASK(64)); |
---|
521 | 559 | if (ret) |
---|
522 | | - goto err_unmap; |
---|
| 560 | + goto err_resource; |
---|
523 | 561 | |
---|
524 | | - pci_set_dma_seg_boundary(pdev, SZ_1M - 1); |
---|
525 | | - pci_set_dma_max_seg_size(pdev, SZ_1M); |
---|
| 562 | + dma_set_seg_boundary(&pdev->dev, SZ_1M - 1); |
---|
| 563 | + dma_set_max_seg_size(&pdev->dev, SZ_1M); |
---|
526 | 564 | pci_set_master(pdev); |
---|
527 | 565 | |
---|
528 | 566 | ism->smcd = smcd_alloc_dev(&pdev->dev, dev_name(&pdev->dev), &ism_ops, |
---|
529 | 567 | ISM_NR_DMBS); |
---|
530 | | - if (!ism->smcd) |
---|
531 | | - goto err_unmap; |
---|
| 568 | + if (!ism->smcd) { |
---|
| 569 | + ret = -ENOMEM; |
---|
| 570 | + goto err_resource; |
---|
| 571 | + } |
---|
532 | 572 | |
---|
533 | 573 | ism->smcd->priv = ism; |
---|
534 | 574 | ret = ism_dev_init(ism); |
---|
.. | .. |
---|
539 | 579 | |
---|
540 | 580 | err_free: |
---|
541 | 581 | smcd_free_dev(ism->smcd); |
---|
542 | | -err_unmap: |
---|
543 | | - pci_iounmap(pdev, ism->ctl); |
---|
544 | 582 | err_resource: |
---|
545 | 583 | pci_release_mem_regions(pdev); |
---|
546 | 584 | err_disable: |
---|
.. | .. |
---|
556 | 594 | struct pci_dev *pdev = ism->pdev; |
---|
557 | 595 | |
---|
558 | 596 | smcd_unregister_dev(ism->smcd); |
---|
| 597 | + if (SYSTEM_EID.serial_number[0] != '0' || |
---|
| 598 | + SYSTEM_EID.type[0] != '0') |
---|
| 599 | + ism_del_vlan_id(ism->smcd, ISM_RESERVED_VLANID); |
---|
559 | 600 | unregister_ieq(ism); |
---|
560 | 601 | unregister_sba(ism); |
---|
561 | 602 | free_irq(pci_irq_vector(pdev, 0), ism); |
---|
.. | .. |
---|
569 | 610 | ism_dev_exit(ism); |
---|
570 | 611 | |
---|
571 | 612 | smcd_free_dev(ism->smcd); |
---|
572 | | - pci_iounmap(pdev, ism->ctl); |
---|
573 | 613 | pci_release_mem_regions(pdev); |
---|
574 | 614 | pci_disable_device(pdev); |
---|
575 | 615 | dev_set_drvdata(&pdev->dev, NULL); |
---|
576 | 616 | kfree(ism); |
---|
577 | 617 | } |
---|
578 | 618 | |
---|
579 | | -static int ism_suspend(struct device *dev) |
---|
580 | | -{ |
---|
581 | | - struct ism_dev *ism = dev_get_drvdata(dev); |
---|
582 | | - |
---|
583 | | - ism_dev_exit(ism); |
---|
584 | | - return 0; |
---|
585 | | -} |
---|
586 | | - |
---|
587 | | -static int ism_resume(struct device *dev) |
---|
588 | | -{ |
---|
589 | | - struct ism_dev *ism = dev_get_drvdata(dev); |
---|
590 | | - |
---|
591 | | - return ism_dev_init(ism); |
---|
592 | | -} |
---|
593 | | - |
---|
594 | | -static SIMPLE_DEV_PM_OPS(ism_pm_ops, ism_suspend, ism_resume); |
---|
595 | | - |
---|
596 | 619 | static struct pci_driver ism_driver = { |
---|
597 | 620 | .name = DRV_NAME, |
---|
598 | 621 | .id_table = ism_device_table, |
---|
599 | 622 | .probe = ism_probe, |
---|
600 | 623 | .remove = ism_remove, |
---|
601 | | - .driver = { |
---|
602 | | - .pm = &ism_pm_ops, |
---|
603 | | - }, |
---|
604 | 624 | }; |
---|
605 | 625 | |
---|
606 | 626 | static int __init ism_init(void) |
---|