summaryrefslogtreecommitdiff
path: root/drivers/video/tegra/host
diff options
context:
space:
mode:
authorTerje Bergstrom <tbergstrom@nvidia.com>2012-05-24 15:06:58 +0300
committerSimone Willett <swillett@nvidia.com>2012-05-25 14:49:06 -0700
commit73f65f7f6898bd88fe457f96d4dc702f746058bc (patch)
tree4e1f89079d451da1d084630e97b08cba05cb13fe /drivers/video/tegra/host
parent97b5fcb955784c5245debc020473318dd45e5683 (diff)
video: tegra: host: Replace nvmap structs with own
Replace usage of nvmap_pinarray_elem with own nvhost_reloc and nvhost_reloc_shift structs. Bug 965206 Change-Id: I90618d8a34d79156d8880d9925dadbf416353811 Signed-off-by: Terje Bergstrom <tbergstrom@nvidia.com> Reviewed-on: http://git-master/r/104450 Reviewed-by: Juha Tukkinen <jtukkinen@nvidia.com> Reviewed-by: Automatic_Commit_Validation_User Reviewed-by: Mayuresh Kulkarni <mkulkarni@nvidia.com>
Diffstat (limited to 'drivers/video/tegra/host')
-rw-r--r--drivers/video/tegra/host/bus_client.c39
-rw-r--r--drivers/video/tegra/host/nvhost_job.c54
-rw-r--r--drivers/video/tegra/host/nvhost_job.h3
3 files changed, 56 insertions, 40 deletions
diff --git a/drivers/video/tegra/host/bus_client.c b/drivers/video/tegra/host/bus_client.c
index 397cd21f555d..9b71542a48aa 100644
--- a/drivers/video/tegra/host/bus_client.c
+++ b/drivers/video/tegra/host/bus_client.c
@@ -238,21 +238,28 @@ static ssize_t nvhost_channelwrite(struct file *filp, const char __user *buf,
cmdbuf.mem, cmdbuf.words, cmdbuf.offset);
hdr->num_cmdbufs--;
} else if (hdr->num_relocs) {
- consumed = sizeof(struct nvhost_reloc);
- if (remaining < consumed)
+ int numrelocs = remaining / sizeof(struct nvhost_reloc);
+ if (!numrelocs)
break;
- if (copy_from_user(&job->pinarray[job->num_relocs],
+ numrelocs = min_t(int, numrelocs, priv->hdr.num_relocs);
+ consumed = numrelocs * sizeof(struct nvhost_reloc);
+ if (copy_from_user(&job->relocarray[job->num_relocs],
buf, consumed)) {
err = -EFAULT;
break;
}
- trace_nvhost_channel_write_reloc(chname,
- job->pinarray[job->num_relocs].patch_mem,
- job->pinarray[job->num_relocs].patch_offset,
- job->pinarray[job->num_relocs].pin_mem,
- job->pinarray[job->num_relocs].pin_offset);
- job->num_relocs++;
- hdr->num_relocs--;
+ while (numrelocs) {
+ struct nvhost_reloc *reloc =
+ &job->relocarray[job->num_relocs];
+ trace_nvhost_channel_write_reloc(chname,
+ reloc->cmdbuf_mem,
+ reloc->cmdbuf_offset,
+ reloc->target,
+ reloc->target_offset);
+ job->num_relocs++;
+ hdr->num_relocs--;
+ numrelocs--;
+ }
} else if (hdr->num_waitchks) {
int numwaitchks =
(remaining / sizeof(struct nvhost_waitchk));
@@ -274,16 +281,18 @@ static ssize_t nvhost_channelwrite(struct file *filp, const char __user *buf,
} else if (priv->num_relocshifts) {
int next_shift =
job->num_relocs - priv->num_relocshifts;
- consumed = sizeof(struct nvhost_reloc_shift);
- if (remaining < consumed)
+ int num =
+ (remaining / sizeof(struct nvhost_reloc_shift));
+ if (!num)
break;
- if (copy_from_user(
- &job->pinarray[next_shift].reloc_shift,
+ num = min_t(int, num, priv->num_relocshifts);
+ consumed = num * sizeof(struct nvhost_reloc_shift);
+ if (copy_from_user(&job->relocshiftarray[next_shift],
buf, consumed)) {
err = -EFAULT;
break;
}
- priv->num_relocshifts--;
+ priv->num_relocshifts -= num;
} else {
err = -EFAULT;
break;
diff --git a/drivers/video/tegra/host/nvhost_job.c b/drivers/video/tegra/host/nvhost_job.c
index 6d8c3bd2bd50..e029449b6184 100644
--- a/drivers/video/tegra/host/nvhost_job.c
+++ b/drivers/video/tegra/host/nvhost_job.c
@@ -41,7 +41,8 @@ static int job_size(struct nvhost_submit_hdr_ext *hdr)
int num_unpins = num_cmdbufs + num_relocs;
return sizeof(struct nvhost_job)
- + num_relocs * sizeof(struct nvmap_pinarray_elem)
+ + num_relocs * sizeof(struct nvhost_reloc)
+ + num_relocs * sizeof(struct nvhost_reloc_shift)
+ num_unpins * sizeof(struct nvmap_handle_ref *)
+ num_waitchks * sizeof(struct nvhost_waitchk)
+ num_cmdbufs * sizeof(struct nvhost_job_gather);
@@ -63,8 +64,10 @@ static void init_fields(struct nvhost_job *job,
/* Redistribute memory to the structs */
mem += sizeof(struct nvhost_job);
- job->pinarray = num_relocs ? mem : NULL;
- mem += num_relocs * sizeof(struct nvmap_pinarray_elem);
+ job->relocarray = num_relocs ? mem : NULL;
+ mem += num_relocs * sizeof(struct nvhost_reloc);
+ job->relocshiftarray = num_relocs ? mem : NULL;
+ mem += num_relocs * sizeof(struct nvhost_reloc_shift);
job->unpins = num_unpins ? mem : NULL;
mem += num_unpins * sizeof(struct nvmap_handle_ref *);
job->waitchk = num_waitchks ? mem : NULL;
@@ -154,44 +157,46 @@ void nvhost_job_add_gather(struct nvhost_job *job,
job->num_gathers += 1;
}
-static int do_relocs(struct nvhost_job *job, u32 patch_mem, void *patch_addr)
+static int do_relocs(struct nvhost_job *job, u32 cmdbuf_mem, void *cmdbuf_addr)
{
- phys_addr_t pin_phys;
+ phys_addr_t target_phys;
int i;
u32 mem_id = 0;
- struct nvmap_handle_ref *pin_ref = NULL;
+ struct nvmap_handle_ref *target_ref = NULL;
/* pin & patch the relocs for one gather */
for (i = 0; i < job->num_relocs; i++) {
- struct nvmap_pinarray_elem *pin = &job->pinarray[i];
+ struct nvhost_reloc *reloc = &job->relocarray[i];
+ struct nvhost_reloc_shift *shift = &job->relocshiftarray[i];
/* skip all other gathers */
- if (patch_mem != pin->patch_mem)
+ if (cmdbuf_mem != reloc->cmdbuf_mem)
continue;
/* check if pin-mem is same as previous */
- if (pin->pin_mem != mem_id) {
- pin_ref = nvmap_duplicate_handle_id(job->nvmap,
- pin->pin_mem);
- if (IS_ERR(pin_ref))
- return PTR_ERR(pin_ref);
-
- pin_phys = nvmap_pin(job->nvmap, pin_ref);
- if (IS_ERR((void *)pin_phys)) {
- nvmap_free(job->nvmap, pin_ref);
- return pin_phys;
+ if (reloc->target != mem_id) {
+ target_ref = nvmap_duplicate_handle_id(job->nvmap,
+ reloc->target);
+ if (IS_ERR(target_ref))
+ return PTR_ERR(target_ref);
+
+ target_phys = nvmap_pin(job->nvmap, target_ref);
+ if (IS_ERR((void *)target_phys)) {
+ nvmap_free(job->nvmap, target_ref);
+ return target_phys;
}
- mem_id = pin->pin_mem;
- job->unpins[job->num_unpins++] = pin_ref;
+ mem_id = reloc->target;
+ job->unpins[job->num_unpins++] = target_ref;
}
- __raw_writel((pin_phys + pin->pin_offset) >> pin->reloc_shift,
- (patch_addr + pin->patch_offset));
+ __raw_writel(
+ (target_phys + reloc->target_offset) >> shift->shift,
+ (cmdbuf_addr + reloc->cmdbuf_offset));
/* Different gathers might have same mem_id. This ensures we
* perform reloc only once per gather memid. */
- pin->patch_mem = 0;
+ reloc->cmdbuf_mem = 0;
}
return 0;
@@ -216,7 +221,8 @@ static int do_waitchks(struct nvhost_job *job, struct nvhost_syncpt *sp,
continue;
trace_nvhost_syncpt_wait_check(wait->mem, wait->offset,
- wait->syncpt_id, wait->thresh);
+ wait->syncpt_id, wait->thresh,
+ nvhost_syncpt_read(sp, wait->syncpt_id));
if (nvhost_syncpt_is_expired(sp,
wait->syncpt_id, wait->thresh)) {
/*
diff --git a/drivers/video/tegra/host/nvhost_job.h b/drivers/video/tegra/host/nvhost_job.h
index b30f5faf7e8f..ec1366337279 100644
--- a/drivers/video/tegra/host/nvhost_job.h
+++ b/drivers/video/tegra/host/nvhost_job.h
@@ -67,7 +67,8 @@ struct nvhost_job {
u32 waitchk_mask;
/* Array of handles to be pinned & unpinned */
- struct nvmap_pinarray_elem *pinarray;
+ struct nvhost_reloc *relocarray;
+ struct nvhost_reloc_shift *relocshiftarray;
int num_relocs;
struct nvmap_handle_ref **unpins;
int num_unpins;