Subversion Repositories Kolibri OS

Rev

Rev 3298 | Rev 4075 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 3298 Rev 3480
Line 215... Line 215...
215
	 * could race us to double-decrement the refcount and cause a
215
	 * could race us to double-decrement the refcount and cause a
216
	 * use-after-free later.  Given the frequency of our handle lookups,
216
	 * use-after-free later.  Given the frequency of our handle lookups,
217
	 * we may want to use ida for number allocation and a hash table
217
	 * we may want to use ida for number allocation and a hash table
218
	 * for the pointers, anyway.
218
	 * for the pointers, anyway.
219
	 */
219
	 */
-
 
220
    if(handle == -2)
-
 
221
        printf("%s handle %d\n", __FUNCTION__, handle);
-
 
222
 
220
	spin_lock(&filp->table_lock);
223
	spin_lock(&filp->table_lock);
Line 221... Line 224...
221
 
224
 
222
	/* Check if we currently have a reference on the object */
225
	/* Check if we currently have a reference on the object */
223
	obj = idr_find(&filp->object_idr, handle);
226
	obj = idr_find(&filp->object_idr, handle);
Line 255... Line 258...
255
{
258
{
256
	struct drm_device *dev = obj->dev;
259
	struct drm_device *dev = obj->dev;
257
	int ret;
260
	int ret;
Line 258... Line 261...
258
 
261
 
259
	/*
262
	/*
-
 
263
	 * Get the user-visible handle using idr.  Preload and perform
260
	 * Get the user-visible handle using idr.
264
	 * allocation under our spinlock.
261
	 */
-
 
262
again:
-
 
263
	/* ensure there is space available to allocate a handle */
265
	 */
264
	if (idr_pre_get(&file_priv->object_idr, GFP_KERNEL) == 0)
-
 
265
		return -ENOMEM;
-
 
266
 
-
 
267
	/* do the allocation under our spinlock */
266
	idr_preload(GFP_KERNEL);
-
 
267
	spin_lock(&file_priv->table_lock);
268
	spin_lock(&file_priv->table_lock);
268
 
-
 
269
	ret = idr_alloc(&file_priv->object_idr, obj, 1, 0, GFP_NOWAIT);
269
	ret = idr_get_new_above(&file_priv->object_idr, obj, 1, (int *)handlep);
270
 
270
	spin_unlock(&file_priv->table_lock);
271
	spin_unlock(&file_priv->table_lock);
271
	if (ret == -EAGAIN)
-
 
272
		goto again;
272
	idr_preload_end();
273
	else if (ret)
273
	if (ret < 0)
-
 
274
		return ret;
Line 274... Line 275...
274
		return ret;
275
	*handlep = ret;
Line 275... Line 276...
275
 
276
 
276
	drm_gem_object_handle_reference(obj);
277
	drm_gem_object_handle_reference(obj);
Line 382... Line 383...
382
drm_gem_object_lookup(struct drm_device *dev, struct drm_file *filp,
383
drm_gem_object_lookup(struct drm_device *dev, struct drm_file *filp,
383
		      u32 handle)
384
		      u32 handle)
384
{
385
{
385
	struct drm_gem_object *obj;
386
	struct drm_gem_object *obj;
Line -... Line 387...
-
 
387
 
-
 
388
     if(handle == -2)
-
 
389
        printf("%s handle %d\n", __FUNCTION__, handle);
386
 
390
 
Line 387... Line 391...
387
	spin_lock(&filp->table_lock);
391
	spin_lock(&filp->table_lock);
388
 
392
 
389
	/* Check if we currently have a reference on the object */
393
	/* Check if we currently have a reference on the object */
Line 437... Line 441...
437
 
441
 
438
	obj = drm_gem_object_lookup(dev, file_priv, args->handle);
442
	obj = drm_gem_object_lookup(dev, file_priv, args->handle);
439
	if (obj == NULL)
443
	if (obj == NULL)
Line 440... Line -...
440
		return -ENOENT;
-
 
441
 
444
		return -ENOENT;
442
again:
-
 
443
	if (idr_pre_get(&dev->object_name_idr, GFP_KERNEL) == 0) {
-
 
444
		ret = -ENOMEM;
-
 
445
		goto err;
-
 
446
	}
445
 
447
 
446
	idr_preload(GFP_KERNEL);
448
	spin_lock(&dev->object_name_lock);
447
	spin_lock(&dev->object_name_lock);
449
	if (!obj->name) {
448
	if (!obj->name) {
450
		ret = idr_get_new_above(&dev->object_name_idr, obj, 1,
449
		ret = idr_alloc(&dev->object_name_idr, obj, 1, 0, GFP_NOWAIT);
451
					&obj->name);
450
		obj->name = ret;
-
 
451
		args->name = (uint64_t) obj->name;
Line 452... Line 452...
452
		args->name = (uint64_t) obj->name;
452
		spin_unlock(&dev->object_name_lock);
453
		spin_unlock(&dev->object_name_lock);
-
 
454
 
-
 
455
		if (ret == -EAGAIN)
453
		idr_preload_end();
-
 
454
 
Line 456... Line 455...
456
			goto again;
455
		if (ret < 0)
457
		else if (ret)
456
			goto err;
458
			goto err;
457
		ret = 0;
459
 
458
 
460
		/* Allocate a reference for the name table.  */
459
		/* Allocate a reference for the name table.  */
-
 
460
		drm_gem_object_reference(obj);
461
		drm_gem_object_reference(obj);
461
	} else {
462
	} else {
462
		args->name = (uint64_t) obj->name;
Line 463... Line 463...
463
		args->name = (uint64_t) obj->name;
463
		spin_unlock(&dev->object_name_lock);
464
		spin_unlock(&dev->object_name_lock);
464
		idr_preload_end();
Line 486... Line 486...
486
	u32 handle;
486
	u32 handle;
Line 487... Line 487...
487
 
487
 
488
	if (!(dev->driver->driver_features & DRIVER_GEM))
488
	if (!(dev->driver->driver_features & DRIVER_GEM))
Line -... Line 489...
-
 
489
		return -ENODEV;
-
 
490
 
-
 
491
    if(handle == -2)
489
		return -ENODEV;
492
        printf("%s handle %d\n", __FUNCTION__, handle);
490
 
493
 
491
	spin_lock(&dev->object_name_lock);
494
	spin_lock(&dev->object_name_lock);
492
	obj = idr_find(&dev->object_name_idr, (int) args->name);
495
	obj = idr_find(&dev->object_name_idr, (int) args->name);
493
	if (obj)
496
	if (obj)
Line 547... Line 550...
547
void
550
void
548
drm_gem_release(struct drm_device *dev, struct drm_file *file_private)
551
drm_gem_release(struct drm_device *dev, struct drm_file *file_private)
549
{
552
{
550
	idr_for_each(&file_private->object_idr,
553
	idr_for_each(&file_private->object_idr,
551
		     &drm_gem_object_release_handle, file_private);
554
		     &drm_gem_object_release_handle, file_private);
552
 
-
 
553
	idr_remove_all(&file_private->object_idr);
-
 
554
	idr_destroy(&file_private->object_idr);
555
	idr_destroy(&file_private->object_idr);
555
}
556
}
556
#endif
557
#endif
Line 557... Line 558...
557
 
558