summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorErick Reyes <erickreyes@google.com>2020-08-25 18:54:21 -0700
committerDavid Chiang <davidchiang@google.com>2020-08-29 06:07:56 +0000
commit14f470f43738ff1aa682aed5394a4d5d86f557bd (patch)
treef960b9c7f2934639b5d148764f660d7307bb598a
parent569210b9d2ca684fac2cbb3856eefad6cc8a9e35 (diff)
downloadabrolhos-14f470f43738ff1aa682aed5394a4d5d86f557bd.tar.gz
Merge branch 'whitechapel' into android-gs-pixel-4.19
* darwinn-2.0: edgetpu: use chip-specific firmware IOVA edgetpu: abrolhos: add abrolhos-iommu to Kbuild edgetpu: abrolhos: slightly refactor IOMMU domain init Bug: 163619561 Change-Id: I1d4aec35ed8362843d27413e67adcc30b5410f10 Signed-off-by: Erick Reyes <erickreyes@google.com> (cherry picked from commit 0b1e29cd45c9a1824a239b019932e443dc054214)
-rw-r--r--drivers/edgetpu/Kbuild2
-rw-r--r--drivers/edgetpu/abrolhos-firmware.c9
-rw-r--r--drivers/edgetpu/abrolhos-iommu.c32
-rw-r--r--drivers/edgetpu/abrolhos/config.h7
-rw-r--r--drivers/edgetpu/edgetpu-firmware.c6
-rw-r--r--drivers/edgetpu/edgetpu-firmware.h6
-rw-r--r--drivers/edgetpu/edgetpu-internal.h3
7 files changed, 44 insertions, 21 deletions
diff --git a/drivers/edgetpu/Kbuild b/drivers/edgetpu/Kbuild
index 8c48252..f07419b 100644
--- a/drivers/edgetpu/Kbuild
+++ b/drivers/edgetpu/Kbuild
@@ -21,4 +21,4 @@ CFLAGS_abrolhos-firmware.o := -DCONFIG_ABROLHOS=1
CFLAGS_abrolhos-platform.o := -DCONFIG_ABROLHOS=1
CFLAGS_abrolhos-pm.o := -DCONFIG_ABROLHOS=1
CFLAGS_abrolhos-thermal.o := -DCONFIG_ABROLHOS=1
-
+CFLAGS_abrolhos-iommu.o := -DCONFIG_ABROLHOS=1
diff --git a/drivers/edgetpu/abrolhos-firmware.c b/drivers/edgetpu/abrolhos-firmware.c
index c4c267f..ea157ab 100644
--- a/drivers/edgetpu/abrolhos-firmware.c
+++ b/drivers/edgetpu/abrolhos-firmware.c
@@ -115,3 +115,12 @@ int edgetpu_chip_firmware_run(struct edgetpu_dev *etdev, const char *name,
{
return edgetpu_firmware_run(etdev, name, flags);
}
+
+unsigned long edgetpu_chip_firmware_iova(struct edgetpu_dev *etdev)
+{
+ /*
+ * TODO(b/129761817): Fetch the correct address, it won't be a constant
+ * value after GSA gets involved.
+ */
+ return FW_IOVA;
+}
diff --git a/drivers/edgetpu/abrolhos-iommu.c b/drivers/edgetpu/abrolhos-iommu.c
index bae9280..5134f6d 100644
--- a/drivers/edgetpu/abrolhos-iommu.c
+++ b/drivers/edgetpu/abrolhos-iommu.c
@@ -54,11 +54,21 @@ static int edgetpu_iommu_fault_handler(struct iommu_domain *domain,
return 0;
}
+static void edgetpu_init_etdomain(struct edgetpu_dev *etdev,
+ struct edgetpu_iommu_domain *etdomain,
+ struct iommu_domain *domain,
+ unsigned int pasid)
+{
+ etdomain->iommu_domain = domain;
+ etdomain->pasid = pasid;
+ iommu_set_fault_handler(domain, edgetpu_iommu_fault_handler, etdomain);
+}
+
/* mmu_info is unused and NULL for IOMMU version, let IOMMU API supply info */
int edgetpu_mmu_attach(struct edgetpu_dev *etdev, void *mmu_info)
{
struct edgetpu_iommu *etiommu;
- struct edgetpu_iommu_domain *etdomain;
+ struct iommu_domain *domain;
int i;
etiommu = kzalloc(sizeof(*etiommu), GFP_KERNEL);
@@ -80,17 +90,13 @@ int edgetpu_mmu_attach(struct edgetpu_dev *etdev, void *mmu_info)
* it as one of the user context domains.
*/
i = 0;
- etdomain = &etiommu->domain[0];
- etdomain->iommu_domain = iommu_get_domain_for_dev(etdev->dev);
- etiommu->context_0_default = etdomain->iommu_domain;
- if (!etiommu->context_0_default) {
+ domain = iommu_get_domain_for_dev(etdev->dev);
+ if (!domain) {
dev_warn(etdev->dev,
"device group has no default iommu domain\n");
} else {
- etdomain->pasid = 0;
- iommu_set_fault_handler(etdomain->iommu_domain,
- edgetpu_iommu_fault_handler, etdomain);
-
+ etiommu->context_0_default = true;
+ edgetpu_init_etdomain(etdev, &etiommu->domain[0], domain, 0);
i++;
}
@@ -99,7 +105,6 @@ int edgetpu_mmu_attach(struct edgetpu_dev *etdev, void *mmu_info)
return i ? 0 : -EINVAL;
for (; i < NCONTEXTS; i++) {
- struct iommu_domain *domain;
unsigned int pasid;
domain = iommu_domain_alloc(etdev->dev->bus);
@@ -123,11 +128,8 @@ int edgetpu_mmu_attach(struct edgetpu_dev *etdev, void *mmu_info)
iommu_aux_detach_device(domain, etdev->dev);
iommu_domain_free(domain);
} else {
- etdomain = &etiommu->domain[pasid];
- etdomain->iommu_domain = domain;
- etdomain->pasid = pasid;
- iommu_set_fault_handler(
- domain, edgetpu_iommu_fault_handler, etdomain);
+ edgetpu_init_etdomain(etdev, &etiommu->domain[pasid],
+ domain, pasid);
}
}
return 0;
diff --git a/drivers/edgetpu/abrolhos/config.h b/drivers/edgetpu/abrolhos/config.h
index 6e67345..a8ad3bf 100644
--- a/drivers/edgetpu/abrolhos/config.h
+++ b/drivers/edgetpu/abrolhos/config.h
@@ -20,6 +20,13 @@
#define EDGETPU_HAS_REMAPPED_DATA
/*
+ * The TPU VA where the firmware is located.
+ *
+ * The address is chosen to not overlap with any memory region specified in the
+ * firmware's linker file.
+ */
+#define FW_IOVA 0x16000000u
+/*
* Size of the area in remapped DRAM reserved for firmware code and internal
* data. This must match the firmware's linker file.
*/
diff --git a/drivers/edgetpu/edgetpu-firmware.c b/drivers/edgetpu/edgetpu-firmware.c
index 01bb214..99ccb84 100644
--- a/drivers/edgetpu/edgetpu-firmware.c
+++ b/drivers/edgetpu/edgetpu-firmware.c
@@ -572,6 +572,7 @@ void edgetpu_firmware_mappings_show(struct edgetpu_dev *etdev,
struct edgetpu_firmware *et_fw = etdev->firmware;
struct edgetpu_firmware_buffer *fw_buf;
phys_addr_t fw_iova_target;
+ unsigned long iova;
if (!et_fw)
return;
@@ -579,7 +580,8 @@ void edgetpu_firmware_mappings_show(struct edgetpu_dev *etdev,
if (!fw_buf->vaddr)
return;
fw_iova_target = fw_buf->dram_tpa ? fw_buf->dram_tpa : fw_buf->dma_addr;
- seq_printf(s, " 0x%llx %lu fw - %pad %s\n",
- FW_IOVA, fw_buf->alloc_size / PAGE_SIZE, &fw_iova_target,
+ iova = edgetpu_chip_firmware_iova(etdev);
+ seq_printf(s, " 0x%lx %lu fw - %pad %s\n", iova,
+ fw_buf->alloc_size / PAGE_SIZE, &fw_iova_target,
fw_buf->flags & FW_ONDEV ? "dev" : "");
}
diff --git a/drivers/edgetpu/edgetpu-firmware.h b/drivers/edgetpu/edgetpu-firmware.h
index d487280..49b4f76 100644
--- a/drivers/edgetpu/edgetpu-firmware.h
+++ b/drivers/edgetpu/edgetpu-firmware.h
@@ -133,6 +133,12 @@ struct edgetpu_firmware_handlers {
*/
int edgetpu_chip_firmware_run(struct edgetpu_dev *etdev, const char *name,
enum edgetpu_firmware_flags flags);
+/*
+ * Returns the chip-specific IOVA where the firmware is mapped.
+ *
+ * Debug purpose only.
+ */
+unsigned long edgetpu_chip_firmware_iova(struct edgetpu_dev *etdev);
/*
* Load and run firmware. Called by edgetpu_chip_firmware_run().
diff --git a/drivers/edgetpu/edgetpu-internal.h b/drivers/edgetpu/edgetpu-internal.h
index 10a70de..4668eb4 100644
--- a/drivers/edgetpu/edgetpu-internal.h
+++ b/drivers/edgetpu/edgetpu-internal.h
@@ -61,9 +61,6 @@ enum edgetpu_context_id {
/* contexts 8 and above not yet allocated */
};
-/* TPU address where the firmware is expected to be located (after remap) */
-#define FW_IOVA 0x80000000ll
-
typedef u64 tpu_addr_t;
struct edgetpu_coherent_mem {