Skip to content

Commit

Permalink
Merge branch 'etnaviv/next' of https://git.pengutronix.de/git/lst/linux
Browse files Browse the repository at this point in the history
… into drm-next

Highlights this time:
1. Fix for a nasty Kconfig dependency chain issue from Philipp.
2. Occlusion query buffer address added to the cmdstream validator by
Christian.
3. Fixes and cleanups to the job handling from me. This allows us to
turn on the GPU performance profiling added in the last cycle.
It is also prep work for hooking in the DRM GPU scheduler, which I hope
to land for the next cycle.

* 'etnaviv/next' of https://git.pengutronix.de/git/lst/linux: (32 commits)
  drm/etnaviv: use memset32 to init pagetable
  drm/etnaviv: move submit free out of critical section
  drm/etnaviv: re-enable perfmon support
  drm/etnaviv: couple runtime PM management to submit object lifetime
  drm/etnaviv: move GPU active handling to bo pin/unpin
  drm/etnaviv: move cmdbuf into submit object
  drm/etnaviv: use submit exec_state for perfmon sampling
  drm/etnaviv: move exec_state to submit object
  drm/etnaviv: move PMRs to submit object
  drm/etnaviv: refcount the submit object
  drm/etnaviv: move ww_acquire_ctx out of submit object
  drm/etnaviv: move object unpinning to submit cleanup
  drm/etnaviv: attach in fence to submit and move fence wait to fence_sync
  drm/etnaviv: rename submit fence to out_fence
  drm/etnaviv: move object fence attachment to gem_submit path
  drm/etnaviv: simplify submit_create
  drm/etnaviv: add lockdep annotations to buffer manipulation functions
  drm/etnaviv: hold GPU lock while inserting END command
  drm/etnaviv: move workqueue to be per GPU
  drm/etnaviv: remove switch_context member from etnaviv_gpu
  ...
  • Loading branch information
Dave Airlie committed Jan 4, 2018
2 parents 4ef0bef + 2f20fc4 commit 066f9eb
Show file tree
Hide file tree
Showing 19 changed files with 323 additions and 511 deletions.
9 changes: 9 additions & 0 deletions drivers/gpu/drm/etnaviv/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,22 @@ config DRM_ETNAVIV
depends on MMU
select SHMEM
select SYNC_FILE
select THERMAL if DRM_ETNAVIV_THERMAL
select TMPFS
select WANT_DEV_COREDUMP
select CMA if HAVE_DMA_CONTIGUOUS
select DMA_CMA if HAVE_DMA_CONTIGUOUS
help
DRM driver for Vivante GPUs.

config DRM_ETNAVIV_THERMAL
bool "enable ETNAVIV thermal throttling"
depends on DRM_ETNAVIV
default y
help
Compile in support for thermal throttling.
Say Y unless you want to risk burning your SoC.

config DRM_ETNAVIV_REGISTER_LOGGING
bool "enable ETNAVIV register logging"
depends on DRM_ETNAVIV
Expand Down
40 changes: 27 additions & 13 deletions drivers/gpu/drm/etnaviv/etnaviv_buffer.c
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,8 @@ static void etnaviv_cmd_select_pipe(struct etnaviv_gpu *gpu,
{
u32 flush = 0;

lockdep_assert_held(&gpu->lock);

/*
* This assumes that if we're switching to 2D, we're switching
* away from 3D, and vice versa. Hence, if we're switching to
Expand Down Expand Up @@ -164,7 +166,9 @@ static u32 etnaviv_buffer_reserve(struct etnaviv_gpu *gpu,

u16 etnaviv_buffer_init(struct etnaviv_gpu *gpu)
{
struct etnaviv_cmdbuf *buffer = gpu->buffer;
struct etnaviv_cmdbuf *buffer = &gpu->buffer;

lockdep_assert_held(&gpu->lock);

/* initialize buffer */
buffer->user_size = 0;
Expand All @@ -178,7 +182,9 @@ u16 etnaviv_buffer_init(struct etnaviv_gpu *gpu)

u16 etnaviv_buffer_config_mmuv2(struct etnaviv_gpu *gpu, u32 mtlb_addr, u32 safe_addr)
{
struct etnaviv_cmdbuf *buffer = gpu->buffer;
struct etnaviv_cmdbuf *buffer = &gpu->buffer;

lockdep_assert_held(&gpu->lock);

buffer->user_size = 0;

Expand Down Expand Up @@ -211,10 +217,12 @@ u16 etnaviv_buffer_config_mmuv2(struct etnaviv_gpu *gpu, u32 mtlb_addr, u32 safe

void etnaviv_buffer_end(struct etnaviv_gpu *gpu)
{
struct etnaviv_cmdbuf *buffer = gpu->buffer;
struct etnaviv_cmdbuf *buffer = &gpu->buffer;
unsigned int waitlink_offset = buffer->user_size - 16;
u32 link_target, flush = 0;

lockdep_assert_held(&gpu->lock);

if (gpu->exec_state == ETNA_PIPE_2D)
flush = VIVS_GL_FLUSH_CACHE_PE2D;
else if (gpu->exec_state == ETNA_PIPE_3D)
Expand Down Expand Up @@ -253,10 +261,12 @@ void etnaviv_buffer_end(struct etnaviv_gpu *gpu)
/* Append a 'sync point' to the ring buffer. */
void etnaviv_sync_point_queue(struct etnaviv_gpu *gpu, unsigned int event)
{
struct etnaviv_cmdbuf *buffer = gpu->buffer;
struct etnaviv_cmdbuf *buffer = &gpu->buffer;
unsigned int waitlink_offset = buffer->user_size - 16;
u32 dwords, target;

lockdep_assert_held(&gpu->lock);

/*
* We need at most 3 dwords in the return target:
* 1 event + 1 end + 1 wait + 1 link.
Expand Down Expand Up @@ -287,13 +297,16 @@ void etnaviv_sync_point_queue(struct etnaviv_gpu *gpu, unsigned int event)
}

/* Append a command buffer to the ring buffer. */
void etnaviv_buffer_queue(struct etnaviv_gpu *gpu, unsigned int event,
struct etnaviv_cmdbuf *cmdbuf)
void etnaviv_buffer_queue(struct etnaviv_gpu *gpu, u32 exec_state,
unsigned int event, struct etnaviv_cmdbuf *cmdbuf)
{
struct etnaviv_cmdbuf *buffer = gpu->buffer;
struct etnaviv_cmdbuf *buffer = &gpu->buffer;
unsigned int waitlink_offset = buffer->user_size - 16;
u32 return_target, return_dwords;
u32 link_target, link_dwords;
bool switch_context = gpu->exec_state != exec_state;

lockdep_assert_held(&gpu->lock);

if (drm_debug & DRM_UT_DRIVER)
etnaviv_buffer_dump(gpu, buffer, 0, 0x50);
Expand All @@ -306,7 +319,7 @@ void etnaviv_buffer_queue(struct etnaviv_gpu *gpu, unsigned int event,
* need to append a mmu flush load state, followed by a new
* link to this buffer - a total of four additional words.
*/
if (gpu->mmu->need_flush || gpu->switch_context) {
if (gpu->mmu->need_flush || switch_context) {
u32 target, extra_dwords;

/* link command */
Expand All @@ -321,7 +334,7 @@ void etnaviv_buffer_queue(struct etnaviv_gpu *gpu, unsigned int event,
}

/* pipe switch commands */
if (gpu->switch_context)
if (switch_context)
extra_dwords += 4;

target = etnaviv_buffer_reserve(gpu, buffer, extra_dwords);
Expand Down Expand Up @@ -349,10 +362,9 @@ void etnaviv_buffer_queue(struct etnaviv_gpu *gpu, unsigned int event,
gpu->mmu->need_flush = false;
}

if (gpu->switch_context) {
etnaviv_cmd_select_pipe(gpu, buffer, cmdbuf->exec_state);
gpu->exec_state = cmdbuf->exec_state;
gpu->switch_context = false;
if (switch_context) {
etnaviv_cmd_select_pipe(gpu, buffer, exec_state);
gpu->exec_state = exec_state;
}

/* And the link to the submitted buffer */
Expand Down Expand Up @@ -421,4 +433,6 @@ void etnaviv_buffer_queue(struct etnaviv_gpu *gpu, unsigned int event,

if (drm_debug & DRM_UT_DRIVER)
etnaviv_buffer_dump(gpu, buffer, 0, 0x50);

gpu->lastctx = cmdbuf->ctx;
}
1 change: 1 addition & 0 deletions drivers/gpu/drm/etnaviv/etnaviv_cmd_parser.c
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ static const struct {
ST(0x17c0, 8),
ST(0x17e0, 8),
ST(0x2400, 14 * 16),
ST(0x3824, 1),
ST(0x10800, 32 * 16),
ST(0x14600, 16),
ST(0x14800, 8 * 8),
Expand Down
29 changes: 4 additions & 25 deletions drivers/gpu/drm/etnaviv/etnaviv_cmdbuf.c
Original file line number Diff line number Diff line change
Expand Up @@ -86,26 +86,11 @@ void etnaviv_cmdbuf_suballoc_destroy(struct etnaviv_cmdbuf_suballoc *suballoc)
kfree(suballoc);
}

struct etnaviv_cmdbuf *
etnaviv_cmdbuf_new(struct etnaviv_cmdbuf_suballoc *suballoc, u32 size,
size_t nr_bos, size_t nr_pmrs)
int etnaviv_cmdbuf_init(struct etnaviv_cmdbuf_suballoc *suballoc,
struct etnaviv_cmdbuf *cmdbuf, u32 size)
{
struct etnaviv_cmdbuf *cmdbuf;
struct etnaviv_perfmon_request *pmrs;
size_t sz = size_vstruct(nr_bos, sizeof(cmdbuf->bo_map[0]),
sizeof(*cmdbuf));
int granule_offs, order, ret;

cmdbuf = kzalloc(sz, GFP_KERNEL);
if (!cmdbuf)
return NULL;

sz = sizeof(*pmrs) * nr_pmrs;
pmrs = kzalloc(sz, GFP_KERNEL);
if (!pmrs)
goto out_free_cmdbuf;

cmdbuf->pmrs = pmrs;
cmdbuf->suballoc = suballoc;
cmdbuf->size = size;

Expand All @@ -123,19 +108,15 @@ etnaviv_cmdbuf_new(struct etnaviv_cmdbuf_suballoc *suballoc, u32 size,
if (!ret) {
dev_err(suballoc->gpu->dev,
"Timeout waiting for cmdbuf space\n");
return NULL;
return -ETIMEDOUT;
}
goto retry;
}
mutex_unlock(&suballoc->lock);
cmdbuf->suballoc_offset = granule_offs * SUBALLOC_GRANULE;
cmdbuf->vaddr = suballoc->vaddr + cmdbuf->suballoc_offset;

return cmdbuf;

out_free_cmdbuf:
kfree(cmdbuf);
return NULL;
return 0;
}

void etnaviv_cmdbuf_free(struct etnaviv_cmdbuf *cmdbuf)
Expand All @@ -151,8 +132,6 @@ void etnaviv_cmdbuf_free(struct etnaviv_cmdbuf *cmdbuf)
suballoc->free_space = 1;
mutex_unlock(&suballoc->lock);
wake_up_all(&suballoc->free_event);
kfree(cmdbuf->pmrs);
kfree(cmdbuf);
}

u32 etnaviv_cmdbuf_get_va(struct etnaviv_cmdbuf *buf)
Expand Down
18 changes: 3 additions & 15 deletions drivers/gpu/drm/etnaviv/etnaviv_cmdbuf.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,27 +33,15 @@ struct etnaviv_cmdbuf {
void *vaddr;
u32 size;
u32 user_size;
/* fence after which this buffer is to be disposed */
struct dma_fence *fence;
/* target exec state */
u32 exec_state;
/* per GPU in-flight list */
struct list_head node;
/* perfmon requests */
unsigned int nr_pmrs;
struct etnaviv_perfmon_request *pmrs;
/* BOs attached to this command buffer */
unsigned int nr_bos;
struct etnaviv_vram_mapping *bo_map[0];
};

struct etnaviv_cmdbuf_suballoc *
etnaviv_cmdbuf_suballoc_new(struct etnaviv_gpu * gpu);
void etnaviv_cmdbuf_suballoc_destroy(struct etnaviv_cmdbuf_suballoc *suballoc);

struct etnaviv_cmdbuf *
etnaviv_cmdbuf_new(struct etnaviv_cmdbuf_suballoc *suballoc, u32 size,
size_t nr_bos, size_t nr_pmrs);

int etnaviv_cmdbuf_init(struct etnaviv_cmdbuf_suballoc *suballoc,
struct etnaviv_cmdbuf *cmdbuf, u32 size);
void etnaviv_cmdbuf_free(struct etnaviv_cmdbuf *cmdbuf);

u32 etnaviv_cmdbuf_get_va(struct etnaviv_cmdbuf *buf);
Expand Down
22 changes: 2 additions & 20 deletions drivers/gpu/drm/etnaviv/etnaviv_drv.c
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,7 @@ static int etnaviv_mmu_show(struct etnaviv_gpu *gpu, struct seq_file *m)

static void etnaviv_buffer_dump(struct etnaviv_gpu *gpu, struct seq_file *m)
{
struct etnaviv_cmdbuf *buf = gpu->buffer;
struct etnaviv_cmdbuf *buf = &gpu->buffer;
u32 size = buf->size;
u32 *ptr = buf->vaddr;
u32 i;
Expand Down Expand Up @@ -459,9 +459,6 @@ static int etnaviv_ioctl_pm_query_dom(struct drm_device *dev, void *data,
struct drm_etnaviv_pm_domain *args = data;
struct etnaviv_gpu *gpu;

/* reject as long as the feature isn't stable */
return -EINVAL;

if (args->pipe >= ETNA_MAX_PIPES)
return -EINVAL;

Expand All @@ -479,9 +476,6 @@ static int etnaviv_ioctl_pm_query_sig(struct drm_device *dev, void *data,
struct drm_etnaviv_pm_signal *args = data;
struct etnaviv_gpu *gpu;

/* reject as long as the feature isn't stable */
return -EINVAL;

if (args->pipe >= ETNA_MAX_PIPES)
return -EINVAL;

Expand Down Expand Up @@ -556,7 +550,7 @@ static struct drm_driver etnaviv_drm_driver = {
.desc = "etnaviv DRM",
.date = "20151214",
.major = 1,
.minor = 1,
.minor = 2,
};

/*
Expand All @@ -580,12 +574,6 @@ static int etnaviv_bind(struct device *dev)
}
drm->dev_private = priv;

priv->wq = alloc_ordered_workqueue("etnaviv", 0);
if (!priv->wq) {
ret = -ENOMEM;
goto out_wq;
}

mutex_init(&priv->gem_lock);
INIT_LIST_HEAD(&priv->gem_list);
priv->num_gpus = 0;
Expand All @@ -607,9 +595,6 @@ static int etnaviv_bind(struct device *dev)
out_register:
component_unbind_all(dev, drm);
out_bind:
flush_workqueue(priv->wq);
destroy_workqueue(priv->wq);
out_wq:
kfree(priv);
out_unref:
drm_dev_unref(drm);
Expand All @@ -624,9 +609,6 @@ static void etnaviv_unbind(struct device *dev)

drm_dev_unregister(drm);

flush_workqueue(priv->wq);
destroy_workqueue(priv->wq);

component_unbind_all(dev, drm);

drm->dev_private = NULL;
Expand Down
14 changes: 2 additions & 12 deletions drivers/gpu/drm/etnaviv/etnaviv_drv.h
Original file line number Diff line number Diff line change
Expand Up @@ -56,18 +56,8 @@ struct etnaviv_drm_private {
/* list of GEM objects: */
struct mutex gem_lock;
struct list_head gem_list;

struct workqueue_struct *wq;
};

static inline void etnaviv_queue_work(struct drm_device *dev,
struct work_struct *w)
{
struct etnaviv_drm_private *priv = dev->dev_private;

queue_work(priv->wq, w);
}

int etnaviv_ioctl_gem_submit(struct drm_device *dev, void *data,
struct drm_file *file);

Expand Down Expand Up @@ -97,8 +87,8 @@ u16 etnaviv_buffer_init(struct etnaviv_gpu *gpu);
u16 etnaviv_buffer_config_mmuv2(struct etnaviv_gpu *gpu, u32 mtlb_addr, u32 safe_addr);
void etnaviv_buffer_end(struct etnaviv_gpu *gpu);
void etnaviv_sync_point_queue(struct etnaviv_gpu *gpu, unsigned int event);
void etnaviv_buffer_queue(struct etnaviv_gpu *gpu, unsigned int event,
struct etnaviv_cmdbuf *cmdbuf);
void etnaviv_buffer_queue(struct etnaviv_gpu *gpu, u32 exec_state,
unsigned int event, struct etnaviv_cmdbuf *cmdbuf);
void etnaviv_validate_init(void);
bool etnaviv_cmd_validate_one(struct etnaviv_gpu *gpu,
u32 *stream, unsigned int size,
Expand Down
23 changes: 12 additions & 11 deletions drivers/gpu/drm/etnaviv/etnaviv_dump.c
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,7 @@ void etnaviv_core_dump(struct etnaviv_gpu *gpu)
struct core_dump_iterator iter;
struct etnaviv_vram_mapping *vram;
struct etnaviv_gem_object *obj;
struct etnaviv_cmdbuf *cmd;
struct etnaviv_gem_submit *submit;
unsigned int n_obj, n_bomap_pages;
size_t file_size, mmu_size;
__le64 *bomap, *bomap_start;
Expand All @@ -132,11 +132,11 @@ void etnaviv_core_dump(struct etnaviv_gpu *gpu)
n_bomap_pages = 0;
file_size = ARRAY_SIZE(etnaviv_dump_registers) *
sizeof(struct etnaviv_dump_registers) +
mmu_size + gpu->buffer->size;
mmu_size + gpu->buffer.size;

/* Add in the active command buffers */
list_for_each_entry(cmd, &gpu->active_cmd_list, node) {
file_size += cmd->size;
list_for_each_entry(submit, &gpu->active_submit_list, node) {
file_size += submit->cmdbuf.size;
n_obj++;
}

Expand Down Expand Up @@ -176,13 +176,14 @@ void etnaviv_core_dump(struct etnaviv_gpu *gpu)

etnaviv_core_dump_registers(&iter, gpu);
etnaviv_core_dump_mmu(&iter, gpu, mmu_size);
etnaviv_core_dump_mem(&iter, ETDUMP_BUF_RING, gpu->buffer->vaddr,
gpu->buffer->size,
etnaviv_cmdbuf_get_va(gpu->buffer));

list_for_each_entry(cmd, &gpu->active_cmd_list, node)
etnaviv_core_dump_mem(&iter, ETDUMP_BUF_CMD, cmd->vaddr,
cmd->size, etnaviv_cmdbuf_get_va(cmd));
etnaviv_core_dump_mem(&iter, ETDUMP_BUF_RING, gpu->buffer.vaddr,
gpu->buffer.size,
etnaviv_cmdbuf_get_va(&gpu->buffer));

list_for_each_entry(submit, &gpu->active_submit_list, node)
etnaviv_core_dump_mem(&iter, ETDUMP_BUF_CMD,
submit->cmdbuf.vaddr, submit->cmdbuf.size,
etnaviv_cmdbuf_get_va(&submit->cmdbuf));

/* Reserve space for the bomap */
if (n_bomap_pages) {
Expand Down
Loading

0 comments on commit 066f9eb

Please sign in to comment.