diff --git a/src/gallium/drivers/etnaviv/etnaviv_screen.c b/src/gallium/drivers/etnaviv/etnaviv_screen.c index 19a6a98ad8f..a3d3bfff6ac 100644 --- a/src/gallium/drivers/etnaviv/etnaviv_screen.c +++ b/src/gallium/drivers/etnaviv/etnaviv_screen.c @@ -106,6 +106,9 @@ etna_screen_destroy(struct pipe_screen *pscreen) if (screen->pipe) etna_pipe_del(screen->pipe); + if (screen->npu && screen->npu != screen->gpu) + etna_gpu_del(screen->npu); + if (screen->gpu) etna_gpu_del(screen->gpu); @@ -1059,7 +1062,7 @@ etna_screen_get_fd(struct pipe_screen *pscreen) struct pipe_screen * etna_screen_create(struct etna_device *dev, struct etna_gpu *gpu, - struct renderonly *ro) + struct etna_gpu *npu, struct renderonly *ro) { struct etna_screen *screen = CALLOC_STRUCT(etna_screen); struct pipe_screen *pscreen; @@ -1067,9 +1070,13 @@ etna_screen_create(struct etna_device *dev, struct etna_gpu *gpu, if (!screen) return NULL; + if (!gpu) + gpu = npu; + pscreen = &screen->base; screen->dev = dev; screen->gpu = gpu; + screen->npu = npu; screen->ro = ro; screen->info = etna_gpu_get_core_info(gpu); diff --git a/src/gallium/drivers/etnaviv/etnaviv_screen.h b/src/gallium/drivers/etnaviv/etnaviv_screen.h index 2bdf257658d..d45ce5fdb6a 100644 --- a/src/gallium/drivers/etnaviv/etnaviv_screen.h +++ b/src/gallium/drivers/etnaviv/etnaviv_screen.h @@ -49,6 +49,7 @@ struct etna_screen { struct etna_device *dev; struct etna_gpu *gpu; + struct etna_gpu *npu; struct etna_pipe *pipe; struct etna_perfmon *perfmon; struct renderonly *ro; @@ -90,7 +91,7 @@ etna_screen_bo_from_handle(struct pipe_screen *pscreen, struct pipe_screen * etna_screen_create(struct etna_device *dev, struct etna_gpu *gpu, - struct renderonly *ro); + struct etna_gpu *npu, struct renderonly *ro); static inline size_t etna_screen_get_tile_size(struct etna_screen *screen, uint8_t ts_mode, diff --git a/src/gallium/winsys/etnaviv/drm/etnaviv_drm_winsys.c b/src/gallium/winsys/etnaviv/drm/etnaviv_drm_winsys.c index 5ea3eca1a01..6c273c06a62 100644 --- a/src/gallium/winsys/etnaviv/drm/etnaviv_drm_winsys.c +++ b/src/gallium/winsys/etnaviv/drm/etnaviv_drm_winsys.c @@ -38,7 +38,8 @@ static struct pipe_screen * screen_create(int gpu_fd, const struct pipe_screen_config *config, struct renderonly *ro) { struct etna_device *dev; - struct etna_gpu *gpu; + struct etna_gpu *gpu = NULL; + struct etna_gpu *npu = NULL; int i; dev = etna_device_new_dup(gpu_fd); @@ -47,21 +48,41 @@ screen_create(int gpu_fd, const struct pipe_screen_config *config, struct render return NULL; } - for (i = 0;; i++) { - gpu = etna_gpu_new(dev, i); - if (!gpu) { - fprintf(stderr, "Error creating gpu\n"); - return NULL; - } + for (i = 0; !gpu || !npu; i++) { + struct etna_core_info *info; + struct etna_gpu *core = etna_gpu_new(dev, i); - /* Look for a 3D capable GPU */ - if (etna_core_has_feature(etna_gpu_get_core_info(gpu), ETNA_FEATURE_PIPE_3D)) + if (!core) break; - etna_gpu_del(gpu); + info = etna_gpu_get_core_info(core); + switch (info->type) { + case ETNA_CORE_GPU: + /* Look for a 3D capable GPU */ + if (!gpu && etna_core_has_feature(info, ETNA_FEATURE_PIPE_3D)) { + gpu = core; + continue; + } + break; + case ETNA_CORE_NPU: + if (!npu) { + npu = core; + continue; + } + break; + default: + unreachable("invalid core type"); + } + + etna_gpu_del(core); } - return etna_screen_create(dev, gpu, ro); + if (!gpu && !npu) { + fprintf(stderr, "Error creating gpu or npu\n"); + return NULL; + } + + return etna_screen_create(dev, gpu, npu, ro); } struct pipe_screen *