mirror of
				https://github.com/torvalds/linux.git
				synced 2025-11-04 10:40:15 +02:00 
			
		
		
		
	drm/virtio: Handle context ID allocation errors
It is possible to run out of memory while allocating IDs. The current code would create a context with an invalid ID; change it to return -ENOMEM to userspace. Signed-off-by: Matthew Wilcox <willy@infradead.org> Link: http://patchwork.freedesktop.org/patch/msgid/20180926160031.15721-3-willy@infradead.org Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
This commit is contained in:
		
							parent
							
								
									1938d1ae32
								
							
						
					
					
						commit
						6a37c49a94
					
				
					 1 changed files with 11 additions and 18 deletions
				
			
		| 
						 | 
					@ -52,31 +52,22 @@ static void virtio_gpu_config_changed_work_func(struct work_struct *work)
 | 
				
			||||||
		      events_clear, &events_clear);
 | 
							      events_clear, &events_clear);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void virtio_gpu_ctx_id_get(struct virtio_gpu_device *vgdev,
 | 
					static int virtio_gpu_context_create(struct virtio_gpu_device *vgdev,
 | 
				
			||||||
				  uint32_t *resid)
 | 
									      uint32_t nlen, const char *name)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	int handle = ida_alloc_min(&vgdev->ctx_id_ida, 1, GFP_KERNEL);
 | 
						int handle = ida_alloc_min(&vgdev->ctx_id_ida, 1, GFP_KERNEL);
 | 
				
			||||||
	*resid = handle;
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void virtio_gpu_ctx_id_put(struct virtio_gpu_device *vgdev, uint32_t id)
 | 
						if (handle < 0)
 | 
				
			||||||
{
 | 
							return handle;
 | 
				
			||||||
	ida_free(&vgdev->ctx_id_ida, id);
 | 
						virtio_gpu_cmd_context_create(vgdev, handle, nlen, name);
 | 
				
			||||||
}
 | 
						return handle;
 | 
				
			||||||
 | 
					 | 
				
			||||||
static void virtio_gpu_context_create(struct virtio_gpu_device *vgdev,
 | 
					 | 
				
			||||||
				      uint32_t nlen, const char *name,
 | 
					 | 
				
			||||||
				      uint32_t *ctx_id)
 | 
					 | 
				
			||||||
{
 | 
					 | 
				
			||||||
	virtio_gpu_ctx_id_get(vgdev, ctx_id);
 | 
					 | 
				
			||||||
	virtio_gpu_cmd_context_create(vgdev, *ctx_id, nlen, name);
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void virtio_gpu_context_destroy(struct virtio_gpu_device *vgdev,
 | 
					static void virtio_gpu_context_destroy(struct virtio_gpu_device *vgdev,
 | 
				
			||||||
				      uint32_t ctx_id)
 | 
									      uint32_t ctx_id)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	virtio_gpu_cmd_context_destroy(vgdev, ctx_id);
 | 
						virtio_gpu_cmd_context_destroy(vgdev, ctx_id);
 | 
				
			||||||
	virtio_gpu_ctx_id_put(vgdev, ctx_id);
 | 
						ida_free(&vgdev->ctx_id_ida, ctx_id);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void virtio_gpu_init_vq(struct virtio_gpu_queue *vgvq,
 | 
					static void virtio_gpu_init_vq(struct virtio_gpu_queue *vgvq,
 | 
				
			||||||
| 
						 | 
					@ -261,7 +252,7 @@ int virtio_gpu_driver_open(struct drm_device *dev, struct drm_file *file)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct virtio_gpu_device *vgdev = dev->dev_private;
 | 
						struct virtio_gpu_device *vgdev = dev->dev_private;
 | 
				
			||||||
	struct virtio_gpu_fpriv *vfpriv;
 | 
						struct virtio_gpu_fpriv *vfpriv;
 | 
				
			||||||
	uint32_t id;
 | 
						int id;
 | 
				
			||||||
	char dbgname[TASK_COMM_LEN];
 | 
						char dbgname[TASK_COMM_LEN];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	/* can't create contexts without 3d renderer */
 | 
						/* can't create contexts without 3d renderer */
 | 
				
			||||||
| 
						 | 
					@ -274,7 +265,9 @@ int virtio_gpu_driver_open(struct drm_device *dev, struct drm_file *file)
 | 
				
			||||||
		return -ENOMEM;
 | 
							return -ENOMEM;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	get_task_comm(dbgname, current);
 | 
						get_task_comm(dbgname, current);
 | 
				
			||||||
	virtio_gpu_context_create(vgdev, strlen(dbgname), dbgname, &id);
 | 
						id = virtio_gpu_context_create(vgdev, strlen(dbgname), dbgname);
 | 
				
			||||||
 | 
						if (id < 0)
 | 
				
			||||||
 | 
							return id;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	vfpriv->ctx_id = id;
 | 
						vfpriv->ctx_id = id;
 | 
				
			||||||
	file->driver_priv = vfpriv;
 | 
						file->driver_priv = vfpriv;
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in a new issue