diff options
| -rw-r--r-- | Documentation/ABI/testing/sysfs-class-iommu-amd-iommu | 14 | ||||
| -rw-r--r-- | drivers/iommu/amd_iommu.c | 6 | ||||
| -rw-r--r-- | drivers/iommu/amd_iommu_init.c | 38 | ||||
| -rw-r--r-- | drivers/iommu/amd_iommu_types.h | 3 |
4 files changed, 61 insertions, 0 deletions
diff --git a/Documentation/ABI/testing/sysfs-class-iommu-amd-iommu b/Documentation/ABI/testing/sysfs-class-iommu-amd-iommu new file mode 100644 index 000000000000..d6ba8e8a4a97 --- /dev/null +++ b/Documentation/ABI/testing/sysfs-class-iommu-amd-iommu | |||
| @@ -0,0 +1,14 @@ | |||
| 1 | What: /sys/class/iommu/<iommu>/amd-iommu/cap | ||
| 2 | Date: June 2014 | ||
| 3 | KernelVersion: 3.17 | ||
| 4 | Contact: Alex Williamson <alex.williamson@redhat.com> | ||
| 5 | Description: | ||
| 6 | IOMMU capability header as documented in the AMD IOMMU | ||
| 7 | specification. Format: %x | ||
| 8 | |||
| 9 | What: /sys/class/iommu/<iommu>/amd-iommu/features | ||
| 10 | Date: June 2014 | ||
| 11 | KernelVersion: 3.17 | ||
| 12 | Contact: Alex Williamson <alex.williamson@redhat.com> | ||
| 13 | Description: | ||
| 14 | Extended features of the IOMMU. Format: %llx | ||
diff --git a/drivers/iommu/amd_iommu.c b/drivers/iommu/amd_iommu.c index 2e03c17c2499..c8f87a6c9b90 100644 --- a/drivers/iommu/amd_iommu.c +++ b/drivers/iommu/amd_iommu.c | |||
| @@ -379,6 +379,9 @@ static int iommu_init_device(struct device *dev) | |||
| 379 | 379 | ||
| 380 | dev->archdata.iommu = dev_data; | 380 | dev->archdata.iommu = dev_data; |
| 381 | 381 | ||
| 382 | iommu_device_link(amd_iommu_rlookup_table[dev_data->devid]->iommu_dev, | ||
| 383 | dev); | ||
| 384 | |||
| 382 | return 0; | 385 | return 0; |
| 383 | } | 386 | } |
| 384 | 387 | ||
| @@ -403,6 +406,9 @@ static void iommu_uninit_device(struct device *dev) | |||
| 403 | if (!dev_data) | 406 | if (!dev_data) |
| 404 | return; | 407 | return; |
| 405 | 408 | ||
| 409 | iommu_device_unlink(amd_iommu_rlookup_table[dev_data->devid]->iommu_dev, | ||
| 410 | dev); | ||
| 411 | |||
| 406 | iommu_group_remove_device(dev); | 412 | iommu_group_remove_device(dev); |
| 407 | 413 | ||
| 408 | /* Unlink from alias, it may change if another device is re-plugged */ | 414 | /* Unlink from alias, it may change if another device is re-plugged */ |
diff --git a/drivers/iommu/amd_iommu_init.c b/drivers/iommu/amd_iommu_init.c index 0e08545d7298..3783e0b44df6 100644 --- a/drivers/iommu/amd_iommu_init.c +++ b/drivers/iommu/amd_iommu_init.c | |||
| @@ -26,6 +26,7 @@ | |||
| 26 | #include <linux/msi.h> | 26 | #include <linux/msi.h> |
| 27 | #include <linux/amd-iommu.h> | 27 | #include <linux/amd-iommu.h> |
| 28 | #include <linux/export.h> | 28 | #include <linux/export.h> |
| 29 | #include <linux/iommu.h> | ||
| 29 | #include <asm/pci-direct.h> | 30 | #include <asm/pci-direct.h> |
| 30 | #include <asm/iommu.h> | 31 | #include <asm/iommu.h> |
| 31 | #include <asm/gart.h> | 32 | #include <asm/gart.h> |
| @@ -1197,6 +1198,39 @@ static void init_iommu_perf_ctr(struct amd_iommu *iommu) | |||
| 1197 | iommu->max_counters = (u8) ((val >> 7) & 0xf); | 1198 | iommu->max_counters = (u8) ((val >> 7) & 0xf); |
| 1198 | } | 1199 | } |
| 1199 | 1200 | ||
| 1201 | static ssize_t amd_iommu_show_cap(struct device *dev, | ||
| 1202 | struct device_attribute *attr, | ||
| 1203 | char *buf) | ||
| 1204 | { | ||
| 1205 | struct amd_iommu *iommu = dev_get_drvdata(dev); | ||
| 1206 | return sprintf(buf, "%x\n", iommu->cap); | ||
| 1207 | } | ||
| 1208 | static DEVICE_ATTR(cap, S_IRUGO, amd_iommu_show_cap, NULL); | ||
| 1209 | |||
| 1210 | static ssize_t amd_iommu_show_features(struct device *dev, | ||
| 1211 | struct device_attribute *attr, | ||
| 1212 | char *buf) | ||
| 1213 | { | ||
| 1214 | struct amd_iommu *iommu = dev_get_drvdata(dev); | ||
| 1215 | return sprintf(buf, "%llx\n", iommu->features); | ||
| 1216 | } | ||
| 1217 | static DEVICE_ATTR(features, S_IRUGO, amd_iommu_show_features, NULL); | ||
| 1218 | |||
| 1219 | static struct attribute *amd_iommu_attrs[] = { | ||
| 1220 | &dev_attr_cap.attr, | ||
| 1221 | &dev_attr_features.attr, | ||
| 1222 | NULL, | ||
| 1223 | }; | ||
| 1224 | |||
| 1225 | static struct attribute_group amd_iommu_group = { | ||
| 1226 | .name = "amd-iommu", | ||
| 1227 | .attrs = amd_iommu_attrs, | ||
| 1228 | }; | ||
| 1229 | |||
| 1230 | static const struct attribute_group *amd_iommu_groups[] = { | ||
| 1231 | &amd_iommu_group, | ||
| 1232 | NULL, | ||
| 1233 | }; | ||
| 1200 | 1234 | ||
| 1201 | static int iommu_init_pci(struct amd_iommu *iommu) | 1235 | static int iommu_init_pci(struct amd_iommu *iommu) |
| 1202 | { | 1236 | { |
| @@ -1297,6 +1331,10 @@ static int iommu_init_pci(struct amd_iommu *iommu) | |||
| 1297 | 1331 | ||
| 1298 | amd_iommu_erratum_746_workaround(iommu); | 1332 | amd_iommu_erratum_746_workaround(iommu); |
| 1299 | 1333 | ||
| 1334 | iommu->iommu_dev = iommu_device_create(&iommu->dev->dev, iommu, | ||
| 1335 | amd_iommu_groups, "ivhd%d", | ||
| 1336 | iommu->index); | ||
| 1337 | |||
| 1300 | return pci_enable_device(iommu->dev); | 1338 | return pci_enable_device(iommu->dev); |
| 1301 | } | 1339 | } |
| 1302 | 1340 | ||
diff --git a/drivers/iommu/amd_iommu_types.h b/drivers/iommu/amd_iommu_types.h index 7277a200d916..557a20e533f0 100644 --- a/drivers/iommu/amd_iommu_types.h +++ b/drivers/iommu/amd_iommu_types.h | |||
| @@ -577,6 +577,9 @@ struct amd_iommu { | |||
| 577 | /* default dma_ops domain for that IOMMU */ | 577 | /* default dma_ops domain for that IOMMU */ |
| 578 | struct dma_ops_domain *default_dom; | 578 | struct dma_ops_domain *default_dom; |
| 579 | 579 | ||
| 580 | /* IOMMU sysfs device */ | ||
| 581 | struct device *iommu_dev; | ||
| 582 | |||
| 580 | /* | 583 | /* |
| 581 | * We can't rely on the BIOS to restore all values on reinit, so we | 584 | * We can't rely on the BIOS to restore all values on reinit, so we |
| 582 | * need to stash them | 585 | * need to stash them |
