diff options
author | Serge Semin <fancer.lancer@gmail.com> | 2017-01-10 19:11:33 -0500 |
---|---|---|
committer | Jon Mason <jdmason@kudzu.us> | 2017-07-06 11:30:07 -0400 |
commit | 443b9a14ecbe811071467d54d6f2f1182835cc4d (patch) | |
tree | 240003b0193c3ba06090b13479acc949ceb36640 /include/linux/ntb.h | |
parent | 4e8c11b7fd29f70eb7af43bae908297689f2c3da (diff) |
NTB: Alter MW API to support multi-ports devices
Multi-port NTB devices permit to share a memory between all accessible peers.
Memory Windows API is altered to correspondingly initialize and map memory
windows for such devices:
ntb_mw_count(pidx); - number of inbound memory windows, which can be allocated
for shared buffer with specified peer device.
ntb_mw_get_align(pidx, widx); - get alignment and size restriction parameters
to properly allocate inbound memory region.
ntb_peer_mw_count(); - get number of outbound memory windows.
ntb_peer_mw_get_addr(widx); - get mapping address of an outbound memory window
If hardware supports inbound translation configured on the local ntb port:
ntb_mw_set_trans(pidx, widx); - set translation address of allocated inbound
memory window so a peer device could access it.
ntb_mw_clear_trans(pidx, widx); - clear the translation address of an inbound
memory window.
If hardware supports outbound translation configured on the peer ntb port:
ntb_peer_mw_set_trans(pidx, widx); - set translation address of a memory
window retrieved from a peer device
ntb_peer_mw_clear_trans(pidx, widx); - clear the translation address of an
outbound memory window
Signed-off-by: Serge Semin <fancer.lancer@gmail.com>
Acked-by: Allen Hubbe <Allen.Hubbe@dell.com>
Signed-off-by: Jon Mason <jdmason@kudzu.us>
Diffstat (limited to 'include/linux/ntb.h')
-rw-r--r-- | include/linux/ntb.h | 208 |
1 files changed, 163 insertions, 45 deletions
diff --git a/include/linux/ntb.h b/include/linux/ntb.h index b2b2924f5f43..2ea83f91a236 100644 --- a/include/linux/ntb.h +++ b/include/linux/ntb.h | |||
@@ -5,6 +5,7 @@ | |||
5 | * GPL LICENSE SUMMARY | 5 | * GPL LICENSE SUMMARY |
6 | * | 6 | * |
7 | * Copyright (C) 2015 EMC Corporation. All Rights Reserved. | 7 | * Copyright (C) 2015 EMC Corporation. All Rights Reserved. |
8 | * Copyright (C) 2016 T-Platforms. All Rights Reserved. | ||
8 | * | 9 | * |
9 | * This program is free software; you can redistribute it and/or modify | 10 | * This program is free software; you can redistribute it and/or modify |
10 | * it under the terms of version 2 of the GNU General Public License as | 11 | * it under the terms of version 2 of the GNU General Public License as |
@@ -18,6 +19,7 @@ | |||
18 | * BSD LICENSE | 19 | * BSD LICENSE |
19 | * | 20 | * |
20 | * Copyright (C) 2015 EMC Corporation. All Rights Reserved. | 21 | * Copyright (C) 2015 EMC Corporation. All Rights Reserved. |
22 | * Copyright (C) 2016 T-Platforms. All Rights Reserved. | ||
21 | * | 23 | * |
22 | * Redistribution and use in source and binary forms, with or without | 24 | * Redistribution and use in source and binary forms, with or without |
23 | * modification, are permitted provided that the following conditions | 25 | * modification, are permitted provided that the following conditions |
@@ -201,9 +203,13 @@ static inline int ntb_ctx_ops_is_valid(const struct ntb_ctx_ops *ops) | |||
201 | * @link_enable: See ntb_link_enable(). | 203 | * @link_enable: See ntb_link_enable(). |
202 | * @link_disable: See ntb_link_disable(). | 204 | * @link_disable: See ntb_link_disable(). |
203 | * @mw_count: See ntb_mw_count(). | 205 | * @mw_count: See ntb_mw_count(). |
204 | * @mw_get_range: See ntb_mw_get_range(). | 206 | * @mw_get_align: See ntb_mw_get_align(). |
205 | * @mw_set_trans: See ntb_mw_set_trans(). | 207 | * @mw_set_trans: See ntb_mw_set_trans(). |
206 | * @mw_clear_trans: See ntb_mw_clear_trans(). | 208 | * @mw_clear_trans: See ntb_mw_clear_trans(). |
209 | * @peer_mw_count: See ntb_peer_mw_count(). | ||
210 | * @peer_mw_get_addr: See ntb_peer_mw_get_addr(). | ||
211 | * @peer_mw_set_trans: See ntb_peer_mw_set_trans(). | ||
212 | * @peer_mw_clear_trans:See ntb_peer_mw_clear_trans(). | ||
207 | * @db_is_unsafe: See ntb_db_is_unsafe(). | 213 | * @db_is_unsafe: See ntb_db_is_unsafe(). |
208 | * @db_valid_mask: See ntb_db_valid_mask(). | 214 | * @db_valid_mask: See ntb_db_valid_mask(). |
209 | * @db_vector_count: See ntb_db_vector_count(). | 215 | * @db_vector_count: See ntb_db_vector_count(). |
@@ -241,13 +247,20 @@ struct ntb_dev_ops { | |||
241 | enum ntb_speed max_speed, enum ntb_width max_width); | 247 | enum ntb_speed max_speed, enum ntb_width max_width); |
242 | int (*link_disable)(struct ntb_dev *ntb); | 248 | int (*link_disable)(struct ntb_dev *ntb); |
243 | 249 | ||
244 | int (*mw_count)(struct ntb_dev *ntb); | 250 | int (*mw_count)(struct ntb_dev *ntb, int pidx); |
245 | int (*mw_get_range)(struct ntb_dev *ntb, int idx, | 251 | int (*mw_get_align)(struct ntb_dev *ntb, int pidx, int widx, |
246 | phys_addr_t *base, resource_size_t *size, | 252 | resource_size_t *addr_align, |
247 | resource_size_t *align, resource_size_t *align_size); | 253 | resource_size_t *size_align, |
248 | int (*mw_set_trans)(struct ntb_dev *ntb, int idx, | 254 | resource_size_t *size_max); |
255 | int (*mw_set_trans)(struct ntb_dev *ntb, int pidx, int widx, | ||
249 | dma_addr_t addr, resource_size_t size); | 256 | dma_addr_t addr, resource_size_t size); |
250 | int (*mw_clear_trans)(struct ntb_dev *ntb, int idx); | 257 | int (*mw_clear_trans)(struct ntb_dev *ntb, int pidx, int widx); |
258 | int (*peer_mw_count)(struct ntb_dev *ntb); | ||
259 | int (*peer_mw_get_addr)(struct ntb_dev *ntb, int widx, | ||
260 | phys_addr_t *base, resource_size_t *size); | ||
261 | int (*peer_mw_set_trans)(struct ntb_dev *ntb, int pidx, int widx, | ||
262 | u64 addr, resource_size_t size); | ||
263 | int (*peer_mw_clear_trans)(struct ntb_dev *ntb, int pidx, int widx); | ||
251 | 264 | ||
252 | int (*db_is_unsafe)(struct ntb_dev *ntb); | 265 | int (*db_is_unsafe)(struct ntb_dev *ntb); |
253 | u64 (*db_valid_mask)(struct ntb_dev *ntb); | 266 | u64 (*db_valid_mask)(struct ntb_dev *ntb); |
@@ -295,9 +308,13 @@ static inline int ntb_dev_ops_is_valid(const struct ntb_dev_ops *ops) | |||
295 | ops->link_enable && | 308 | ops->link_enable && |
296 | ops->link_disable && | 309 | ops->link_disable && |
297 | ops->mw_count && | 310 | ops->mw_count && |
298 | ops->mw_get_range && | 311 | ops->mw_get_align && |
299 | ops->mw_set_trans && | 312 | (ops->mw_set_trans || |
313 | ops->peer_mw_set_trans) && | ||
300 | /* ops->mw_clear_trans && */ | 314 | /* ops->mw_clear_trans && */ |
315 | ops->peer_mw_count && | ||
316 | ops->peer_mw_get_addr && | ||
317 | /* ops->peer_mw_clear_trans && */ | ||
301 | 318 | ||
302 | /* ops->db_is_unsafe && */ | 319 | /* ops->db_is_unsafe && */ |
303 | ops->db_valid_mask && | 320 | ops->db_valid_mask && |
@@ -655,79 +672,180 @@ static inline int ntb_link_disable(struct ntb_dev *ntb) | |||
655 | } | 672 | } |
656 | 673 | ||
657 | /** | 674 | /** |
658 | * ntb_mw_count() - get the number of memory windows | 675 | * ntb_mw_count() - get the number of inbound memory windows, which could |
676 | * be created for a specified peer device | ||
659 | * @ntb: NTB device context. | 677 | * @ntb: NTB device context. |
678 | * @pidx: Port index of peer device. | ||
660 | * | 679 | * |
661 | * Hardware and topology may support a different number of memory windows. | 680 | * Hardware and topology may support a different number of memory windows. |
681 | * Moreover different peer devices can support different number of memory | ||
682 | * windows. Simply speaking this method returns the number of possible inbound | ||
683 | * memory windows to share with specified peer device. | ||
662 | * | 684 | * |
663 | * Return: the number of memory windows. | 685 | * Return: the number of memory windows. |
664 | */ | 686 | */ |
665 | static inline int ntb_mw_count(struct ntb_dev *ntb) | 687 | static inline int ntb_mw_count(struct ntb_dev *ntb, int pidx) |
666 | { | 688 | { |
667 | return ntb->ops->mw_count(ntb); | 689 | return ntb->ops->mw_count(ntb, pidx); |
668 | } | 690 | } |
669 | 691 | ||
670 | /** | 692 | /** |
671 | * ntb_mw_get_range() - get the range of a memory window | 693 | * ntb_mw_get_align() - get the restriction parameters of inbound memory window |
672 | * @ntb: NTB device context. | 694 | * @ntb: NTB device context. |
673 | * @idx: Memory window number. | 695 | * @pidx: Port index of peer device. |
674 | * @base: OUT - the base address for mapping the memory window | 696 | * @widx: Memory window index. |
675 | * @size: OUT - the size for mapping the memory window | 697 | * @addr_align: OUT - the base alignment for translating the memory window |
676 | * @align: OUT - the base alignment for translating the memory window | 698 | * @size_align: OUT - the size alignment for translating the memory window |
677 | * @align_size: OUT - the size alignment for translating the memory window | 699 | * @size_max: OUT - the maximum size of the memory window |
678 | * | 700 | * |
679 | * Get the range of a memory window. NULL may be given for any output | 701 | * Get the alignments of an inbound memory window with specified index. |
680 | * parameter if the value is not needed. The base and size may be used for | 702 | * NULL may be given for any output parameter if the value is not needed. |
681 | * mapping the memory window, to access the peer memory. The alignment and | 703 | * The alignment and size parameters may be used for allocation of proper |
682 | * size may be used for translating the memory window, for the peer to access | 704 | * shared memory. |
683 | * memory on the local system. | 705 | * |
684 | * | 706 | * Return: Zero on success, otherwise a negative error number. |
685 | * Return: Zero on success, otherwise an error number. | ||
686 | */ | 707 | */ |
687 | static inline int ntb_mw_get_range(struct ntb_dev *ntb, int idx, | 708 | static inline int ntb_mw_get_align(struct ntb_dev *ntb, int pidx, int widx, |
688 | phys_addr_t *base, resource_size_t *size, | 709 | resource_size_t *addr_align, |
689 | resource_size_t *align, resource_size_t *align_size) | 710 | resource_size_t *size_align, |
711 | resource_size_t *size_max) | ||
690 | { | 712 | { |
691 | return ntb->ops->mw_get_range(ntb, idx, base, size, | 713 | return ntb->ops->mw_get_align(ntb, pidx, widx, addr_align, size_align, |
692 | align, align_size); | 714 | size_max); |
693 | } | 715 | } |
694 | 716 | ||
695 | /** | 717 | /** |
696 | * ntb_mw_set_trans() - set the translation of a memory window | 718 | * ntb_mw_set_trans() - set the translation of an inbound memory window |
697 | * @ntb: NTB device context. | 719 | * @ntb: NTB device context. |
698 | * @idx: Memory window number. | 720 | * @pidx: Port index of peer device. |
699 | * @addr: The dma address local memory to expose to the peer. | 721 | * @widx: Memory window index. |
722 | * @addr: The dma address of local memory to expose to the peer. | ||
700 | * @size: The size of the local memory to expose to the peer. | 723 | * @size: The size of the local memory to expose to the peer. |
701 | * | 724 | * |
702 | * Set the translation of a memory window. The peer may access local memory | 725 | * Set the translation of a memory window. The peer may access local memory |
703 | * through the window starting at the address, up to the size. The address | 726 | * through the window starting at the address, up to the size. The address |
704 | * must be aligned to the alignment specified by ntb_mw_get_range(). The size | 727 | * and size must be aligned in compliance with restrictions of |
705 | * must be aligned to the size alignment specified by ntb_mw_get_range(). | 728 | * ntb_mw_get_align(). The region size should not exceed the size_max parameter |
729 | * of that method. | ||
730 | * | ||
731 | * This method may not be implemented due to the hardware specific memory | ||
732 | * windows interface. | ||
706 | * | 733 | * |
707 | * Return: Zero on success, otherwise an error number. | 734 | * Return: Zero on success, otherwise an error number. |
708 | */ | 735 | */ |
709 | static inline int ntb_mw_set_trans(struct ntb_dev *ntb, int idx, | 736 | static inline int ntb_mw_set_trans(struct ntb_dev *ntb, int pidx, int widx, |
710 | dma_addr_t addr, resource_size_t size) | 737 | dma_addr_t addr, resource_size_t size) |
711 | { | 738 | { |
712 | return ntb->ops->mw_set_trans(ntb, idx, addr, size); | 739 | if (!ntb->ops->mw_set_trans) |
740 | return 0; | ||
741 | |||
742 | return ntb->ops->mw_set_trans(ntb, pidx, widx, addr, size); | ||
713 | } | 743 | } |
714 | 744 | ||
715 | /** | 745 | /** |
716 | * ntb_mw_clear_trans() - clear the translation of a memory window | 746 | * ntb_mw_clear_trans() - clear the translation address of an inbound memory |
747 | * window | ||
717 | * @ntb: NTB device context. | 748 | * @ntb: NTB device context. |
718 | * @idx: Memory window number. | 749 | * @pidx: Port index of peer device. |
750 | * @widx: Memory window index. | ||
719 | * | 751 | * |
720 | * Clear the translation of a memory window. The peer may no longer access | 752 | * Clear the translation of an inbound memory window. The peer may no longer |
721 | * local memory through the window. | 753 | * access local memory through the window. |
722 | * | 754 | * |
723 | * Return: Zero on success, otherwise an error number. | 755 | * Return: Zero on success, otherwise an error number. |
724 | */ | 756 | */ |
725 | static inline int ntb_mw_clear_trans(struct ntb_dev *ntb, int idx) | 757 | static inline int ntb_mw_clear_trans(struct ntb_dev *ntb, int pidx, int widx) |
726 | { | 758 | { |
727 | if (!ntb->ops->mw_clear_trans) | 759 | if (!ntb->ops->mw_clear_trans) |
728 | return ntb->ops->mw_set_trans(ntb, idx, 0, 0); | 760 | return ntb_mw_set_trans(ntb, pidx, widx, 0, 0); |
761 | |||
762 | return ntb->ops->mw_clear_trans(ntb, pidx, widx); | ||
763 | } | ||
764 | |||
765 | /** | ||
766 | * ntb_peer_mw_count() - get the number of outbound memory windows, which could | ||
767 | * be mapped to access a shared memory | ||
768 | * @ntb: NTB device context. | ||
769 | * | ||
770 | * Hardware and topology may support a different number of memory windows. | ||
771 | * This method returns the number of outbound memory windows supported by | ||
772 | * local device. | ||
773 | * | ||
774 | * Return: the number of memory windows. | ||
775 | */ | ||
776 | static inline int ntb_peer_mw_count(struct ntb_dev *ntb) | ||
777 | { | ||
778 | return ntb->ops->peer_mw_count(ntb); | ||
779 | } | ||
780 | |||
781 | /** | ||
782 | * ntb_peer_mw_get_addr() - get map address of an outbound memory window | ||
783 | * @ntb: NTB device context. | ||
784 | * @widx: Memory window index (within ntb_peer_mw_count() return value). | ||
785 | * @base: OUT - the base address of mapping region. | ||
786 | * @size: OUT - the size of mapping region. | ||
787 | * | ||
788 | * Get base and size of memory region to map. NULL may be given for any output | ||
789 | * parameter if the value is not needed. The base and size may be used for | ||
790 | * mapping the memory window, to access the peer memory. | ||
791 | * | ||
792 | * Return: Zero on success, otherwise a negative error number. | ||
793 | */ | ||
794 | static inline int ntb_peer_mw_get_addr(struct ntb_dev *ntb, int widx, | ||
795 | phys_addr_t *base, resource_size_t *size) | ||
796 | { | ||
797 | return ntb->ops->peer_mw_get_addr(ntb, widx, base, size); | ||
798 | } | ||
799 | |||
800 | /** | ||
801 | * ntb_peer_mw_set_trans() - set a translation address of a memory window | ||
802 | * retrieved from a peer device | ||
803 | * @ntb: NTB device context. | ||
804 | * @pidx: Port index of peer device the translation address received from. | ||
805 | * @widx: Memory window index. | ||
806 | * @addr: The dma address of the shared memory to access. | ||
807 | * @size: The size of the shared memory to access. | ||
808 | * | ||
809 | * Set the translation of an outbound memory window. The local device may | ||
810 | * access shared memory allocated by a peer device sent the address. | ||
811 | * | ||
812 | * This method may not be implemented due to the hardware specific memory | ||
813 | * windows interface, so a translation address can be only set on the side, | ||
814 | * where shared memory (inbound memory windows) is allocated. | ||
815 | * | ||
816 | * Return: Zero on success, otherwise an error number. | ||
817 | */ | ||
818 | static inline int ntb_peer_mw_set_trans(struct ntb_dev *ntb, int pidx, int widx, | ||
819 | u64 addr, resource_size_t size) | ||
820 | { | ||
821 | if (!ntb->ops->peer_mw_set_trans) | ||
822 | return 0; | ||
823 | |||
824 | return ntb->ops->peer_mw_set_trans(ntb, pidx, widx, addr, size); | ||
825 | } | ||
826 | |||
827 | /** | ||
828 | * ntb_peer_mw_clear_trans() - clear the translation address of an outbound | ||
829 | * memory window | ||
830 | * @ntb: NTB device context. | ||
831 | * @pidx: Port index of peer device. | ||
832 | * @widx: Memory window index. | ||
833 | * | ||
834 | * Clear the translation of a outbound memory window. The local device may no | ||
835 | * longer access a shared memory through the window. | ||
836 | * | ||
837 | * This method may not be implemented due to the hardware specific memory | ||
838 | * windows interface. | ||
839 | * | ||
840 | * Return: Zero on success, otherwise an error number. | ||
841 | */ | ||
842 | static inline int ntb_peer_mw_clear_trans(struct ntb_dev *ntb, int pidx, | ||
843 | int widx) | ||
844 | { | ||
845 | if (!ntb->ops->peer_mw_clear_trans) | ||
846 | return ntb_peer_mw_set_trans(ntb, pidx, widx, 0, 0); | ||
729 | 847 | ||
730 | return ntb->ops->mw_clear_trans(ntb, idx); | 848 | return ntb->ops->peer_mw_clear_trans(ntb, pidx, widx); |
731 | } | 849 | } |
732 | 850 | ||
733 | /** | 851 | /** |