aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJoerg Roedel <joro@8bytes.org>2013-02-04 08:00:01 -0500
committerJoerg Roedel <joro@8bytes.org>2013-02-06 04:47:28 -0500
commit693567125bde1966a095267a9d8ca1b8d40f59ee (patch)
tree0ab1b5b9fea365c2d3d0b16388652c5041ce438d
parentd7787d579cbef9f8079104759a2259fc916c688c (diff)
iommu: Add DOMAIN_ATTR_WINDOWS domain attribute
This attribute can be used to set and get the number of subwindows on IOMMUs that are window-based. Signed-off-by: Joerg Roedel <joro@8bytes.org>
-rw-r--r--drivers/iommu/iommu.c33
-rw-r--r--include/linux/iommu.h5
2 files changed, 35 insertions, 3 deletions
diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index b3aced7356cc..b972d430d92b 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -891,6 +891,7 @@ int iommu_domain_get_attr(struct iommu_domain *domain,
891 struct iommu_domain_geometry *geometry; 891 struct iommu_domain_geometry *geometry;
892 bool *paging; 892 bool *paging;
893 int ret = 0; 893 int ret = 0;
894 u32 *count;
894 895
895 switch (attr) { 896 switch (attr) {
896 case DOMAIN_ATTR_GEOMETRY: 897 case DOMAIN_ATTR_GEOMETRY:
@@ -902,6 +903,15 @@ int iommu_domain_get_attr(struct iommu_domain *domain,
902 paging = data; 903 paging = data;
903 *paging = (domain->ops->pgsize_bitmap != 0UL); 904 *paging = (domain->ops->pgsize_bitmap != 0UL);
904 break; 905 break;
906 case DOMAIN_ATTR_WINDOWS:
907 count = data;
908
909 if (domain->ops->domain_get_windows != NULL)
910 *count = domain->ops->domain_get_windows(domain);
911 else
912 ret = -ENODEV;
913
914 break;
905 default: 915 default:
906 if (!domain->ops->domain_get_attr) 916 if (!domain->ops->domain_get_attr)
907 return -EINVAL; 917 return -EINVAL;
@@ -916,9 +926,26 @@ EXPORT_SYMBOL_GPL(iommu_domain_get_attr);
916int iommu_domain_set_attr(struct iommu_domain *domain, 926int iommu_domain_set_attr(struct iommu_domain *domain,
917 enum iommu_attr attr, void *data) 927 enum iommu_attr attr, void *data)
918{ 928{
919 if (!domain->ops->domain_set_attr) 929 int ret = 0;
920 return -EINVAL; 930 u32 *count;
931
932 switch (attr) {
933 case DOMAIN_ATTR_WINDOWS:
934 count = data;
935
936 if (domain->ops->domain_set_windows != NULL)
937 ret = domain->ops->domain_set_windows(domain, *count);
938 else
939 ret = -ENODEV;
921 940
922 return domain->ops->domain_set_attr(domain, attr, data); 941 break;
942 default:
943 if (domain->ops->domain_set_attr == NULL)
944 return -EINVAL;
945
946 ret = domain->ops->domain_set_attr(domain, attr, data);
947 }
948
949 return ret;
923} 950}
924EXPORT_SYMBOL_GPL(iommu_domain_set_attr); 951EXPORT_SYMBOL_GPL(iommu_domain_set_attr);
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 5ea3d7250917..ba3b8a98a049 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -60,6 +60,7 @@ struct iommu_domain {
60enum iommu_attr { 60enum iommu_attr {
61 DOMAIN_ATTR_GEOMETRY, 61 DOMAIN_ATTR_GEOMETRY,
62 DOMAIN_ATTR_PAGING, 62 DOMAIN_ATTR_PAGING,
63 DOMAIN_ATTR_WINDOWS,
63 DOMAIN_ATTR_MAX, 64 DOMAIN_ATTR_MAX,
64}; 65};
65 66
@@ -106,6 +107,10 @@ struct iommu_ops {
106 int (*domain_window_enable)(struct iommu_domain *domain, u32 wnd_nr, 107 int (*domain_window_enable)(struct iommu_domain *domain, u32 wnd_nr,
107 phys_addr_t paddr, u64 size); 108 phys_addr_t paddr, u64 size);
108 void (*domain_window_disable)(struct iommu_domain *domain, u32 wnd_nr); 109 void (*domain_window_disable)(struct iommu_domain *domain, u32 wnd_nr);
110 /* Set the numer of window per domain */
111 int (*domain_set_windows)(struct iommu_domain *domain, u32 w_count);
112 /* Get the numer of window per domain */
113 u32 (*domain_get_windows)(struct iommu_domain *domain);
109 114
110 unsigned long pgsize_bitmap; 115 unsigned long pgsize_bitmap;
111}; 116};