Skip to content

Commit

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

Lucas wrote:
"a couple of small fixes:
- 2 patches from Fabio to fix module reloading
- one patch to fix a userspace visible regression, where the job
timeout is a bit too eager and kills legitimate jobs"

Signed-off-by: Dave Airlie <airlied@redhat.com>
Link: https://patchwork.freedesktop.org/patch/msgid/1530868450.15725.8.camel@pengutronix.de
  • Loading branch information
Dave Airlie committed Jul 10, 2018
2 parents 1e4b044 + 2c83a72 commit fcaca5d
Show file tree
Hide file tree
Showing 3 changed files with 47 additions and 4 deletions.
24 changes: 20 additions & 4 deletions drivers/gpu/drm/etnaviv/etnaviv_drv.c
Original file line number Diff line number Diff line change
Expand Up @@ -631,8 +631,11 @@ static struct platform_driver etnaviv_platform_driver = {
},
};

static struct platform_device *etnaviv_drm;

static int __init etnaviv_init(void)
{
struct platform_device *pdev;
int ret;
struct device_node *np;

Expand All @@ -644,7 +647,7 @@ static int __init etnaviv_init(void)

ret = platform_driver_register(&etnaviv_platform_driver);
if (ret != 0)
platform_driver_unregister(&etnaviv_gpu_driver);
goto unregister_gpu_driver;

/*
* If the DT contains at least one available GPU device, instantiate
Expand All @@ -653,20 +656,33 @@ static int __init etnaviv_init(void)
for_each_compatible_node(np, NULL, "vivante,gc") {
if (!of_device_is_available(np))
continue;

platform_device_register_simple("etnaviv", -1, NULL, 0);
pdev = platform_device_register_simple("etnaviv", -1,
NULL, 0);
if (IS_ERR(pdev)) {
ret = PTR_ERR(pdev);
of_node_put(np);
goto unregister_platform_driver;
}
etnaviv_drm = pdev;
of_node_put(np);
break;
}

return 0;

unregister_platform_driver:
platform_driver_unregister(&etnaviv_platform_driver);
unregister_gpu_driver:
platform_driver_unregister(&etnaviv_gpu_driver);
return ret;
}
module_init(etnaviv_init);

static void __exit etnaviv_exit(void)
{
platform_driver_unregister(&etnaviv_gpu_driver);
platform_device_unregister(etnaviv_drm);
platform_driver_unregister(&etnaviv_platform_driver);
platform_driver_unregister(&etnaviv_gpu_driver);
}
module_exit(etnaviv_exit);

Expand Down
3 changes: 3 additions & 0 deletions drivers/gpu/drm/etnaviv/etnaviv_gpu.h
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,9 @@ struct etnaviv_gpu {
struct work_struct sync_point_work;
int sync_point_event;

/* hang detection */
u32 hangcheck_dma_addr;

void __iomem *mmio;
int irq;

Expand Down
24 changes: 24 additions & 0 deletions drivers/gpu/drm/etnaviv/etnaviv_sched.c
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
#include "etnaviv_gem.h"
#include "etnaviv_gpu.h"
#include "etnaviv_sched.h"
#include "state.xml.h"

static int etnaviv_job_hang_limit = 0;
module_param_named(job_hang_limit, etnaviv_job_hang_limit, int , 0444);
Expand Down Expand Up @@ -85,6 +86,29 @@ static void etnaviv_sched_timedout_job(struct drm_sched_job *sched_job)
{
struct etnaviv_gem_submit *submit = to_etnaviv_submit(sched_job);
struct etnaviv_gpu *gpu = submit->gpu;
u32 dma_addr;
int change;

/*
* If the GPU managed to complete this jobs fence, the timout is
* spurious. Bail out.
*/
if (fence_completed(gpu, submit->out_fence->seqno))
return;

/*
* If the GPU is still making forward progress on the front-end (which
* should never loop) we shift out the timeout to give it a chance to
* finish the job.
*/
dma_addr = gpu_read(gpu, VIVS_FE_DMA_ADDRESS);
change = dma_addr - gpu->hangcheck_dma_addr;
if (change < 0 || change > 16) {
gpu->hangcheck_dma_addr = dma_addr;
schedule_delayed_work(&sched_job->work_tdr,
sched_job->sched->timeout);
return;
}

/* block scheduler */
kthread_park(gpu->sched.thread);
Expand Down

0 comments on commit fcaca5d

Please sign in to comment.