Subversion Repositories Kolibri OS

Rev

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

Rev 2160 Rev 3031
Line 29... Line 29...
29
 *      Dave Airlie 
29
 *      Dave Airlie 
30
 *      Jesse Barnes 
30
 *      Jesse Barnes 
31
 */
31
 */
32
#include 
32
#include 
33
#include 
33
#include 
34
#include "drm.h"
34
#include 
35
#include "drmP.h"
35
#include 
36
#include "drm_crtc.h"
36
#include 
37
#include "drm_edid.h"
37
#include 
38
 
-
 
39
struct drm_prop_enum_list {
38
#include 
40
	int type;
-
 
41
	char *name;
-
 
42
};
-
 
Line 43... Line 39...
43
 
39
 
44
/* Avoid boilerplate.  I'm tired of typing. */
40
/* Avoid boilerplate.  I'm tired of typing. */
45
#define DRM_ENUM_NAME_FN(fnname, list)				\
41
#define DRM_ENUM_NAME_FN(fnname, list)				\
46
	char *fnname(int val)					\
42
	char *fnname(int val)					\
Line 160... Line 156...
160
	{ DRM_MODE_CONNECTOR_DisplayPort, "DP", 0 },
156
	{ DRM_MODE_CONNECTOR_DisplayPort, "DP", 0 },
161
	{ DRM_MODE_CONNECTOR_HDMIA, "HDMI-A", 0 },
157
	{ DRM_MODE_CONNECTOR_HDMIA, "HDMI-A", 0 },
162
	{ DRM_MODE_CONNECTOR_HDMIB, "HDMI-B", 0 },
158
	{ DRM_MODE_CONNECTOR_HDMIB, "HDMI-B", 0 },
163
	{ DRM_MODE_CONNECTOR_TV, "TV", 0 },
159
	{ DRM_MODE_CONNECTOR_TV, "TV", 0 },
164
	{ DRM_MODE_CONNECTOR_eDP, "eDP", 0 },
160
	{ DRM_MODE_CONNECTOR_eDP, "eDP", 0 },
-
 
161
	{ DRM_MODE_CONNECTOR_VIRTUAL, "Virtual", 0},
165
};
162
};
Line 166... Line 163...
166
 
163
 
167
static struct drm_prop_enum_list drm_encoder_enum_list[] =
164
static struct drm_prop_enum_list drm_encoder_enum_list[] =
168
{	{ DRM_MODE_ENCODER_NONE, "None" },
165
{	{ DRM_MODE_ENCODER_NONE, "None" },
169
	{ DRM_MODE_ENCODER_DAC, "DAC" },
166
	{ DRM_MODE_ENCODER_DAC, "DAC" },
170
	{ DRM_MODE_ENCODER_TMDS, "TMDS" },
167
	{ DRM_MODE_ENCODER_TMDS, "TMDS" },
171
	{ DRM_MODE_ENCODER_LVDS, "LVDS" },
168
	{ DRM_MODE_ENCODER_LVDS, "LVDS" },
-
 
169
	{ DRM_MODE_ENCODER_TVDAC, "TV" },
172
	{ DRM_MODE_ENCODER_TVDAC, "TV" },
170
	{ DRM_MODE_ENCODER_VIRTUAL, "Virtual" },
Line 173... Line 171...
173
};
171
};
174
 
172
 
175
char *drm_get_encoder_name(struct drm_encoder *encoder)
173
char *drm_get_encoder_name(struct drm_encoder *encoder)
Line 226... Line 224...
226
	int ret;
224
	int ret;
Line 227... Line 225...
227
 
225
 
228
again:
226
again:
229
	if (idr_pre_get(&dev->mode_config.crtc_idr, GFP_KERNEL) == 0) {
227
	if (idr_pre_get(&dev->mode_config.crtc_idr, GFP_KERNEL) == 0) {
230
		DRM_ERROR("Ran out memory getting a mode number\n");
228
		DRM_ERROR("Ran out memory getting a mode number\n");
231
		return -EINVAL;
229
		return -ENOMEM;
Line 232... Line 230...
232
	}
230
	}
233
 
231
 
234
	mutex_lock(&dev->mode_config.idr_mutex);
232
	mutex_lock(&dev->mode_config.idr_mutex);
235
	ret = idr_get_new_above(&dev->mode_config.crtc_idr, obj, 1, &new_id);
233
	ret = idr_get_new_above(&dev->mode_config.crtc_idr, obj, 1, &new_id);
236
	mutex_unlock(&dev->mode_config.idr_mutex);
234
	mutex_unlock(&dev->mode_config.idr_mutex);
-
 
235
	if (ret == -EAGAIN)
-
 
236
        goto again;
Line 237... Line 237...
237
	if (ret == -EAGAIN)
237
	else if (ret)
238
        goto again;
238
		return ret;
239
 
239
 
240
	obj->id = new_id;
240
	obj->id = new_id;
Line 292... Line 292...
292
			 const struct drm_framebuffer_funcs *funcs)
292
			 const struct drm_framebuffer_funcs *funcs)
293
{
293
{
294
	int ret;
294
	int ret;
Line 295... Line 295...
295
 
295
 
296
	ret = drm_mode_object_get(dev, &fb->base, DRM_MODE_OBJECT_FB);
296
	ret = drm_mode_object_get(dev, &fb->base, DRM_MODE_OBJECT_FB);
297
	if (ret) {
297
	if (ret)
298
		return ret;
-
 
Line 299... Line 298...
299
	}
298
		return ret;
300
 
299
 
301
	fb->dev = dev;
300
	fb->dev = dev;
302
	fb->funcs = funcs;
301
	fb->funcs = funcs;
Line 318... Line 317...
318
 * it, setting it to NULL.
317
 * it, setting it to NULL.
319
 */
318
 */
320
void drm_framebuffer_cleanup(struct drm_framebuffer *fb)
319
void drm_framebuffer_cleanup(struct drm_framebuffer *fb)
321
{
320
{
322
	struct drm_device *dev = fb->dev;
321
	struct drm_device *dev = fb->dev;
323
	struct drm_crtc *crtc;
-
 
324
	struct drm_mode_set set;
-
 
325
	int ret;
-
 
326
 
322
	/*
327
	/* remove from any CRTC */
-
 
328
	list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
323
	 * This could be moved to drm_framebuffer_remove(), but for
329
		if (crtc->fb == fb) {
-
 
330
			/* should turn off the crtc */
324
	 * debugging is nice to keep around the list of fb's that are
331
			memset(&set, 0, sizeof(struct drm_mode_set));
325
	 * no longer associated w/ a drm_file but are not unreferenced
332
			set.crtc = crtc;
-
 
333
			set.fb = NULL;
-
 
334
			ret = crtc->funcs->set_config(&set);
326
	 * yet.  (i915 and omapdrm have debugfs files which will show
335
			if (ret)
327
	 * this.)
336
				DRM_ERROR("failed to reset crtc %p when fb was deleted\n", crtc);
-
 
337
	   }
328
	 */
338
	}
-
 
339
 
-
 
340
	drm_mode_object_put(dev, &fb->base);
329
	drm_mode_object_put(dev, &fb->base);
341
	list_del(&fb->head);
330
	list_del(&fb->head);
342
	dev->mode_config.num_fb--;
331
	dev->mode_config.num_fb--;
343
}
332
}
344
EXPORT_SYMBOL(drm_framebuffer_cleanup);
333
EXPORT_SYMBOL(drm_framebuffer_cleanup);
Line -... Line 334...
-
 
334
 
-
 
335
 
-
 
336
 
-
 
337
 
345
 
338
 
346
/**
339
/**
347
 * drm_crtc_init - Initialise a new CRTC object
340
 * drm_crtc_init - Initialise a new CRTC object
348
 * @dev: DRM device
341
 * @dev: DRM device
349
 * @crtc: CRTC object to init
342
 * @crtc: CRTC object to init
350
 * @funcs: callbacks for the new CRTC
343
 * @funcs: callbacks for the new CRTC
351
 *
344
 *
352
 * LOCKING:
345
 * LOCKING:
353
 * Caller must hold mode config lock.
346
 * Takes mode_config lock.
354
 *
347
 *
-
 
348
 * Inits a new object created as base part of an driver crtc object.
-
 
349
 *
-
 
350
 * RETURNS:
355
 * Inits a new object created as base part of an driver crtc object.
351
 * Zero on success, error code on failure.
356
 */
352
 */
357
void drm_crtc_init(struct drm_device *dev, struct drm_crtc *crtc,
353
int drm_crtc_init(struct drm_device *dev, struct drm_crtc *crtc,
358
		   const struct drm_crtc_funcs *funcs)
354
		   const struct drm_crtc_funcs *funcs)
-
 
355
{
-
 
356
	int ret;
359
{
357
 
360
	crtc->dev = dev;
358
	crtc->dev = dev;
-
 
359
	crtc->funcs = funcs;
Line 361... Line 360...
361
	crtc->funcs = funcs;
360
	crtc->invert_dimensions = false;
-
 
361
 
362
 
362
	mutex_lock(&dev->mode_config.mutex);
-
 
363
 
-
 
364
	ret = drm_mode_object_get(dev, &crtc->base, DRM_MODE_OBJECT_CRTC);
-
 
365
	if (ret)
-
 
366
		goto out;
Line 363... Line 367...
363
	mutex_lock(&dev->mode_config.mutex);
367
 
364
	drm_mode_object_get(dev, &crtc->base, DRM_MODE_OBJECT_CRTC);
368
	crtc->base.properties = &crtc->properties;
-
 
369
 
-
 
370
	list_add_tail(&crtc->head, &dev->mode_config.crtc_list);
365
 
371
	dev->mode_config.num_crtc++;
-
 
372
 
-
 
373
 out:
366
	list_add_tail(&crtc->head, &dev->mode_config.crtc_list);
374
	mutex_unlock(&dev->mode_config.mutex);
367
	dev->mode_config.num_crtc++;
375
 
Line 368... Line 376...
368
	mutex_unlock(&dev->mode_config.mutex);
376
	return ret;
369
}
377
}
Line 423... Line 431...
423
 */
431
 */
424
void drm_mode_remove(struct drm_connector *connector,
432
void drm_mode_remove(struct drm_connector *connector,
425
		     struct drm_display_mode *mode)
433
		     struct drm_display_mode *mode)
426
{
434
{
427
	list_del(&mode->head);
435
	list_del(&mode->head);
428
	kfree(mode);
436
	drm_mode_destroy(connector->dev, mode);
429
}
437
}
430
EXPORT_SYMBOL(drm_mode_remove);
438
EXPORT_SYMBOL(drm_mode_remove);
Line 431... Line 439...
431
 
439
 
432
/**
440
/**
Line 435... Line 443...
435
 * @connector: the connector to init
443
 * @connector: the connector to init
436
 * @funcs: callbacks for this connector
444
 * @funcs: callbacks for this connector
437
 * @name: user visible name of the connector
445
 * @name: user visible name of the connector
438
 *
446
 *
439
 * LOCKING:
447
 * LOCKING:
440
 * Caller must hold @dev's mode_config lock.
448
 * Takes mode config lock.
441
 *
449
 *
442
 * Initialises a preallocated connector. Connectors should be
450
 * Initialises a preallocated connector. Connectors should be
443
 * subclassed as part of driver connector objects.
451
 * subclassed as part of driver connector objects.
-
 
452
 *
-
 
453
 * RETURNS:
-
 
454
 * Zero on success, error code on failure.
444
 */
455
 */
445
void drm_connector_init(struct drm_device *dev,
456
int drm_connector_init(struct drm_device *dev,
446
		     struct drm_connector *connector,
457
		     struct drm_connector *connector,
447
		     const struct drm_connector_funcs *funcs,
458
		     const struct drm_connector_funcs *funcs,
448
		     int connector_type)
459
		     int connector_type)
449
{
460
{
-
 
461
	int ret;
-
 
462
 
450
	mutex_lock(&dev->mode_config.mutex);
463
	mutex_lock(&dev->mode_config.mutex);
Line -... Line 464...
-
 
464
 
-
 
465
	ret = drm_mode_object_get(dev, &connector->base, DRM_MODE_OBJECT_CONNECTOR);
-
 
466
	if (ret)
-
 
467
		goto out;
-
 
468
 
451
 
469
	connector->base.properties = &connector->properties;
452
	connector->dev = dev;
470
	connector->dev = dev;
453
	connector->funcs = funcs;
-
 
454
	drm_mode_object_get(dev, &connector->base, DRM_MODE_OBJECT_CONNECTOR);
471
	connector->funcs = funcs;
455
	connector->connector_type = connector_type;
472
	connector->connector_type = connector_type;
456
	connector->connector_type_id =
473
	connector->connector_type_id =
457
		++drm_connector_enum_list[connector_type].count; /* TODO */
474
		++drm_connector_enum_list[connector_type].count; /* TODO */
458
	INIT_LIST_HEAD(&connector->user_modes);
475
	INIT_LIST_HEAD(&connector->user_modes);
Line 461... Line 478...
461
	connector->edid_blob_ptr = NULL;
478
	connector->edid_blob_ptr = NULL;
Line 462... Line 479...
462
 
479
 
463
	list_add_tail(&connector->head, &dev->mode_config.connector_list);
480
	list_add_tail(&connector->head, &dev->mode_config.connector_list);
Line -... Line 481...
-
 
481
	dev->mode_config.num_connector++;
464
	dev->mode_config.num_connector++;
482
 
465
 
483
	if (connector_type != DRM_MODE_CONNECTOR_VIRTUAL)
-
 
484
	drm_connector_attach_property(connector,
Line 466... Line 485...
466
	drm_connector_attach_property(connector,
485
					      dev->mode_config.edid_property,
467
				      dev->mode_config.edid_property, 0);
486
					      0);
Line -... Line 487...
-
 
487
 
468
 
488
	drm_connector_attach_property(connector,
-
 
489
				      dev->mode_config.dpms_property, 0);
-
 
490
 
469
	drm_connector_attach_property(connector,
491
 out:
470
				      dev->mode_config.dpms_property, 0);
492
	mutex_unlock(&dev->mode_config.mutex);
Line 471... Line 493...
471
 
493
 
472
	mutex_unlock(&dev->mode_config.mutex);
494
	return ret;
473
}
495
}
474
EXPORT_SYMBOL(drm_connector_init);
496
EXPORT_SYMBOL(drm_connector_init);
475
 
497
 
476
/**
498
/**
477
 * drm_connector_cleanup - cleans up an initialised connector
499
 * drm_connector_cleanup - cleans up an initialised connector
478
 * @connector: connector to cleanup
500
 * @connector: connector to cleanup
479
 *
501
 *
480
 * LOCKING:
502
 * LOCKING:
481
 * Caller must hold @dev's mode_config lock.
503
 * Takes mode config lock.
Line 502... Line 524...
502
	dev->mode_config.num_connector--;
524
	dev->mode_config.num_connector--;
503
	mutex_unlock(&dev->mode_config.mutex);
525
	mutex_unlock(&dev->mode_config.mutex);
504
}
526
}
505
EXPORT_SYMBOL(drm_connector_cleanup);
527
EXPORT_SYMBOL(drm_connector_cleanup);
Line -... Line 528...
-
 
528
 
-
 
529
void drm_connector_unplug_all(struct drm_device *dev)
-
 
530
{
-
 
531
	struct drm_connector *connector;
-
 
532
 
-
 
533
	/* taking the mode config mutex ends up in a clash with sysfs */
-
 
534
//   list_for_each_entry(connector, &dev->mode_config.connector_list, head)
-
 
535
//       drm_sysfs_connector_remove(connector);
-
 
536
 
-
 
537
}
-
 
538
EXPORT_SYMBOL(drm_connector_unplug_all);
506
 
539
 
507
void drm_encoder_init(struct drm_device *dev,
540
int drm_encoder_init(struct drm_device *dev,
508
		      struct drm_encoder *encoder,
541
		      struct drm_encoder *encoder,
509
		      const struct drm_encoder_funcs *funcs,
542
		      const struct drm_encoder_funcs *funcs,
510
		      int encoder_type)
543
		      int encoder_type)
-
 
544
{
-
 
545
	int ret;
511
{
546
 
Line -... Line 547...
-
 
547
	mutex_lock(&dev->mode_config.mutex);
-
 
548
 
512
	mutex_lock(&dev->mode_config.mutex);
549
	ret = drm_mode_object_get(dev, &encoder->base, DRM_MODE_OBJECT_ENCODER);
Line 513... Line 550...
513
 
550
	if (ret)
514
	encoder->dev = dev;
551
		goto out;
515
 
552
 
Line 516... Line 553...
516
	drm_mode_object_get(dev, &encoder->base, DRM_MODE_OBJECT_ENCODER);
553
	encoder->dev = dev;
517
	encoder->encoder_type = encoder_type;
554
	encoder->encoder_type = encoder_type;
Line -... Line 555...
-
 
555
	encoder->funcs = funcs;
518
	encoder->funcs = funcs;
556
 
-
 
557
	list_add_tail(&encoder->head, &dev->mode_config.encoder_list);
-
 
558
	dev->mode_config.num_encoder++;
519
 
559
 
520
	list_add_tail(&encoder->head, &dev->mode_config.encoder_list);
560
 out:
Line 521... Line 561...
521
	dev->mode_config.num_encoder++;
561
	mutex_unlock(&dev->mode_config.mutex);
522
 
562
 
Line 533... Line 573...
533
	dev->mode_config.num_encoder--;
573
	dev->mode_config.num_encoder--;
534
	mutex_unlock(&dev->mode_config.mutex);
574
	mutex_unlock(&dev->mode_config.mutex);
535
}
575
}
536
EXPORT_SYMBOL(drm_encoder_cleanup);
576
EXPORT_SYMBOL(drm_encoder_cleanup);
Line -... Line 577...
-
 
577
 
-
 
578
int drm_plane_init(struct drm_device *dev, struct drm_plane *plane,
-
 
579
		   unsigned long possible_crtcs,
-
 
580
		   const struct drm_plane_funcs *funcs,
-
 
581
		   const uint32_t *formats, uint32_t format_count,
-
 
582
		   bool priv)
-
 
583
{
-
 
584
	int ret;
-
 
585
 
-
 
586
	mutex_lock(&dev->mode_config.mutex);
-
 
587
 
-
 
588
	ret = drm_mode_object_get(dev, &plane->base, DRM_MODE_OBJECT_PLANE);
-
 
589
	if (ret)
-
 
590
		goto out;
-
 
591
 
-
 
592
	plane->base.properties = &plane->properties;
-
 
593
	plane->dev = dev;
-
 
594
	plane->funcs = funcs;
-
 
595
	plane->format_types = kmalloc(sizeof(uint32_t) * format_count,
-
 
596
				      GFP_KERNEL);
-
 
597
	if (!plane->format_types) {
-
 
598
		DRM_DEBUG_KMS("out of memory when allocating plane\n");
-
 
599
		drm_mode_object_put(dev, &plane->base);
-
 
600
		ret = -ENOMEM;
-
 
601
		goto out;
-
 
602
	}
-
 
603
 
-
 
604
	memcpy(plane->format_types, formats, format_count * sizeof(uint32_t));
-
 
605
	plane->format_count = format_count;
-
 
606
	plane->possible_crtcs = possible_crtcs;
-
 
607
 
-
 
608
	/* private planes are not exposed to userspace, but depending on
-
 
609
	 * display hardware, might be convenient to allow sharing programming
-
 
610
	 * for the scanout engine with the crtc implementation.
-
 
611
	 */
-
 
612
	if (!priv) {
-
 
613
		list_add_tail(&plane->head, &dev->mode_config.plane_list);
-
 
614
		dev->mode_config.num_plane++;
-
 
615
	} else {
-
 
616
		INIT_LIST_HEAD(&plane->head);
-
 
617
	}
-
 
618
 
-
 
619
 out:
-
 
620
	mutex_unlock(&dev->mode_config.mutex);
-
 
621
 
-
 
622
	return ret;
-
 
623
}
-
 
624
EXPORT_SYMBOL(drm_plane_init);
-
 
625
 
-
 
626
void drm_plane_cleanup(struct drm_plane *plane)
-
 
627
{
-
 
628
	struct drm_device *dev = plane->dev;
-
 
629
 
-
 
630
	mutex_lock(&dev->mode_config.mutex);
-
 
631
	kfree(plane->format_types);
-
 
632
	drm_mode_object_put(dev, &plane->base);
-
 
633
	/* if not added to a list, it must be a private plane */
-
 
634
	if (!list_empty(&plane->head)) {
-
 
635
		list_del(&plane->head);
-
 
636
		dev->mode_config.num_plane--;
-
 
637
	}
-
 
638
	mutex_unlock(&dev->mode_config.mutex);
-
 
639
}
-
 
640
EXPORT_SYMBOL(drm_plane_cleanup);
537
 
641
 
538
/**
642
/**
539
 * drm_mode_create - create a new display mode
643
 * drm_mode_create - create a new display mode
540
 * @dev: DRM device
644
 * @dev: DRM device
541
 *
645
 *
Line 553... Line 657...
553
 
657
 
554
	nmode = kzalloc(sizeof(struct drm_display_mode), GFP_KERNEL);
658
	nmode = kzalloc(sizeof(struct drm_display_mode), GFP_KERNEL);
555
	if (!nmode)
659
	if (!nmode)
Line 556... Line 660...
556
		return NULL;
660
		return NULL;
-
 
661
 
-
 
662
	if (drm_mode_object_get(dev, &nmode->base, DRM_MODE_OBJECT_MODE)) {
-
 
663
		kfree(nmode);
-
 
664
		return NULL;
557
 
665
	}
558
	drm_mode_object_get(dev, &nmode->base, DRM_MODE_OBJECT_MODE);
666
 
559
	return nmode;
667
	return nmode;
Line 560... Line 668...
560
}
668
}
Line 570... Line 678...
570
 *
678
 *
571
 * Free @mode's unique identifier, then free it.
679
 * Free @mode's unique identifier, then free it.
572
 */
680
 */
573
void drm_mode_destroy(struct drm_device *dev, struct drm_display_mode *mode)
681
void drm_mode_destroy(struct drm_device *dev, struct drm_display_mode *mode)
574
{
682
{
-
 
683
	if (!mode)
-
 
684
		return;
-
 
685
 
575
	drm_mode_object_put(dev, &mode->base);
686
	drm_mode_object_put(dev, &mode->base);
Line 576... Line 687...
576
 
687
 
577
	kfree(mode);
688
	kfree(mode);
578
}
689
}
Line 579... Line 690...
579
EXPORT_SYMBOL(drm_mode_destroy);
690
EXPORT_SYMBOL(drm_mode_destroy);
580
 
691
 
581
static int drm_mode_create_standard_connector_properties(struct drm_device *dev)
692
static int drm_mode_create_standard_connector_properties(struct drm_device *dev)
582
{
693
{
583
	struct drm_property *edid;
-
 
Line 584... Line 694...
584
	struct drm_property *dpms;
694
	struct drm_property *edid;
585
	int i;
695
	struct drm_property *dpms;
586
 
696
 
587
	/*
697
	/*
588
	 * Standard properties (apply to all connectors)
698
	 * Standard properties (apply to all connectors)
589
	 */
699
	 */
590
	edid = drm_property_create(dev, DRM_MODE_PROP_BLOB |
700
	edid = drm_property_create(dev, DRM_MODE_PROP_BLOB |
Line 591... Line 701...
591
				   DRM_MODE_PROP_IMMUTABLE,
701
				   DRM_MODE_PROP_IMMUTABLE,
592
				   "EDID", 0);
702
				   "EDID", 0);
593
	dev->mode_config.edid_property = edid;
703
	dev->mode_config.edid_property = edid;
594
 
-
 
595
	dpms = drm_property_create(dev, DRM_MODE_PROP_ENUM,
-
 
596
				   "DPMS", ARRAY_SIZE(drm_dpms_enum_list));
704
 
Line 597... Line 705...
597
	for (i = 0; i < ARRAY_SIZE(drm_dpms_enum_list); i++)
705
	dpms = drm_property_create_enum(dev, 0,
598
		drm_property_add_enum(dpms, i, drm_dpms_enum_list[i].type,
706
				   "DPMS", drm_dpms_enum_list,
Line 610... Line 718...
610
 */
718
 */
611
int drm_mode_create_dvi_i_properties(struct drm_device *dev)
719
int drm_mode_create_dvi_i_properties(struct drm_device *dev)
612
{
720
{
613
	struct drm_property *dvi_i_selector;
721
	struct drm_property *dvi_i_selector;
614
	struct drm_property *dvi_i_subconnector;
722
	struct drm_property *dvi_i_subconnector;
615
	int i;
-
 
Line 616... Line 723...
616
 
723
 
617
	if (dev->mode_config.dvi_i_select_subconnector_property)
724
	if (dev->mode_config.dvi_i_select_subconnector_property)
Line 618... Line 725...
618
		return 0;
725
		return 0;
619
 
726
 
620
	dvi_i_selector =
727
	dvi_i_selector =
-
 
728
		drm_property_create_enum(dev, 0,
621
		drm_property_create(dev, DRM_MODE_PROP_ENUM,
729
				    "select subconnector",
622
				    "select subconnector",
-
 
623
				    ARRAY_SIZE(drm_dvi_i_select_enum_list));
-
 
624
	for (i = 0; i < ARRAY_SIZE(drm_dvi_i_select_enum_list); i++)
-
 
625
		drm_property_add_enum(dvi_i_selector, i,
-
 
626
				      drm_dvi_i_select_enum_list[i].type,
730
				    drm_dvi_i_select_enum_list,
Line 627... Line -...
627
				      drm_dvi_i_select_enum_list[i].name);
-
 
628
	dev->mode_config.dvi_i_select_subconnector_property = dvi_i_selector;
731
				    ARRAY_SIZE(drm_dvi_i_select_enum_list));
629
 
-
 
630
	dvi_i_subconnector =
732
	dev->mode_config.dvi_i_select_subconnector_property = dvi_i_selector;
-
 
733
 
631
		drm_property_create(dev, DRM_MODE_PROP_ENUM |
734
	dvi_i_subconnector = drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
632
				    DRM_MODE_PROP_IMMUTABLE,
-
 
633
				    "subconnector",
-
 
634
				    ARRAY_SIZE(drm_dvi_i_subconnector_enum_list));
-
 
635
	for (i = 0; i < ARRAY_SIZE(drm_dvi_i_subconnector_enum_list); i++)
-
 
636
		drm_property_add_enum(dvi_i_subconnector, i,
735
				    "subconnector",
Line 637... Line 736...
637
				      drm_dvi_i_subconnector_enum_list[i].type,
736
				    drm_dvi_i_subconnector_enum_list,
638
				      drm_dvi_i_subconnector_enum_list[i].name);
737
				    ARRAY_SIZE(drm_dvi_i_subconnector_enum_list));
639
	dev->mode_config.dvi_i_subconnector_property = dvi_i_subconnector;
738
	dev->mode_config.dvi_i_subconnector_property = dvi_i_subconnector;
Line 664... Line 763...
664
		return 0;
763
		return 0;
Line 665... Line 764...
665
 
764
 
666
	/*
765
	/*
667
	 * Basic connector properties
766
	 * Basic connector properties
668
	 */
767
	 */
669
	tv_selector = drm_property_create(dev, DRM_MODE_PROP_ENUM,
768
	tv_selector = drm_property_create_enum(dev, 0,
-
 
769
					  "select subconnector",
670
					  "select subconnector",
770
					  drm_tv_select_enum_list,
671
					  ARRAY_SIZE(drm_tv_select_enum_list));
-
 
672
	for (i = 0; i < ARRAY_SIZE(drm_tv_select_enum_list); i++)
-
 
673
		drm_property_add_enum(tv_selector, i,
-
 
674
				      drm_tv_select_enum_list[i].type,
-
 
675
				      drm_tv_select_enum_list[i].name);
771
					  ARRAY_SIZE(drm_tv_select_enum_list));
Line 676... Line 772...
676
	dev->mode_config.tv_select_subconnector_property = tv_selector;
772
	dev->mode_config.tv_select_subconnector_property = tv_selector;
677
 
773
 
678
	tv_subconnector =
774
	tv_subconnector =
-
 
775
		drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
679
		drm_property_create(dev, DRM_MODE_PROP_ENUM |
776
				    "subconnector",
680
				    DRM_MODE_PROP_IMMUTABLE, "subconnector",
-
 
681
				    ARRAY_SIZE(drm_tv_subconnector_enum_list));
-
 
682
	for (i = 0; i < ARRAY_SIZE(drm_tv_subconnector_enum_list); i++)
-
 
683
		drm_property_add_enum(tv_subconnector, i,
-
 
684
				      drm_tv_subconnector_enum_list[i].type,
777
				    drm_tv_subconnector_enum_list,
Line 685... Line 778...
685
				      drm_tv_subconnector_enum_list[i].name);
778
				    ARRAY_SIZE(drm_tv_subconnector_enum_list));
686
	dev->mode_config.tv_subconnector_property = tv_subconnector;
779
	dev->mode_config.tv_subconnector_property = tv_subconnector;
687
 
780
 
688
	/*
781
	/*
689
	 * Other, TV specific properties: margins & TV modes.
782
	 * Other, TV specific properties: margins & TV modes.
690
	 */
-
 
691
	dev->mode_config.tv_left_margin_property =
-
 
692
		drm_property_create(dev, DRM_MODE_PROP_RANGE,
-
 
Line 693... Line 783...
693
				    "left margin", 2);
783
	 */
694
	dev->mode_config.tv_left_margin_property->values[0] = 0;
784
	dev->mode_config.tv_left_margin_property =
695
	dev->mode_config.tv_left_margin_property->values[1] = 100;
-
 
696
 
-
 
697
	dev->mode_config.tv_right_margin_property =
-
 
Line 698... Line 785...
698
		drm_property_create(dev, DRM_MODE_PROP_RANGE,
785
		drm_property_create_range(dev, 0, "left margin", 0, 100);
699
				    "right margin", 2);
786
 
700
	dev->mode_config.tv_right_margin_property->values[0] = 0;
-
 
701
	dev->mode_config.tv_right_margin_property->values[1] = 100;
-
 
702
 
-
 
Line 703... Line 787...
703
	dev->mode_config.tv_top_margin_property =
787
	dev->mode_config.tv_right_margin_property =
704
		drm_property_create(dev, DRM_MODE_PROP_RANGE,
788
		drm_property_create_range(dev, 0, "right margin", 0, 100);
705
				    "top margin", 2);
-
 
706
	dev->mode_config.tv_top_margin_property->values[0] = 0;
-
 
707
	dev->mode_config.tv_top_margin_property->values[1] = 100;
-
 
Line 708... Line 789...
708
 
789
 
709
	dev->mode_config.tv_bottom_margin_property =
790
	dev->mode_config.tv_top_margin_property =
710
		drm_property_create(dev, DRM_MODE_PROP_RANGE,
791
		drm_property_create_range(dev, 0, "top margin", 0, 100);
711
				    "bottom margin", 2);
792
 
712
	dev->mode_config.tv_bottom_margin_property->values[0] = 0;
793
	dev->mode_config.tv_bottom_margin_property =
713
	dev->mode_config.tv_bottom_margin_property->values[1] = 100;
794
		drm_property_create_range(dev, 0, "bottom margin", 0, 100);
Line 714... Line 795...
714
 
795
 
715
	dev->mode_config.tv_mode_property =
796
	dev->mode_config.tv_mode_property =
716
		drm_property_create(dev, DRM_MODE_PROP_ENUM,
-
 
717
				    "mode", num_modes);
-
 
718
	for (i = 0; i < num_modes; i++)
-
 
Line 719... Line 797...
719
		drm_property_add_enum(dev->mode_config.tv_mode_property, i,
797
		drm_property_create(dev, DRM_MODE_PROP_ENUM,
720
				      i, modes[i]);
798
				    "mode", num_modes);
721
 
-
 
722
	dev->mode_config.tv_brightness_property =
-
 
723
		drm_property_create(dev, DRM_MODE_PROP_RANGE,
-
 
Line 724... Line 799...
724
				    "brightness", 2);
799
	for (i = 0; i < num_modes; i++)
725
	dev->mode_config.tv_brightness_property->values[0] = 0;
800
		drm_property_add_enum(dev->mode_config.tv_mode_property, i,
726
	dev->mode_config.tv_brightness_property->values[1] = 100;
-
 
727
 
-
 
728
	dev->mode_config.tv_contrast_property =
-
 
Line 729... Line 801...
729
		drm_property_create(dev, DRM_MODE_PROP_RANGE,
801
				      i, modes[i]);
730
				    "contrast", 2);
802
 
731
	dev->mode_config.tv_contrast_property->values[0] = 0;
-
 
732
	dev->mode_config.tv_contrast_property->values[1] = 100;
-
 
733
 
-
 
Line 734... Line 803...
734
	dev->mode_config.tv_flicker_reduction_property =
803
	dev->mode_config.tv_brightness_property =
735
		drm_property_create(dev, DRM_MODE_PROP_RANGE,
804
		drm_property_create_range(dev, 0, "brightness", 0, 100);
736
				    "flicker reduction", 2);
-
 
737
	dev->mode_config.tv_flicker_reduction_property->values[0] = 0;
-
 
738
	dev->mode_config.tv_flicker_reduction_property->values[1] = 100;
-
 
Line 739... Line 805...
739
 
805
 
740
	dev->mode_config.tv_overscan_property =
806
	dev->mode_config.tv_contrast_property =
741
		drm_property_create(dev, DRM_MODE_PROP_RANGE,
-
 
742
				    "overscan", 2);
-
 
743
	dev->mode_config.tv_overscan_property->values[0] = 0;
-
 
Line 744... Line 807...
744
	dev->mode_config.tv_overscan_property->values[1] = 100;
807
		drm_property_create_range(dev, 0, "contrast", 0, 100);
745
 
808
 
746
	dev->mode_config.tv_saturation_property =
809
	dev->mode_config.tv_flicker_reduction_property =
Line 767... Line 830...
767
 * connectors.
830
 * connectors.
768
 */
831
 */
769
int drm_mode_create_scaling_mode_property(struct drm_device *dev)
832
int drm_mode_create_scaling_mode_property(struct drm_device *dev)
770
{
833
{
771
	struct drm_property *scaling_mode;
834
	struct drm_property *scaling_mode;
772
	int i;
-
 
Line 773... Line 835...
773
 
835
 
774
	if (dev->mode_config.scaling_mode_property)
836
	if (dev->mode_config.scaling_mode_property)
Line 775... Line 837...
775
		return 0;
837
		return 0;
776
 
838
 
-
 
839
	scaling_mode =
777
	scaling_mode =
840
		drm_property_create_enum(dev, 0, "scaling mode",
778
		drm_property_create(dev, DRM_MODE_PROP_ENUM, "scaling mode",
-
 
779
				    ARRAY_SIZE(drm_scaling_mode_enum_list));
-
 
780
	for (i = 0; i < ARRAY_SIZE(drm_scaling_mode_enum_list); i++)
-
 
781
		drm_property_add_enum(scaling_mode, i,
-
 
Line 782... Line 841...
782
				      drm_scaling_mode_enum_list[i].type,
841
				drm_scaling_mode_enum_list,
Line 783... Line 842...
783
				      drm_scaling_mode_enum_list[i].name);
842
				    ARRAY_SIZE(drm_scaling_mode_enum_list));
784
 
843
 
Line 796... Line 855...
796
 * connectors.
855
 * connectors.
797
 */
856
 */
798
int drm_mode_create_dithering_property(struct drm_device *dev)
857
int drm_mode_create_dithering_property(struct drm_device *dev)
799
{
858
{
800
	struct drm_property *dithering_mode;
859
	struct drm_property *dithering_mode;
801
	int i;
-
 
Line 802... Line 860...
802
 
860
 
803
	if (dev->mode_config.dithering_mode_property)
861
	if (dev->mode_config.dithering_mode_property)
Line 804... Line 862...
804
		return 0;
862
		return 0;
805
 
863
 
-
 
864
	dithering_mode =
806
	dithering_mode =
865
		drm_property_create_enum(dev, 0, "dithering",
807
		drm_property_create(dev, DRM_MODE_PROP_ENUM, "dithering",
-
 
808
				    ARRAY_SIZE(drm_dithering_mode_enum_list));
-
 
809
	for (i = 0; i < ARRAY_SIZE(drm_dithering_mode_enum_list); i++)
-
 
810
		drm_property_add_enum(dithering_mode, i,
-
 
811
				      drm_dithering_mode_enum_list[i].type,
866
				drm_dithering_mode_enum_list,
Line 812... Line 867...
812
				      drm_dithering_mode_enum_list[i].name);
867
				    ARRAY_SIZE(drm_dithering_mode_enum_list));
813
	dev->mode_config.dithering_mode_property = dithering_mode;
868
	dev->mode_config.dithering_mode_property = dithering_mode;
814
 
869
 
Line 824... Line 879...
824
 * connectors.
879
 * connectors.
825
 */
880
 */
826
int drm_mode_create_dirty_info_property(struct drm_device *dev)
881
int drm_mode_create_dirty_info_property(struct drm_device *dev)
827
{
882
{
828
	struct drm_property *dirty_info;
883
	struct drm_property *dirty_info;
829
	int i;
-
 
Line 830... Line 884...
830
 
884
 
831
	if (dev->mode_config.dirty_info_property)
885
	if (dev->mode_config.dirty_info_property)
Line 832... Line 886...
832
		return 0;
886
		return 0;
833
 
887
 
834
	dirty_info =
-
 
835
		drm_property_create(dev, DRM_MODE_PROP_ENUM |
888
	dirty_info =
-
 
889
		drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
836
				    DRM_MODE_PROP_IMMUTABLE,
890
				    "dirty",
837
				    "dirty",
-
 
838
				    ARRAY_SIZE(drm_dirty_info_enum_list));
-
 
839
	for (i = 0; i < ARRAY_SIZE(drm_dirty_info_enum_list); i++)
-
 
840
		drm_property_add_enum(dirty_info, i,
-
 
841
				      drm_dirty_info_enum_list[i].type,
891
				    drm_dirty_info_enum_list,
Line 842... Line 892...
842
				      drm_dirty_info_enum_list[i].name);
892
				    ARRAY_SIZE(drm_dirty_info_enum_list));
843
	dev->mode_config.dirty_info_property = dirty_info;
893
	dev->mode_config.dirty_info_property = dirty_info;
844
 
894
 
Line 864... Line 914...
864
	INIT_LIST_HEAD(&dev->mode_config.crtc_list);
914
	INIT_LIST_HEAD(&dev->mode_config.crtc_list);
865
	INIT_LIST_HEAD(&dev->mode_config.connector_list);
915
	INIT_LIST_HEAD(&dev->mode_config.connector_list);
866
	INIT_LIST_HEAD(&dev->mode_config.encoder_list);
916
	INIT_LIST_HEAD(&dev->mode_config.encoder_list);
867
	INIT_LIST_HEAD(&dev->mode_config.property_list);
917
	INIT_LIST_HEAD(&dev->mode_config.property_list);
868
	INIT_LIST_HEAD(&dev->mode_config.property_blob_list);
918
	INIT_LIST_HEAD(&dev->mode_config.property_blob_list);
-
 
919
	INIT_LIST_HEAD(&dev->mode_config.plane_list);
869
	idr_init(&dev->mode_config.crtc_idr);
920
	idr_init(&dev->mode_config.crtc_idr);
Line 870... Line 921...
870
 
921
 
871
	mutex_lock(&dev->mode_config.mutex);
922
	mutex_lock(&dev->mode_config.mutex);
872
	drm_mode_create_standard_connector_properties(dev);
923
	drm_mode_create_standard_connector_properties(dev);
Line 920... Line 971...
920
		group->id_list[group->num_crtcs + group->num_encoders +
971
		group->id_list[group->num_crtcs + group->num_encoders +
921
			       group->num_connectors++] = connector->base.id;
972
			       group->num_connectors++] = connector->base.id;
Line 922... Line 973...
922
 
973
 
923
	return 0;
974
	return 0;
-
 
975
}
Line 924... Line 976...
924
}
976
EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
925
 
977
 
926
/**
978
/**
927
 * drm_mode_config_cleanup - free up DRM mode_config info
979
 * drm_mode_config_cleanup - free up DRM mode_config info
Line 940... Line 992...
940
	struct drm_connector *connector, *ot;
992
	struct drm_connector *connector, *ot;
941
	struct drm_crtc *crtc, *ct;
993
	struct drm_crtc *crtc, *ct;
942
	struct drm_encoder *encoder, *enct;
994
	struct drm_encoder *encoder, *enct;
943
	struct drm_framebuffer *fb, *fbt;
995
	struct drm_framebuffer *fb, *fbt;
944
	struct drm_property *property, *pt;
996
	struct drm_property *property, *pt;
-
 
997
	struct drm_plane *plane, *plt;
Line 945... Line 998...
945
 
998
 
946
	list_for_each_entry_safe(encoder, enct, &dev->mode_config.encoder_list,
999
	list_for_each_entry_safe(encoder, enct, &dev->mode_config.encoder_list,
947
				 head) {
1000
				 head) {
948
		encoder->funcs->destroy(encoder);
1001
		encoder->funcs->destroy(encoder);
Line 956... Line 1009...
956
	list_for_each_entry_safe(property, pt, &dev->mode_config.property_list,
1009
	list_for_each_entry_safe(property, pt, &dev->mode_config.property_list,
957
				 head) {
1010
				 head) {
958
		drm_property_destroy(dev, property);
1011
		drm_property_destroy(dev, property);
959
	}
1012
	}
Line 960... Line 1013...
960
 
1013
 
-
 
1014
	list_for_each_entry_safe(plane, plt, &dev->mode_config.plane_list,
961
	list_for_each_entry_safe(fb, fbt, &dev->mode_config.fb_list, head) {
1015
				 head) {
962
		fb->funcs->destroy(fb);
1016
		plane->funcs->destroy(plane);
Line 963... Line 1017...
963
	}
1017
	}
964
 
1018
 
965
	list_for_each_entry_safe(crtc, ct, &dev->mode_config.crtc_list, head) {
1019
	list_for_each_entry_safe(crtc, ct, &dev->mode_config.crtc_list, head) {
Line -... Line 1020...
-
 
1020
		crtc->funcs->destroy(crtc);
-
 
1021
	}
966
		crtc->funcs->destroy(crtc);
1022
 
967
	}
1023
	idr_remove_all(&dev->mode_config.crtc_idr);
Line 968... Line 1024...
968
 
1024
	idr_destroy(&dev->mode_config.crtc_idr);
969
}
1025
}
Line 978... Line 1034...
978
 * None.
1034
 * None.
979
 *
1035
 *
980
 * Convert a drm_display_mode into a drm_mode_modeinfo structure to return to
1036
 * Convert a drm_display_mode into a drm_mode_modeinfo structure to return to
981
 * the user.
1037
 * the user.
982
 */
1038
 */
983
void drm_crtc_convert_to_umode(struct drm_mode_modeinfo *out,
1039
static void drm_crtc_convert_to_umode(struct drm_mode_modeinfo *out,
984
			       struct drm_display_mode *in)
1040
				      const struct drm_display_mode *in)
985
{
1041
{
-
 
1042
	WARN(in->hdisplay > USHRT_MAX || in->hsync_start > USHRT_MAX ||
-
 
1043
	     in->hsync_end > USHRT_MAX || in->htotal > USHRT_MAX ||
-
 
1044
	     in->hskew > USHRT_MAX || in->vdisplay > USHRT_MAX ||
-
 
1045
	     in->vsync_start > USHRT_MAX || in->vsync_end > USHRT_MAX ||
-
 
1046
	     in->vtotal > USHRT_MAX || in->vscan > USHRT_MAX,
-
 
1047
	     "timing values too large for mode info\n");
-
 
1048
 
986
	out->clock = in->clock;
1049
	out->clock = in->clock;
987
	out->hdisplay = in->hdisplay;
1050
	out->hdisplay = in->hdisplay;
988
	out->hsync_start = in->hsync_start;
1051
	out->hsync_start = in->hsync_start;
989
	out->hsync_end = in->hsync_end;
1052
	out->hsync_end = in->hsync_end;
990
	out->htotal = in->htotal;
1053
	out->htotal = in->htotal;
Line 1009... Line 1072...
1009
 * LOCKING:
1072
 * LOCKING:
1010
 * None.
1073
 * None.
1011
 *
1074
 *
1012
 * Convert a drm_mode_modeinfo into a drm_display_mode structure to return to
1075
 * Convert a drm_mode_modeinfo into a drm_display_mode structure to return to
1013
 * the caller.
1076
 * the caller.
-
 
1077
 *
-
 
1078
 * RETURNS:
-
 
1079
 * Zero on success, errno on failure.
1014
 */
1080
 */
1015
void drm_crtc_convert_umode(struct drm_display_mode *out,
1081
static int drm_crtc_convert_umode(struct drm_display_mode *out,
1016
			    struct drm_mode_modeinfo *in)
1082
				  const struct drm_mode_modeinfo *in)
1017
{
1083
{
-
 
1084
	if (in->clock > INT_MAX || in->vrefresh > INT_MAX)
-
 
1085
		return -ERANGE;
-
 
1086
 
1018
	out->clock = in->clock;
1087
	out->clock = in->clock;
1019
	out->hdisplay = in->hdisplay;
1088
	out->hdisplay = in->hdisplay;
1020
	out->hsync_start = in->hsync_start;
1089
	out->hsync_start = in->hsync_start;
1021
	out->hsync_end = in->hsync_end;
1090
	out->hsync_end = in->hsync_end;
1022
	out->htotal = in->htotal;
1091
	out->htotal = in->htotal;
Line 1029... Line 1098...
1029
	out->vrefresh = in->vrefresh;
1098
	out->vrefresh = in->vrefresh;
1030
	out->flags = in->flags;
1099
	out->flags = in->flags;
1031
	out->type = in->type;
1100
	out->type = in->type;
1032
	strncpy(out->name, in->name, DRM_DISPLAY_MODE_LEN);
1101
	strncpy(out->name, in->name, DRM_DISPLAY_MODE_LEN);
1033
	out->name[DRM_DISPLAY_MODE_LEN-1] = 0;
1102
	out->name[DRM_DISPLAY_MODE_LEN-1] = 0;
-
 
1103
 
-
 
1104
	return 0;
1034
}
1105
}
Line 1035... Line 1106...
1035
 
1106
 
1036
 
1107
 
Line 1229... Line 1300...
1229
 * @filp: file * from the ioctl
1300
 * @filp: file * from the ioctl
1230
 * @cmd: cmd from ioctl
1301
 * @cmd: cmd from ioctl
1231
 * @arg: arg from ioctl
1302
 * @arg: arg from ioctl
1232
 *
1303
 *
1233
 * LOCKING:
1304
 * LOCKING:
1234
 * Caller? (FIXME)
1305
 * Takes mode config lock.
1235
 *
1306
 *
1236
 * Construct a CRTC configuration structure to return to the user.
1307
 * Construct a CRTC configuration structure to return to the user.
1237
 *
1308
 *
1238
 * Called by the user via ioctl.
1309
 * Called by the user via ioctl.
1239
 *
1310
 *
Line 1289... Line 1360...
1289
 * @filp: file * from the ioctl
1360
 * @filp: file * from the ioctl
1290
 * @cmd: cmd from ioctl
1361
 * @cmd: cmd from ioctl
1291
 * @arg: arg from ioctl
1362
 * @arg: arg from ioctl
1292
 *
1363
 *
1293
 * LOCKING:
1364
 * LOCKING:
1294
 * Caller? (FIXME)
1365
 * Takes mode config lock.
1295
 *
1366
 *
1296
 * Construct a connector configuration structure to return to the user.
1367
 * Construct a connector configuration structure to return to the user.
1297
 *
1368
 *
1298
 * Called by the user via ioctl.
1369
 * Called by the user via ioctl.
1299
 *
1370
 *
Line 1334... Line 1405...
1334
		ret = -EINVAL;
1405
		ret = -EINVAL;
1335
		goto out;
1406
		goto out;
1336
	}
1407
	}
1337
	connector = obj_to_connector(obj);
1408
	connector = obj_to_connector(obj);
Line 1338... Line -...
1338
 
-
 
1339
	for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
1409
 
1340
		if (connector->property_ids[i] != 0) {
-
 
1341
			props_count++;
-
 
1342
		}
-
 
Line 1343... Line 1410...
1343
	}
1410
	props_count = connector->properties.count;
1344
 
1411
 
1345
	for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
1412
	for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
1346
		if (connector->encoder_ids[i] != 0) {
1413
		if (connector->encoder_ids[i] != 0) {
Line 1374... Line 1441...
1374
	 * This ioctl is called twice, once to determine how much space is
1441
	 * This ioctl is called twice, once to determine how much space is
1375
	 * needed, and the 2nd time to fill it.
1442
	 * needed, and the 2nd time to fill it.
1376
	 */
1443
	 */
1377
	if ((out_resp->count_modes >= mode_count) && mode_count) {
1444
	if ((out_resp->count_modes >= mode_count) && mode_count) {
1378
		copied = 0;
1445
		copied = 0;
1379
		mode_ptr = (struct drm_mode_modeinfo *)(unsigned long)out_resp->modes_ptr;
1446
		mode_ptr = (struct drm_mode_modeinfo __user *)(unsigned long)out_resp->modes_ptr;
1380
		list_for_each_entry(mode, &connector->modes, head) {
1447
		list_for_each_entry(mode, &connector->modes, head) {
1381
			drm_crtc_convert_to_umode(&u_mode, mode);
1448
			drm_crtc_convert_to_umode(&u_mode, mode);
1382
			if (copy_to_user(mode_ptr + copied,
1449
			if (copy_to_user(mode_ptr + copied,
1383
					 &u_mode, sizeof(u_mode))) {
1450
					 &u_mode, sizeof(u_mode))) {
1384
				ret = -EFAULT;
1451
				ret = -EFAULT;
Line 1389... Line 1456...
1389
	}
1456
	}
1390
	out_resp->count_modes = mode_count;
1457
	out_resp->count_modes = mode_count;
Line 1391... Line 1458...
1391
 
1458
 
1392
	if ((out_resp->count_props >= props_count) && props_count) {
1459
	if ((out_resp->count_props >= props_count) && props_count) {
1393
		copied = 0;
1460
		copied = 0;
1394
		prop_ptr = (uint32_t *)(unsigned long)(out_resp->props_ptr);
1461
		prop_ptr = (uint32_t __user *)(unsigned long)(out_resp->props_ptr);
1395
		prop_values = (uint64_t *)(unsigned long)(out_resp->prop_values_ptr);
1462
		prop_values = (uint64_t __user *)(unsigned long)(out_resp->prop_values_ptr);
1396
		for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
-
 
1397
			if (connector->property_ids[i] != 0) {
1463
		for (i = 0; i < connector->properties.count; i++) {
1398
				if (put_user(connector->property_ids[i],
1464
			if (put_user(connector->properties.ids[i],
1399
					     prop_ptr + copied)) {
1465
					     prop_ptr + copied)) {
1400
					ret = -EFAULT;
1466
					ret = -EFAULT;
1401
					goto out;
1467
					goto out;
Line 1402... Line 1468...
1402
				}
1468
				}
1403
 
1469
 
1404
				if (put_user(connector->property_values[i],
1470
			if (put_user(connector->properties.values[i],
1405
					     prop_values + copied)) {
1471
					     prop_values + copied)) {
1406
					ret = -EFAULT;
1472
					ret = -EFAULT;
1407
					goto out;
1473
					goto out;
1408
				}
1474
				}
1409
				copied++;
1475
				copied++;
1410
			}
-
 
1411
		}
1476
			}
Line 1412... Line 1477...
1412
	}
1477
		}
1413
	out_resp->count_props = props_count;
1478
	out_resp->count_props = props_count;
1414
 
1479
 
1415
	if ((out_resp->count_encoders >= encoders_count) && encoders_count) {
1480
	if ((out_resp->count_encoders >= encoders_count) && encoders_count) {
1416
		copied = 0;
1481
		copied = 0;
1417
		encoder_ptr = (uint32_t *)(unsigned long)(out_resp->encoders_ptr);
1482
		encoder_ptr = (uint32_t __user *)(unsigned long)(out_resp->encoders_ptr);
1418
		for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
1483
		for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
1419
			if (connector->encoder_ids[i] != 0) {
1484
			if (connector->encoder_ids[i] != 0) {
Line 1466... Line 1531...
1466
	mutex_unlock(&dev->mode_config.mutex);
1531
	mutex_unlock(&dev->mode_config.mutex);
1467
	return ret;
1532
	return ret;
1468
}
1533
}
Line 1469... Line 1534...
1469
 
1534
 
-
 
1535
/**
-
 
1536
 * drm_mode_getplane_res - get plane info
-
 
1537
 * @dev: DRM device
-
 
1538
 * @data: ioctl data
-
 
1539
 * @file_priv: DRM file info
-
 
1540
 *
-
 
1541
 * LOCKING:
-
 
1542
 * Takes mode config lock.
-
 
1543
 *
-
 
1544
 * Return an plane count and set of IDs.
-
 
1545
 */
-
 
1546
int drm_mode_getplane_res(struct drm_device *dev, void *data,
-
 
1547
			    struct drm_file *file_priv)
-
 
1548
{
-
 
1549
	struct drm_mode_get_plane_res *plane_resp = data;
-
 
1550
	struct drm_mode_config *config;
-
 
1551
	struct drm_plane *plane;
-
 
1552
	uint32_t __user *plane_ptr;
-
 
1553
	int copied = 0, ret = 0;
-
 
1554
 
-
 
1555
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
-
 
1556
		return -EINVAL;
-
 
1557
 
-
 
1558
	mutex_lock(&dev->mode_config.mutex);
-
 
1559
	config = &dev->mode_config;
-
 
1560
 
-
 
1561
	/*
-
 
1562
	 * This ioctl is called twice, once to determine how much space is
-
 
1563
	 * needed, and the 2nd time to fill it.
-
 
1564
	 */
-
 
1565
	if (config->num_plane &&
-
 
1566
	    (plane_resp->count_planes >= config->num_plane)) {
-
 
1567
		plane_ptr = (uint32_t __user *)(unsigned long)plane_resp->plane_id_ptr;
-
 
1568
 
-
 
1569
		list_for_each_entry(plane, &config->plane_list, head) {
-
 
1570
			if (put_user(plane->base.id, plane_ptr + copied)) {
-
 
1571
				ret = -EFAULT;
-
 
1572
				goto out;
-
 
1573
			}
-
 
1574
			copied++;
-
 
1575
		}
-
 
1576
	}
-
 
1577
	plane_resp->count_planes = config->num_plane;
-
 
1578
 
-
 
1579
out:
-
 
1580
	mutex_unlock(&dev->mode_config.mutex);
-
 
1581
	return ret;
-
 
1582
}
-
 
1583
 
-
 
1584
/**
-
 
1585
 * drm_mode_getplane - get plane info
-
 
1586
 * @dev: DRM device
-
 
1587
 * @data: ioctl data
-
 
1588
 * @file_priv: DRM file info
-
 
1589
 *
-
 
1590
 * LOCKING:
-
 
1591
 * Takes mode config lock.
-
 
1592
 *
-
 
1593
 * Return plane info, including formats supported, gamma size, any
-
 
1594
 * current fb, etc.
-
 
1595
 */
-
 
1596
int drm_mode_getplane(struct drm_device *dev, void *data,
-
 
1597
			struct drm_file *file_priv)
-
 
1598
{
-
 
1599
	struct drm_mode_get_plane *plane_resp = data;
-
 
1600
	struct drm_mode_object *obj;
-
 
1601
	struct drm_plane *plane;
-
 
1602
	uint32_t __user *format_ptr;
-
 
1603
	int ret = 0;
-
 
1604
 
-
 
1605
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
-
 
1606
		return -EINVAL;
-
 
1607
 
-
 
1608
	mutex_lock(&dev->mode_config.mutex);
-
 
1609
	obj = drm_mode_object_find(dev, plane_resp->plane_id,
-
 
1610
				   DRM_MODE_OBJECT_PLANE);
-
 
1611
	if (!obj) {
-
 
1612
		ret = -ENOENT;
-
 
1613
		goto out;
-
 
1614
	}
-
 
1615
	plane = obj_to_plane(obj);
-
 
1616
 
-
 
1617
	if (plane->crtc)
-
 
1618
		plane_resp->crtc_id = plane->crtc->base.id;
-
 
1619
	else
-
 
1620
		plane_resp->crtc_id = 0;
-
 
1621
 
-
 
1622
	if (plane->fb)
-
 
1623
		plane_resp->fb_id = plane->fb->base.id;
-
 
1624
	else
-
 
1625
		plane_resp->fb_id = 0;
-
 
1626
 
-
 
1627
	plane_resp->plane_id = plane->base.id;
-
 
1628
	plane_resp->possible_crtcs = plane->possible_crtcs;
-
 
1629
	plane_resp->gamma_size = plane->gamma_size;
-
 
1630
 
-
 
1631
	/*
-
 
1632
	 * This ioctl is called twice, once to determine how much space is
-
 
1633
	 * needed, and the 2nd time to fill it.
-
 
1634
	 */
-
 
1635
	if (plane->format_count &&
-
 
1636
	    (plane_resp->count_format_types >= plane->format_count)) {
-
 
1637
		format_ptr = (uint32_t __user *)(unsigned long)plane_resp->format_type_ptr;
-
 
1638
		if (copy_to_user(format_ptr,
-
 
1639
				 plane->format_types,
-
 
1640
				 sizeof(uint32_t) * plane->format_count)) {
-
 
1641
			ret = -EFAULT;
-
 
1642
			goto out;
-
 
1643
		}
-
 
1644
	}
-
 
1645
	plane_resp->count_format_types = plane->format_count;
-
 
1646
 
-
 
1647
out:
-
 
1648
	mutex_unlock(&dev->mode_config.mutex);
-
 
1649
	return ret;
-
 
1650
}
-
 
1651
 
-
 
1652
/**
-
 
1653
 * drm_mode_setplane - set up or tear down an plane
-
 
1654
 * @dev: DRM device
-
 
1655
 * @data: ioctl data*
-
 
1656
 * @file_prive: DRM file info
-
 
1657
 *
-
 
1658
 * LOCKING:
-
 
1659
 * Takes mode config lock.
-
 
1660
 *
-
 
1661
 * Set plane info, including placement, fb, scaling, and other factors.
-
 
1662
 * Or pass a NULL fb to disable.
-
 
1663
 */
-
 
1664
int drm_mode_setplane(struct drm_device *dev, void *data,
-
 
1665
			struct drm_file *file_priv)
-
 
1666
{
-
 
1667
	struct drm_mode_set_plane *plane_req = data;
-
 
1668
	struct drm_mode_object *obj;
-
 
1669
	struct drm_plane *plane;
-
 
1670
	struct drm_crtc *crtc;
-
 
1671
	struct drm_framebuffer *fb;
-
 
1672
	int ret = 0;
-
 
1673
	unsigned int fb_width, fb_height;
-
 
1674
	int i;
-
 
1675
 
-
 
1676
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
-
 
1677
		return -EINVAL;
-
 
1678
 
-
 
1679
	mutex_lock(&dev->mode_config.mutex);
-
 
1680
 
-
 
1681
	/*
-
 
1682
	 * First, find the plane, crtc, and fb objects.  If not available,
-
 
1683
	 * we don't bother to call the driver.
-
 
1684
	 */
-
 
1685
	obj = drm_mode_object_find(dev, plane_req->plane_id,
-
 
1686
				   DRM_MODE_OBJECT_PLANE);
-
 
1687
	if (!obj) {
-
 
1688
		DRM_DEBUG_KMS("Unknown plane ID %d\n",
-
 
1689
			      plane_req->plane_id);
-
 
1690
		ret = -ENOENT;
-
 
1691
		goto out;
-
 
1692
	}
-
 
1693
	plane = obj_to_plane(obj);
-
 
1694
 
-
 
1695
	/* No fb means shut it down */
-
 
1696
	if (!plane_req->fb_id) {
-
 
1697
		plane->funcs->disable_plane(plane);
-
 
1698
		plane->crtc = NULL;
-
 
1699
		plane->fb = NULL;
-
 
1700
		goto out;
-
 
1701
	}
-
 
1702
 
-
 
1703
	obj = drm_mode_object_find(dev, plane_req->crtc_id,
-
 
1704
				   DRM_MODE_OBJECT_CRTC);
-
 
1705
	if (!obj) {
-
 
1706
		DRM_DEBUG_KMS("Unknown crtc ID %d\n",
-
 
1707
			      plane_req->crtc_id);
-
 
1708
		ret = -ENOENT;
-
 
1709
		goto out;
-
 
1710
	}
-
 
1711
	crtc = obj_to_crtc(obj);
-
 
1712
 
-
 
1713
	obj = drm_mode_object_find(dev, plane_req->fb_id,
-
 
1714
				   DRM_MODE_OBJECT_FB);
-
 
1715
	if (!obj) {
-
 
1716
		DRM_DEBUG_KMS("Unknown framebuffer ID %d\n",
-
 
1717
			      plane_req->fb_id);
-
 
1718
		ret = -ENOENT;
-
 
1719
		goto out;
-
 
1720
	}
-
 
1721
	fb = obj_to_fb(obj);
-
 
1722
 
-
 
1723
	/* Check whether this plane supports the fb pixel format. */
-
 
1724
	for (i = 0; i < plane->format_count; i++)
-
 
1725
		if (fb->pixel_format == plane->format_types[i])
-
 
1726
			break;
-
 
1727
	if (i == plane->format_count) {
-
 
1728
		DRM_DEBUG_KMS("Invalid pixel format 0x%08x\n", fb->pixel_format);
-
 
1729
		ret = -EINVAL;
-
 
1730
		goto out;
-
 
1731
	}
-
 
1732
 
-
 
1733
	fb_width = fb->width << 16;
-
 
1734
	fb_height = fb->height << 16;
-
 
1735
 
-
 
1736
	/* Make sure source coordinates are inside the fb. */
-
 
1737
	if (plane_req->src_w > fb_width ||
-
 
1738
	    plane_req->src_x > fb_width - plane_req->src_w ||
-
 
1739
	    plane_req->src_h > fb_height ||
-
 
1740
	    plane_req->src_y > fb_height - plane_req->src_h) {
-
 
1741
		DRM_DEBUG_KMS("Invalid source coordinates "
-
 
1742
			      "%u.%06ux%u.%06u+%u.%06u+%u.%06u\n",
-
 
1743
			      plane_req->src_w >> 16,
-
 
1744
			      ((plane_req->src_w & 0xffff) * 15625) >> 10,
-
 
1745
			      plane_req->src_h >> 16,
-
 
1746
			      ((plane_req->src_h & 0xffff) * 15625) >> 10,
-
 
1747
			      plane_req->src_x >> 16,
-
 
1748
			      ((plane_req->src_x & 0xffff) * 15625) >> 10,
-
 
1749
			      plane_req->src_y >> 16,
-
 
1750
			      ((plane_req->src_y & 0xffff) * 15625) >> 10);
-
 
1751
		ret = -ENOSPC;
-
 
1752
		goto out;
-
 
1753
	}
-
 
1754
 
-
 
1755
	/* Give drivers some help against integer overflows */
-
 
1756
	if (plane_req->crtc_w > INT_MAX ||
-
 
1757
	    plane_req->crtc_x > INT_MAX - (int32_t) plane_req->crtc_w ||
-
 
1758
	    plane_req->crtc_h > INT_MAX ||
-
 
1759
	    plane_req->crtc_y > INT_MAX - (int32_t) plane_req->crtc_h) {
-
 
1760
		DRM_DEBUG_KMS("Invalid CRTC coordinates %ux%u+%d+%d\n",
-
 
1761
			      plane_req->crtc_w, plane_req->crtc_h,
-
 
1762
			      plane_req->crtc_x, plane_req->crtc_y);
-
 
1763
		ret = -ERANGE;
-
 
1764
		goto out;
-
 
1765
	}
-
 
1766
 
-
 
1767
	ret = plane->funcs->update_plane(plane, crtc, fb,
-
 
1768
					 plane_req->crtc_x, plane_req->crtc_y,
-
 
1769
					 plane_req->crtc_w, plane_req->crtc_h,
-
 
1770
					 plane_req->src_x, plane_req->src_y,
-
 
1771
					 plane_req->src_w, plane_req->src_h);
-
 
1772
	if (!ret) {
-
 
1773
		plane->crtc = crtc;
-
 
1774
		plane->fb = fb;
-
 
1775
	}
-
 
1776
 
-
 
1777
out:
-
 
1778
	mutex_unlock(&dev->mode_config.mutex);
-
 
1779
 
-
 
1780
	return ret;
-
 
1781
}
-
 
1782
 
1470
/**
1783
/**
1471
 * drm_mode_setcrtc - set CRTC configuration
1784
 * drm_mode_setcrtc - set CRTC configuration
1472
 * @inode: inode from the ioctl
1785
 * @inode: inode from the ioctl
1473
 * @filp: file * from the ioctl
1786
 * @filp: file * from the ioctl
1474
 * @cmd: cmd from ioctl
1787
 * @cmd: cmd from ioctl
1475
 * @arg: arg from ioctl
1788
 * @arg: arg from ioctl
1476
 *
1789
 *
1477
 * LOCKING:
1790
 * LOCKING:
1478
 * Caller? (FIXME)
1791
 * Takes mode config lock.
1479
 *
1792
 *
1480
 * Build a new CRTC configuration based on user request.
1793
 * Build a new CRTC configuration based on user request.
1481
 *
1794
 *
1482
 * Called by the user via ioctl.
1795
 * Called by the user via ioctl.
Line 1488... Line 1801...
1488
		     struct drm_file *file_priv)
1801
		     struct drm_file *file_priv)
1489
{
1802
{
1490
	struct drm_mode_config *config = &dev->mode_config;
1803
	struct drm_mode_config *config = &dev->mode_config;
1491
	struct drm_mode_crtc *crtc_req = data;
1804
	struct drm_mode_crtc *crtc_req = data;
1492
	struct drm_mode_object *obj;
1805
	struct drm_mode_object *obj;
1493
	struct drm_crtc *crtc, *crtcfb;
1806
	struct drm_crtc *crtc;
1494
	struct drm_connector **connector_set = NULL, *connector;
1807
	struct drm_connector **connector_set = NULL, *connector;
1495
	struct drm_framebuffer *fb = NULL;
1808
	struct drm_framebuffer *fb = NULL;
1496
	struct drm_display_mode *mode = NULL;
1809
	struct drm_display_mode *mode = NULL;
1497
	struct drm_mode_set set;
1810
	struct drm_mode_set set;
1498
	uint32_t __user *set_connectors_ptr;
1811
	uint32_t __user *set_connectors_ptr;
1499
	int ret = 0;
1812
	int ret;
1500
	int i;
1813
	int i;
Line 1501... Line 1814...
1501
 
1814
 
1502
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
1815
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line -... Line 1816...
-
 
1816
		return -EINVAL;
-
 
1817
 
-
 
1818
	/* For some reason crtc x/y offsets are signed internally. */
-
 
1819
	if (crtc_req->x > INT_MAX || crtc_req->y > INT_MAX)
1503
		return -EINVAL;
1820
		return -ERANGE;
1504
 
1821
 
1505
	mutex_lock(&dev->mode_config.mutex);
1822
	mutex_lock(&dev->mode_config.mutex);
1506
	obj = drm_mode_object_find(dev, crtc_req->crtc_id,
1823
	obj = drm_mode_object_find(dev, crtc_req->crtc_id,
1507
				   DRM_MODE_OBJECT_CRTC);
1824
				   DRM_MODE_OBJECT_CRTC);
Line 1512... Line 1829...
1512
	}
1829
	}
1513
	crtc = obj_to_crtc(obj);
1830
	crtc = obj_to_crtc(obj);
1514
	DRM_DEBUG_KMS("[CRTC:%d]\n", crtc->base.id);
1831
	DRM_DEBUG_KMS("[CRTC:%d]\n", crtc->base.id);
Line 1515... Line 1832...
1515
 
1832
 
-
 
1833
	if (crtc_req->mode_valid) {
1516
	if (crtc_req->mode_valid) {
1834
		int hdisplay, vdisplay;
1517
		/* If we have a mode we need a framebuffer. */
1835
		/* If we have a mode we need a framebuffer. */
1518
		/* If we pass -1, set the mode with the currently bound fb */
1836
		/* If we pass -1, set the mode with the currently bound fb */
1519
		if (crtc_req->fb_id == -1) {
-
 
1520
			list_for_each_entry(crtcfb,
-
 
1521
					    &dev->mode_config.crtc_list, head) {
1837
		if (crtc_req->fb_id == -1) {
1522
				if (crtcfb == crtc) {
1838
			if (!crtc->fb) {
1523
					DRM_DEBUG_KMS("Using current fb for "
-
 
1524
							"setmode\n");
1839
				DRM_DEBUG_KMS("CRTC doesn't have current FB\n");
1525
					fb = crtc->fb;
1840
				ret = -EINVAL;
1526
				}
1841
				goto out;
-
 
1842
			}
1527
			}
1843
					fb = crtc->fb;
1528
		} else {
1844
		} else {
1529
			obj = drm_mode_object_find(dev, crtc_req->fb_id,
1845
			obj = drm_mode_object_find(dev, crtc_req->fb_id,
1530
						   DRM_MODE_OBJECT_FB);
1846
						   DRM_MODE_OBJECT_FB);
1531
			if (!obj) {
1847
			if (!obj) {
Line 1536... Line 1852...
1536
			}
1852
			}
1537
			fb = obj_to_fb(obj);
1853
			fb = obj_to_fb(obj);
1538
		}
1854
		}
Line 1539... Line 1855...
1539
 
1855
 
-
 
1856
		mode = drm_mode_create(dev);
-
 
1857
		if (!mode) {
-
 
1858
			ret = -ENOMEM;
-
 
1859
			goto out;
-
 
1860
		}
1540
		mode = drm_mode_create(dev);
1861
 
-
 
1862
		ret = drm_crtc_convert_umode(mode, &crtc_req->mode);
-
 
1863
		if (ret) {
-
 
1864
			DRM_DEBUG_KMS("Invalid mode\n");
-
 
1865
			goto out;
-
 
1866
		}
1541
		drm_crtc_convert_umode(mode, &crtc_req->mode);
1867
 
-
 
1868
		drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
-
 
1869
 
-
 
1870
		hdisplay = mode->hdisplay;
-
 
1871
		vdisplay = mode->vdisplay;
-
 
1872
 
-
 
1873
		if (crtc->invert_dimensions)
-
 
1874
			swap(hdisplay, vdisplay);
-
 
1875
 
-
 
1876
		if (hdisplay > fb->width ||
-
 
1877
		    vdisplay > fb->height ||
-
 
1878
		    crtc_req->x > fb->width - hdisplay ||
-
 
1879
		    crtc_req->y > fb->height - vdisplay) {
-
 
1880
			DRM_DEBUG_KMS("Invalid fb size %ux%u for CRTC viewport %ux%u+%d+%d%s.\n",
-
 
1881
				      fb->width, fb->height,
-
 
1882
				      hdisplay, vdisplay, crtc_req->x, crtc_req->y,
-
 
1883
				      crtc->invert_dimensions ? " (inverted)" : "");
-
 
1884
			ret = -ENOSPC;
-
 
1885
			goto out;
1542
		drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
1886
		}
Line 1543... Line 1887...
1543
	}
1887
	}
1544
 
1888
 
1545
	if (crtc_req->count_connectors == 0 && mode) {
1889
	if (crtc_req->count_connectors == 0 && mode) {
Line 1571... Line 1915...
1571
			ret = -ENOMEM;
1915
			ret = -ENOMEM;
1572
			goto out;
1916
			goto out;
1573
		}
1917
		}
Line 1574... Line 1918...
1574
 
1918
 
1575
		for (i = 0; i < crtc_req->count_connectors; i++) {
1919
		for (i = 0; i < crtc_req->count_connectors; i++) {
1576
			set_connectors_ptr = (uint32_t *)(unsigned long)crtc_req->set_connectors_ptr;
1920
			set_connectors_ptr = (uint32_t __user *)(unsigned long)crtc_req->set_connectors_ptr;
1577
			if (get_user(out_id, &set_connectors_ptr[i])) {
1921
			if (get_user(out_id, &set_connectors_ptr[i])) {
1578
				ret = -EFAULT;
1922
				ret = -EFAULT;
1579
				goto out;
1923
				goto out;
Line 1605... Line 1949...
1605
	set.fb = fb;
1949
	set.fb = fb;
1606
	ret = crtc->funcs->set_config(&set);
1950
	ret = crtc->funcs->set_config(&set);
Line 1607... Line 1951...
1607
 
1951
 
1608
out:
1952
out:
-
 
1953
	kfree(connector_set);
1609
	kfree(connector_set);
1954
	drm_mode_destroy(dev, mode);
1610
	mutex_unlock(&dev->mode_config.mutex);
1955
	mutex_unlock(&dev->mode_config.mutex);
1611
	return ret;
1956
	return ret;
Line 1612... Line 1957...
1612
}
1957
}
Line 1620... Line 1965...
1620
	int ret = 0;
1965
	int ret = 0;
Line 1621... Line 1966...
1621
 
1966
 
1622
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
1967
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line 1623... Line 1968...
1623
		return -EINVAL;
1968
		return -EINVAL;
1624
 
-
 
1625
	if (!req->flags) {
1969
 
1626
		DRM_ERROR("no operation set\n");
-
 
Line 1627... Line 1970...
1627
		return -EINVAL;
1970
	if (!req->flags || (~DRM_MODE_CURSOR_FLAGS & req->flags))
1628
	}
1971
		return -EINVAL;
1629
 
1972
 
1630
	mutex_lock(&dev->mode_config.mutex);
1973
	mutex_lock(&dev->mode_config.mutex);
Line 1636... Line 1979...
1636
	}
1979
	}
1637
	crtc = obj_to_crtc(obj);
1980
	crtc = obj_to_crtc(obj);
Line 1638... Line 1981...
1638
 
1981
 
1639
	if (req->flags & DRM_MODE_CURSOR_BO) {
1982
	if (req->flags & DRM_MODE_CURSOR_BO) {
1640
		if (!crtc->funcs->cursor_set) {
-
 
1641
			DRM_ERROR("crtc does not support cursor\n");
1983
		if (!crtc->funcs->cursor_set) {
1642
			ret = -ENXIO;
1984
			ret = -ENXIO;
1643
			goto out;
1985
			goto out;
1644
		}
1986
		}
1645
		/* Turns off the cursor if handle is 0 */
1987
		/* Turns off the cursor if handle is 0 */
Line 1649... Line 1991...
1649
 
1991
 
1650
	if (req->flags & DRM_MODE_CURSOR_MOVE) {
1992
	if (req->flags & DRM_MODE_CURSOR_MOVE) {
1651
		if (crtc->funcs->cursor_move) {
1993
		if (crtc->funcs->cursor_move) {
1652
			ret = crtc->funcs->cursor_move(crtc, req->x, req->y);
1994
			ret = crtc->funcs->cursor_move(crtc, req->x, req->y);
1653
		} else {
-
 
1654
			DRM_ERROR("crtc does not support cursor\n");
1995
		} else {
1655
			ret = -EFAULT;
1996
			ret = -EFAULT;
1656
			goto out;
1997
			goto out;
1657
		}
1998
		}
1658
	}
1999
	}
1659
out:
2000
out:
1660
	mutex_unlock(&dev->mode_config.mutex);
2001
	mutex_unlock(&dev->mode_config.mutex);
1661
	return ret;
2002
	return ret;
-
 
2003
}
-
 
2004
#endif
-
 
2005
/* Original addfb only supported RGB formats, so figure out which one */
-
 
2006
uint32_t drm_mode_legacy_fb_format(uint32_t bpp, uint32_t depth)
-
 
2007
{
-
 
2008
	uint32_t fmt;
-
 
2009
 
-
 
2010
	switch (bpp) {
-
 
2011
	case 8:
-
 
2012
		fmt = DRM_FORMAT_RGB332;
-
 
2013
		break;
-
 
2014
	case 16:
-
 
2015
		if (depth == 15)
-
 
2016
			fmt = DRM_FORMAT_XRGB1555;
-
 
2017
		else
-
 
2018
			fmt = DRM_FORMAT_RGB565;
-
 
2019
		break;
-
 
2020
	case 24:
-
 
2021
		fmt = DRM_FORMAT_RGB888;
-
 
2022
		break;
-
 
2023
	case 32:
-
 
2024
		if (depth == 24)
-
 
2025
			fmt = DRM_FORMAT_XRGB8888;
-
 
2026
		else if (depth == 30)
-
 
2027
			fmt = DRM_FORMAT_XRGB2101010;
-
 
2028
		else
-
 
2029
			fmt = DRM_FORMAT_ARGB8888;
-
 
2030
		break;
-
 
2031
	default:
-
 
2032
		DRM_ERROR("bad bpp, assuming x8r8g8b8 pixel format\n");
-
 
2033
		fmt = DRM_FORMAT_XRGB8888;
-
 
2034
		break;
Line -... Line 2035...
-
 
2035
	}
-
 
2036
 
-
 
2037
	return fmt;
-
 
2038
}
1662
}
2039
EXPORT_SYMBOL(drm_mode_legacy_fb_format);
1663
 
2040
#if 0
1664
/**
2041
/**
1665
 * drm_mode_addfb - add an FB to the graphics configuration
2042
 * drm_mode_addfb - add an FB to the graphics configuration
1666
 * @inode: inode from the ioctl
2043
 * @inode: inode from the ioctl
Line 1679... Line 2056...
1679
 * Zero on success, errno on failure.
2056
 * Zero on success, errno on failure.
1680
 */
2057
 */
1681
int drm_mode_addfb(struct drm_device *dev,
2058
int drm_mode_addfb(struct drm_device *dev,
1682
		   void *data, struct drm_file *file_priv)
2059
		   void *data, struct drm_file *file_priv)
1683
{
2060
{
1684
	struct drm_mode_fb_cmd *r = data;
2061
	struct drm_mode_fb_cmd *or = data;
-
 
2062
	struct drm_mode_fb_cmd2 r = {};
1685
	struct drm_mode_config *config = &dev->mode_config;
2063
	struct drm_mode_config *config = &dev->mode_config;
1686
	struct drm_framebuffer *fb;
2064
	struct drm_framebuffer *fb;
1687
	int ret = 0;
2065
	int ret = 0;
Line -... Line 2066...
-
 
2066
 
-
 
2067
	/* Use new struct with format internally */
-
 
2068
	r.fb_id = or->fb_id;
-
 
2069
	r.width = or->width;
-
 
2070
	r.height = or->height;
-
 
2071
	r.pitches[0] = or->pitch;
-
 
2072
	r.pixel_format = drm_mode_legacy_fb_format(or->bpp, or->depth);
-
 
2073
	r.handles[0] = or->handle;
-
 
2074
 
-
 
2075
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
-
 
2076
		return -EINVAL;
-
 
2077
 
-
 
2078
	if ((config->min_width > r.width) || (r.width > config->max_width))
-
 
2079
		return -EINVAL;
-
 
2080
 
-
 
2081
	if ((config->min_height > r.height) || (r.height > config->max_height))
-
 
2082
		return -EINVAL;
-
 
2083
 
-
 
2084
	mutex_lock(&dev->mode_config.mutex);
-
 
2085
 
-
 
2086
	/* TODO check buffer is sufficiently large */
-
 
2087
	/* TODO setup destructor callback */
-
 
2088
 
-
 
2089
	fb = dev->mode_config.funcs->fb_create(dev, file_priv, &r);
-
 
2090
	if (IS_ERR(fb)) {
-
 
2091
		DRM_DEBUG_KMS("could not create framebuffer\n");
-
 
2092
		ret = PTR_ERR(fb);
-
 
2093
		goto out;
-
 
2094
	}
-
 
2095
 
-
 
2096
	or->fb_id = fb->base.id;
-
 
2097
	list_add(&fb->filp_head, &file_priv->fbs);
-
 
2098
	DRM_DEBUG_KMS("[FB:%d]\n", fb->base.id);
-
 
2099
 
-
 
2100
out:
-
 
2101
	mutex_unlock(&dev->mode_config.mutex);
-
 
2102
	return ret;
-
 
2103
}
-
 
2104
 
-
 
2105
static int format_check(const struct drm_mode_fb_cmd2 *r)
-
 
2106
{
-
 
2107
	uint32_t format = r->pixel_format & ~DRM_FORMAT_BIG_ENDIAN;
-
 
2108
 
-
 
2109
	switch (format) {
-
 
2110
	case DRM_FORMAT_C8:
-
 
2111
	case DRM_FORMAT_RGB332:
-
 
2112
	case DRM_FORMAT_BGR233:
-
 
2113
	case DRM_FORMAT_XRGB4444:
-
 
2114
	case DRM_FORMAT_XBGR4444:
-
 
2115
	case DRM_FORMAT_RGBX4444:
-
 
2116
	case DRM_FORMAT_BGRX4444:
-
 
2117
	case DRM_FORMAT_ARGB4444:
-
 
2118
	case DRM_FORMAT_ABGR4444:
-
 
2119
	case DRM_FORMAT_RGBA4444:
-
 
2120
	case DRM_FORMAT_BGRA4444:
-
 
2121
	case DRM_FORMAT_XRGB1555:
-
 
2122
	case DRM_FORMAT_XBGR1555:
-
 
2123
	case DRM_FORMAT_RGBX5551:
-
 
2124
	case DRM_FORMAT_BGRX5551:
-
 
2125
	case DRM_FORMAT_ARGB1555:
-
 
2126
	case DRM_FORMAT_ABGR1555:
-
 
2127
	case DRM_FORMAT_RGBA5551:
-
 
2128
	case DRM_FORMAT_BGRA5551:
-
 
2129
	case DRM_FORMAT_RGB565:
-
 
2130
	case DRM_FORMAT_BGR565:
-
 
2131
	case DRM_FORMAT_RGB888:
-
 
2132
	case DRM_FORMAT_BGR888:
-
 
2133
	case DRM_FORMAT_XRGB8888:
-
 
2134
	case DRM_FORMAT_XBGR8888:
-
 
2135
	case DRM_FORMAT_RGBX8888:
-
 
2136
	case DRM_FORMAT_BGRX8888:
-
 
2137
	case DRM_FORMAT_ARGB8888:
-
 
2138
	case DRM_FORMAT_ABGR8888:
-
 
2139
	case DRM_FORMAT_RGBA8888:
-
 
2140
	case DRM_FORMAT_BGRA8888:
-
 
2141
	case DRM_FORMAT_XRGB2101010:
-
 
2142
	case DRM_FORMAT_XBGR2101010:
-
 
2143
	case DRM_FORMAT_RGBX1010102:
-
 
2144
	case DRM_FORMAT_BGRX1010102:
-
 
2145
	case DRM_FORMAT_ARGB2101010:
-
 
2146
	case DRM_FORMAT_ABGR2101010:
-
 
2147
	case DRM_FORMAT_RGBA1010102:
-
 
2148
	case DRM_FORMAT_BGRA1010102:
-
 
2149
	case DRM_FORMAT_YUYV:
-
 
2150
	case DRM_FORMAT_YVYU:
-
 
2151
	case DRM_FORMAT_UYVY:
-
 
2152
	case DRM_FORMAT_VYUY:
-
 
2153
	case DRM_FORMAT_AYUV:
-
 
2154
	case DRM_FORMAT_NV12:
-
 
2155
	case DRM_FORMAT_NV21:
-
 
2156
	case DRM_FORMAT_NV16:
-
 
2157
	case DRM_FORMAT_NV61:
-
 
2158
	case DRM_FORMAT_NV24:
-
 
2159
	case DRM_FORMAT_NV42:
-
 
2160
	case DRM_FORMAT_YUV410:
-
 
2161
	case DRM_FORMAT_YVU410:
-
 
2162
	case DRM_FORMAT_YUV411:
-
 
2163
	case DRM_FORMAT_YVU411:
-
 
2164
	case DRM_FORMAT_YUV420:
-
 
2165
	case DRM_FORMAT_YVU420:
-
 
2166
	case DRM_FORMAT_YUV422:
-
 
2167
	case DRM_FORMAT_YVU422:
-
 
2168
	case DRM_FORMAT_YUV444:
-
 
2169
	case DRM_FORMAT_YVU444:
-
 
2170
		return 0;
-
 
2171
	default:
-
 
2172
		return -EINVAL;
-
 
2173
	}
-
 
2174
}
-
 
2175
 
-
 
2176
static int framebuffer_check(const struct drm_mode_fb_cmd2 *r)
-
 
2177
{
-
 
2178
	int ret, hsub, vsub, num_planes, i;
-
 
2179
 
-
 
2180
	ret = format_check(r);
-
 
2181
	if (ret) {
-
 
2182
		DRM_DEBUG_KMS("bad framebuffer format 0x%08x\n", r->pixel_format);
-
 
2183
		return ret;
-
 
2184
	}
-
 
2185
 
-
 
2186
	hsub = drm_format_horz_chroma_subsampling(r->pixel_format);
-
 
2187
	vsub = drm_format_vert_chroma_subsampling(r->pixel_format);
-
 
2188
	num_planes = drm_format_num_planes(r->pixel_format);
-
 
2189
 
-
 
2190
	if (r->width == 0 || r->width % hsub) {
-
 
2191
		DRM_DEBUG_KMS("bad framebuffer width %u\n", r->height);
-
 
2192
		return -EINVAL;
-
 
2193
	}
-
 
2194
 
-
 
2195
	if (r->height == 0 || r->height % vsub) {
-
 
2196
		DRM_DEBUG_KMS("bad framebuffer height %u\n", r->height);
-
 
2197
		return -EINVAL;
-
 
2198
	}
-
 
2199
 
-
 
2200
	for (i = 0; i < num_planes; i++) {
-
 
2201
		unsigned int width = r->width / (i != 0 ? hsub : 1);
-
 
2202
 
-
 
2203
		if (!r->handles[i]) {
-
 
2204
			DRM_DEBUG_KMS("no buffer object handle for plane %d\n", i);
-
 
2205
			return -EINVAL;
-
 
2206
		}
-
 
2207
 
-
 
2208
		if (r->pitches[i] < drm_format_plane_cpp(r->pixel_format, i) * width) {
-
 
2209
			DRM_DEBUG_KMS("bad pitch %u for plane %d\n", r->pitches[i], i);
-
 
2210
			return -EINVAL;
-
 
2211
		}
-
 
2212
	}
-
 
2213
 
-
 
2214
	return 0;
-
 
2215
}
-
 
2216
 
-
 
2217
/**
-
 
2218
 * drm_mode_addfb2 - add an FB to the graphics configuration
-
 
2219
 * @inode: inode from the ioctl
-
 
2220
 * @filp: file * from the ioctl
-
 
2221
 * @cmd: cmd from ioctl
-
 
2222
 * @arg: arg from ioctl
-
 
2223
 *
-
 
2224
 * LOCKING:
-
 
2225
 * Takes mode config lock.
-
 
2226
 *
-
 
2227
 * Add a new FB to the specified CRTC, given a user request with format.
-
 
2228
 *
-
 
2229
 * Called by the user via ioctl.
-
 
2230
 *
-
 
2231
 * RETURNS:
-
 
2232
 * Zero on success, errno on failure.
-
 
2233
 */
-
 
2234
int drm_mode_addfb2(struct drm_device *dev,
-
 
2235
		    void *data, struct drm_file *file_priv)
-
 
2236
{
-
 
2237
	struct drm_mode_fb_cmd2 *r = data;
-
 
2238
	struct drm_mode_config *config = &dev->mode_config;
-
 
2239
	struct drm_framebuffer *fb;
-
 
2240
	int ret;
1688
 
2241
 
1689
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
2242
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line 1690... Line 2243...
1690
		return -EINVAL;
2243
		return -EINVAL;
1691
 
2244
 
-
 
2245
	if ((config->min_width > r->width) || (r->width > config->max_width)) {
1692
	if ((config->min_width > r->width) || (r->width > config->max_width)) {
2246
		DRM_DEBUG_KMS("bad framebuffer width %d, should be >= %d && <= %d\n",
1693
		DRM_ERROR("mode new framebuffer width not within limits\n");
2247
			  r->width, config->min_width, config->max_width);
1694
		return -EINVAL;
2248
		return -EINVAL;
1695
	}
2249
	}
-
 
2250
	if ((config->min_height > r->height) || (r->height > config->max_height)) {
1696
	if ((config->min_height > r->height) || (r->height > config->max_height)) {
2251
		DRM_DEBUG_KMS("bad framebuffer height %d, should be >= %d && <= %d\n",
1697
		DRM_ERROR("mode new framebuffer height not within limits\n");
2252
			  r->height, config->min_height, config->max_height);
Line 1698... Line 2253...
1698
		return -EINVAL;
2253
		return -EINVAL;
-
 
2254
	}
-
 
2255
 
Line 1699... Line 2256...
1699
	}
2256
	ret = framebuffer_check(r);
1700
 
-
 
Line 1701... Line 2257...
1701
	mutex_lock(&dev->mode_config.mutex);
2257
	if (ret)
1702
 
2258
		return ret;
1703
	/* TODO check buffer is sufficiently large */
2259
 
1704
	/* TODO setup destructor callback */
2260
	mutex_lock(&dev->mode_config.mutex);
1705
 
2261
 
1706
	fb = dev->mode_config.funcs->fb_create(dev, file_priv, r);
2262
	fb = dev->mode_config.funcs->fb_create(dev, file_priv, r);
Line 1707... Line 2263...
1707
	if (IS_ERR(fb)) {
2263
	if (IS_ERR(fb)) {
Line 1751... Line 2307...
1751
 
2307
 
1752
	mutex_lock(&dev->mode_config.mutex);
2308
	mutex_lock(&dev->mode_config.mutex);
1753
	obj = drm_mode_object_find(dev, *id, DRM_MODE_OBJECT_FB);
2309
	obj = drm_mode_object_find(dev, *id, DRM_MODE_OBJECT_FB);
1754
	/* TODO check that we really get a framebuffer back. */
2310
	/* TODO check that we really get a framebuffer back. */
1755
	if (!obj) {
-
 
1756
		DRM_ERROR("mode invalid framebuffer id\n");
2311
	if (!obj) {
1757
		ret = -EINVAL;
2312
		ret = -EINVAL;
1758
		goto out;
2313
		goto out;
1759
	}
2314
	}
Line 1760... Line 2315...
1760
	fb = obj_to_fb(obj);
2315
	fb = obj_to_fb(obj);
1761
 
2316
 
1762
	list_for_each_entry(fbl, &file_priv->fbs, filp_head)
2317
	list_for_each_entry(fbl, &file_priv->fbs, filp_head)
Line 1763... Line 2318...
1763
		if (fb == fbl)
2318
		if (fb == fbl)
1764
			found = 1;
-
 
1765
 
2319
			found = 1;
1766
	if (!found) {
2320
 
1767
		DRM_ERROR("tried to remove a fb that we didn't own\n");
2321
	if (!found) {
Line 1768... Line -...
1768
		ret = -EINVAL;
-
 
1769
		goto out;
-
 
1770
	}
-
 
1771
 
-
 
1772
	/* TODO release all crtc connected to the framebuffer */
2322
		ret = -EINVAL;
Line 1773... Line 2323...
1773
	/* TODO unhock the destructor from the buffer object */
2323
		goto out;
1774
 
2324
	}
1775
	list_del(&fb->filp_head);
2325
 
1776
	fb->funcs->destroy(fb);
2326
	drm_framebuffer_remove(fb);
Line 1786... Line 2336...
1786
 * @filp: file * from the ioctl
2336
 * @filp: file * from the ioctl
1787
 * @cmd: cmd from ioctl
2337
 * @cmd: cmd from ioctl
1788
 * @arg: arg from ioctl
2338
 * @arg: arg from ioctl
1789
 *
2339
 *
1790
 * LOCKING:
2340
 * LOCKING:
1791
 * Caller? (FIXME)
2341
 * Takes mode config lock.
1792
 *
2342
 *
1793
 * Lookup the FB given its ID and return info about it.
2343
 * Lookup the FB given its ID and return info about it.
1794
 *
2344
 *
1795
 * Called by the user via ioctl.
2345
 * Called by the user via ioctl.
1796
 *
2346
 *
Line 1809... Line 2359...
1809
		return -EINVAL;
2359
		return -EINVAL;
Line 1810... Line 2360...
1810
 
2360
 
1811
	mutex_lock(&dev->mode_config.mutex);
2361
	mutex_lock(&dev->mode_config.mutex);
1812
	obj = drm_mode_object_find(dev, r->fb_id, DRM_MODE_OBJECT_FB);
2362
	obj = drm_mode_object_find(dev, r->fb_id, DRM_MODE_OBJECT_FB);
1813
	if (!obj) {
-
 
1814
		DRM_ERROR("invalid framebuffer id\n");
2363
	if (!obj) {
1815
		ret = -EINVAL;
2364
		ret = -EINVAL;
1816
		goto out;
2365
		goto out;
1817
	}
2366
	}
Line 1818... Line 2367...
1818
	fb = obj_to_fb(obj);
2367
	fb = obj_to_fb(obj);
1819
 
2368
 
1820
	r->height = fb->height;
2369
	r->height = fb->height;
1821
	r->width = fb->width;
2370
	r->width = fb->width;
1822
	r->depth = fb->depth;
2371
	r->depth = fb->depth;
1823
	r->bpp = fb->bits_per_pixel;
2372
	r->bpp = fb->bits_per_pixel;
Line 1824... Line 2373...
1824
	r->pitch = fb->pitch;
2373
	r->pitch = fb->pitches[0];
1825
	fb->funcs->create_handle(fb, file_priv, &r->handle);
2374
	fb->funcs->create_handle(fb, file_priv, &r->handle);
1826
 
2375
 
Line 1837... Line 2386...
1837
	struct drm_mode_fb_dirty_cmd *r = data;
2386
	struct drm_mode_fb_dirty_cmd *r = data;
1838
	struct drm_mode_object *obj;
2387
	struct drm_mode_object *obj;
1839
	struct drm_framebuffer *fb;
2388
	struct drm_framebuffer *fb;
1840
	unsigned flags;
2389
	unsigned flags;
1841
	int num_clips;
2390
	int num_clips;
1842
	int ret = 0;
2391
	int ret;
Line 1843... Line 2392...
1843
 
2392
 
1844
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
2393
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line 1845... Line 2394...
1845
		return -EINVAL;
2394
		return -EINVAL;
1846
 
2395
 
1847
	mutex_lock(&dev->mode_config.mutex);
2396
	mutex_lock(&dev->mode_config.mutex);
1848
	obj = drm_mode_object_find(dev, r->fb_id, DRM_MODE_OBJECT_FB);
-
 
1849
	if (!obj) {
2397
	obj = drm_mode_object_find(dev, r->fb_id, DRM_MODE_OBJECT_FB);
1850
		DRM_ERROR("invalid framebuffer id\n");
2398
	if (!obj) {
1851
		ret = -EINVAL;
2399
		ret = -EINVAL;
1852
		goto out_err1;
2400
		goto out_err1;
Line 1853... Line 2401...
1853
	}
2401
	}
1854
	fb = obj_to_fb(obj);
2402
	fb = obj_to_fb(obj);
Line 1855... Line 2403...
1855
 
2403
 
1856
	num_clips = r->num_clips;
2404
	num_clips = r->num_clips;
1857
	clips_ptr = (struct drm_clip_rect *)(unsigned long)r->clips_ptr;
2405
	clips_ptr = (struct drm_clip_rect __user *)(unsigned long)r->clips_ptr;
1858
 
2406
 
Line 1868... Line 2416...
1868
		ret = -EINVAL;
2416
		ret = -EINVAL;
1869
		goto out_err1;
2417
		goto out_err1;
1870
	}
2418
	}
Line 1871... Line 2419...
1871
 
2419
 
-
 
2420
	if (num_clips && clips_ptr) {
-
 
2421
		if (num_clips < 0 || num_clips > DRM_MODE_FB_DIRTY_MAX_CLIPS) {
-
 
2422
			ret = -EINVAL;
-
 
2423
			goto out_err1;
1872
	if (num_clips && clips_ptr) {
2424
		}
1873
		clips = kzalloc(num_clips * sizeof(*clips), GFP_KERNEL);
2425
		clips = kzalloc(num_clips * sizeof(*clips), GFP_KERNEL);
1874
		if (!clips) {
2426
		if (!clips) {
1875
			ret = -ENOMEM;
2427
			ret = -ENOMEM;
1876
			goto out_err1;
2428
			goto out_err1;
Line 1919... Line 2471...
1919
	struct drm_device *dev = priv->minor->dev;
2471
	struct drm_device *dev = priv->minor->dev;
1920
	struct drm_framebuffer *fb, *tfb;
2472
	struct drm_framebuffer *fb, *tfb;
Line 1921... Line 2473...
1921
 
2473
 
1922
	mutex_lock(&dev->mode_config.mutex);
2474
	mutex_lock(&dev->mode_config.mutex);
1923
	list_for_each_entry_safe(fb, tfb, &priv->fbs, filp_head) {
-
 
1924
		list_del(&fb->filp_head);
2475
	list_for_each_entry_safe(fb, tfb, &priv->fbs, filp_head) {
1925
		fb->funcs->destroy(fb);
2476
		drm_framebuffer_remove(fb);
1926
	}
2477
	}
1927
	mutex_unlock(&dev->mode_config.mutex);
2478
	mutex_unlock(&dev->mode_config.mutex);
1928
}
2479
}
Line 1934... Line 2485...
1934
 * @connector: connector to add the mode to
2485
 * @connector: connector to add the mode to
1935
 * @mode: mode to add
2486
 * @mode: mode to add
1936
 *
2487
 *
1937
 * Add @mode to @connector's user mode list.
2488
 * Add @mode to @connector's user mode list.
1938
 */
2489
 */
1939
static int drm_mode_attachmode(struct drm_device *dev,
2490
static void drm_mode_attachmode(struct drm_device *dev,
1940
			       struct drm_connector *connector,
2491
			       struct drm_connector *connector,
1941
			       struct drm_display_mode *mode)
2492
			       struct drm_display_mode *mode)
1942
{
2493
{
1943
	int ret = 0;
-
 
1944
 
-
 
1945
	list_add_tail(&mode->head, &connector->user_modes);
2494
	list_add_tail(&mode->head, &connector->user_modes);
1946
	return ret;
-
 
1947
}
2495
}
Line 1948... Line 2496...
1948
 
2496
 
1949
int drm_mode_attachmode_crtc(struct drm_device *dev, struct drm_crtc *crtc,
2497
int drm_mode_attachmode_crtc(struct drm_device *dev, struct drm_crtc *crtc,
1950
			     struct drm_display_mode *mode)
2498
			     const struct drm_display_mode *mode)
1951
{
2499
{
1952
	struct drm_connector *connector;
2500
	struct drm_connector *connector;
1953
	int ret = 0;
2501
	int ret = 0;
1954
	struct drm_display_mode *dup_mode;
2502
	struct drm_display_mode *dup_mode, *next;
-
 
2503
	LIST_HEAD(list);
1955
	int need_dup = 0;
2504
 
1956
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
2505
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
1957
		if (!connector->encoder)
2506
		if (!connector->encoder)
1958
			break;
2507
			continue;
1959
		if (connector->encoder->crtc == crtc) {
-
 
1960
			if (need_dup)
2508
		if (connector->encoder->crtc == crtc) {
1961
				dup_mode = drm_mode_duplicate(dev, mode);
-
 
1962
			else
2509
				dup_mode = drm_mode_duplicate(dev, mode);
1963
				dup_mode = mode;
-
 
1964
			ret = drm_mode_attachmode(dev, connector, dup_mode);
-
 
1965
			if (ret)
2510
			if (!dup_mode) {
1966
				return ret;
2511
				ret = -ENOMEM;
1967
			need_dup = 1;
2512
				goto out;
-
 
2513
		}
1968
		}
2514
			list_add_tail(&dup_mode->head, &list);
-
 
2515
		}
-
 
2516
	}
-
 
2517
 
-
 
2518
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-
 
2519
		if (!connector->encoder)
-
 
2520
			continue;
-
 
2521
		if (connector->encoder->crtc == crtc)
-
 
2522
			list_move_tail(list.next, &connector->user_modes);
-
 
2523
	}
-
 
2524
 
-
 
2525
	WARN_ON(!list_empty(&list));
-
 
2526
 
-
 
2527
 out:
-
 
2528
	list_for_each_entry_safe(dup_mode, next, &list, head)
-
 
2529
		drm_mode_destroy(dev, dup_mode);
1969
	}
2530
 
1970
	return 0;
2531
	return ret;
1971
}
2532
}
Line 1972... Line 2533...
1972
EXPORT_SYMBOL(drm_mode_attachmode_crtc);
2533
EXPORT_SYMBOL(drm_mode_attachmode_crtc);
1973
 
2534
 
Line 2026... Line 2587...
2026
	struct drm_mode_mode_cmd *mode_cmd = data;
2587
	struct drm_mode_mode_cmd *mode_cmd = data;
2027
	struct drm_connector *connector;
2588
	struct drm_connector *connector;
2028
	struct drm_display_mode *mode;
2589
	struct drm_display_mode *mode;
2029
	struct drm_mode_object *obj;
2590
	struct drm_mode_object *obj;
2030
	struct drm_mode_modeinfo *umode = &mode_cmd->mode;
2591
	struct drm_mode_modeinfo *umode = &mode_cmd->mode;
2031
	int ret = 0;
2592
	int ret;
Line 2032... Line 2593...
2032
 
2593
 
2033
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
2594
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line 2034... Line 2595...
2034
		return -EINVAL;
2595
		return -EINVAL;
Line 2046... Line 2607...
2046
	if (!mode) {
2607
	if (!mode) {
2047
		ret = -ENOMEM;
2608
		ret = -ENOMEM;
2048
		goto out;
2609
		goto out;
2049
	}
2610
	}
Line 2050... Line 2611...
2050
 
2611
 
-
 
2612
	ret = drm_crtc_convert_umode(mode, umode);
-
 
2613
	if (ret) {
-
 
2614
		DRM_DEBUG_KMS("Invalid mode\n");
-
 
2615
		drm_mode_destroy(dev, mode);
-
 
2616
		goto out;
Line 2051... Line 2617...
2051
	drm_crtc_convert_umode(mode, umode);
2617
	}
2052
 
2618
 
2053
	ret = drm_mode_attachmode(dev, connector, mode);
2619
	drm_mode_attachmode(dev, connector, mode);
2054
out:
2620
out:
2055
	mutex_unlock(&dev->mode_config.mutex);
2621
	mutex_unlock(&dev->mode_config.mutex);
Line 2075... Line 2641...
2075
	struct drm_mode_object *obj;
2641
	struct drm_mode_object *obj;
2076
	struct drm_mode_mode_cmd *mode_cmd = data;
2642
	struct drm_mode_mode_cmd *mode_cmd = data;
2077
	struct drm_connector *connector;
2643
	struct drm_connector *connector;
2078
	struct drm_display_mode mode;
2644
	struct drm_display_mode mode;
2079
	struct drm_mode_modeinfo *umode = &mode_cmd->mode;
2645
	struct drm_mode_modeinfo *umode = &mode_cmd->mode;
2080
	int ret = 0;
2646
	int ret;
Line 2081... Line 2647...
2081
 
2647
 
2082
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
2648
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line 2083... Line 2649...
2083
		return -EINVAL;
2649
		return -EINVAL;
Line 2089... Line 2655...
2089
		ret = -EINVAL;
2655
		ret = -EINVAL;
2090
		goto out;
2656
		goto out;
2091
	}
2657
	}
2092
	connector = obj_to_connector(obj);
2658
	connector = obj_to_connector(obj);
Line 2093... Line 2659...
2093
 
2659
 
-
 
2660
	ret = drm_crtc_convert_umode(&mode, umode);
-
 
2661
	if (ret) {
-
 
2662
		DRM_DEBUG_KMS("Invalid mode\n");
-
 
2663
		goto out;
-
 
2664
	}
2094
	drm_crtc_convert_umode(&mode, umode);
2665
 
2095
	ret = drm_mode_detachmode(dev, connector, &mode);
2666
	ret = drm_mode_detachmode(dev, connector, &mode);
2096
out:
2667
out:
2097
	mutex_unlock(&dev->mode_config.mutex);
2668
	mutex_unlock(&dev->mode_config.mutex);
2098
	return ret;
2669
	return ret;
Line 2101... Line 2672...
2101
 
2672
 
2102
struct drm_property *drm_property_create(struct drm_device *dev, int flags,
2673
struct drm_property *drm_property_create(struct drm_device *dev, int flags,
2103
					 const char *name, int num_values)
2674
					 const char *name, int num_values)
2104
{
2675
{
-
 
2676
	struct drm_property *property = NULL;
Line 2105... Line 2677...
2105
	struct drm_property *property = NULL;
2677
	int ret;
2106
 
2678
 
2107
	property = kzalloc(sizeof(struct drm_property), GFP_KERNEL);
2679
	property = kzalloc(sizeof(struct drm_property), GFP_KERNEL);
Line 2112... Line 2684...
2112
		property->values = kzalloc(sizeof(uint64_t)*num_values, GFP_KERNEL);
2684
		property->values = kzalloc(sizeof(uint64_t)*num_values, GFP_KERNEL);
2113
		if (!property->values)
2685
		if (!property->values)
2114
			goto fail;
2686
			goto fail;
2115
	}
2687
	}
Line 2116... Line 2688...
2116
 
2688
 
-
 
2689
	ret = drm_mode_object_get(dev, &property->base, DRM_MODE_OBJECT_PROPERTY);
-
 
2690
	if (ret)
-
 
2691
		goto fail;
2117
	drm_mode_object_get(dev, &property->base, DRM_MODE_OBJECT_PROPERTY);
2692
 
2118
	property->flags = flags;
2693
	property->flags = flags;
2119
	property->num_values = num_values;
2694
	property->num_values = num_values;
Line 2120... Line 2695...
2120
	INIT_LIST_HEAD(&property->enum_blob_list);
2695
	INIT_LIST_HEAD(&property->enum_blob_list);
2121
 
2696
 
-
 
2697
	if (name) {
-
 
2698
		strncpy(property->name, name, DRM_PROP_NAME_LEN);
Line 2122... Line 2699...
2122
	if (name)
2699
		property->name[DRM_PROP_NAME_LEN-1] = '\0';
2123
		strncpy(property->name, name, DRM_PROP_NAME_LEN);
2700
	}
2124
 
2701
 
-
 
2702
	list_add_tail(&property->head, &dev->mode_config.property_list);
2125
	list_add_tail(&property->head, &dev->mode_config.property_list);
2703
	return property;
2126
	return property;
2704
fail:
2127
fail:
2705
	kfree(property->values);
2128
	kfree(property);
2706
	kfree(property);
Line -... Line 2707...
-
 
2707
	return NULL;
-
 
2708
}
-
 
2709
EXPORT_SYMBOL(drm_property_create);
-
 
2710
 
-
 
2711
struct drm_property *drm_property_create_enum(struct drm_device *dev, int flags,
-
 
2712
					 const char *name,
-
 
2713
					 const struct drm_prop_enum_list *props,
-
 
2714
					 int num_values)
-
 
2715
{
-
 
2716
	struct drm_property *property;
-
 
2717
	int i, ret;
-
 
2718
 
-
 
2719
	flags |= DRM_MODE_PROP_ENUM;
-
 
2720
 
-
 
2721
	property = drm_property_create(dev, flags, name, num_values);
-
 
2722
	if (!property)
-
 
2723
		return NULL;
-
 
2724
 
-
 
2725
	for (i = 0; i < num_values; i++) {
-
 
2726
		ret = drm_property_add_enum(property, i,
-
 
2727
				      props[i].type,
-
 
2728
				      props[i].name);
-
 
2729
		if (ret) {
-
 
2730
			drm_property_destroy(dev, property);
-
 
2731
			return NULL;
-
 
2732
		}
-
 
2733
	}
-
 
2734
 
-
 
2735
	return property;
-
 
2736
}
-
 
2737
EXPORT_SYMBOL(drm_property_create_enum);
-
 
2738
 
-
 
2739
struct drm_property *drm_property_create_bitmask(struct drm_device *dev,
-
 
2740
					 int flags, const char *name,
-
 
2741
					 const struct drm_prop_enum_list *props,
-
 
2742
					 int num_values)
-
 
2743
{
-
 
2744
	struct drm_property *property;
-
 
2745
	int i, ret;
-
 
2746
 
-
 
2747
	flags |= DRM_MODE_PROP_BITMASK;
-
 
2748
 
-
 
2749
	property = drm_property_create(dev, flags, name, num_values);
-
 
2750
	if (!property)
-
 
2751
		return NULL;
-
 
2752
 
-
 
2753
	for (i = 0; i < num_values; i++) {
-
 
2754
		ret = drm_property_add_enum(property, i,
-
 
2755
				      props[i].type,
-
 
2756
				      props[i].name);
-
 
2757
		if (ret) {
-
 
2758
			drm_property_destroy(dev, property);
-
 
2759
			return NULL;
-
 
2760
		}
-
 
2761
	}
-
 
2762
 
-
 
2763
	return property;
-
 
2764
}
-
 
2765
EXPORT_SYMBOL(drm_property_create_bitmask);
-
 
2766
 
-
 
2767
struct drm_property *drm_property_create_range(struct drm_device *dev, int flags,
-
 
2768
					 const char *name,
-
 
2769
					 uint64_t min, uint64_t max)
-
 
2770
{
-
 
2771
	struct drm_property *property;
-
 
2772
 
-
 
2773
	flags |= DRM_MODE_PROP_RANGE;
-
 
2774
 
-
 
2775
	property = drm_property_create(dev, flags, name, 2);
-
 
2776
	if (!property)
-
 
2777
		return NULL;
-
 
2778
 
-
 
2779
	property->values[0] = min;
-
 
2780
	property->values[1] = max;
-
 
2781
 
2129
	return NULL;
2782
	return property;
2130
}
2783
}
2131
EXPORT_SYMBOL(drm_property_create);
2784
EXPORT_SYMBOL(drm_property_create_range);
2132
 
2785
 
Line -... Line 2786...
-
 
2786
int drm_property_add_enum(struct drm_property *property, int index,
-
 
2787
			  uint64_t value, const char *name)
-
 
2788
{
-
 
2789
	struct drm_property_enum *prop_enum;
-
 
2790
 
-
 
2791
	if (!(property->flags & (DRM_MODE_PROP_ENUM | DRM_MODE_PROP_BITMASK)))
-
 
2792
		return -EINVAL;
2133
int drm_property_add_enum(struct drm_property *property, int index,
2793
 
2134
			  uint64_t value, const char *name)
2794
	/*
Line 2135... Line 2795...
2135
{
2795
	 * Bitmask enum properties have the additional constraint of values
2136
	struct drm_property_enum *prop_enum;
2796
	 * from 0 to 63
2137
 
2797
	 */
Line 2177... Line 2837...
2177
	list_del(&property->head);
2837
	list_del(&property->head);
2178
	kfree(property);
2838
	kfree(property);
2179
}
2839
}
2180
EXPORT_SYMBOL(drm_property_destroy);
2840
EXPORT_SYMBOL(drm_property_destroy);
Line 2181... Line 2841...
2181
 
2841
 
2182
int drm_connector_attach_property(struct drm_connector *connector,
2842
void drm_connector_attach_property(struct drm_connector *connector,
2183
			       struct drm_property *property, uint64_t init_val)
2843
			       struct drm_property *property, uint64_t init_val)
-
 
2844
{
2184
{
2845
	drm_object_attach_property(&connector->base, property, init_val);
-
 
2846
}
Line 2185... Line -...
2185
	int i;
-
 
2186
 
2847
EXPORT_SYMBOL(drm_connector_attach_property);
2187
	for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
2848
 
-
 
2849
int drm_connector_property_set_value(struct drm_connector *connector,
2188
		if (connector->property_ids[i] == 0) {
2850
				  struct drm_property *property, uint64_t value)
2189
			connector->property_ids[i] = property->base.id;
-
 
2190
			connector->property_values[i] = init_val;
2851
{
-
 
2852
	return drm_object_property_set_value(&connector->base, property, value);
-
 
2853
}
-
 
2854
EXPORT_SYMBOL(drm_connector_property_set_value);
-
 
2855
 
-
 
2856
int drm_connector_property_get_value(struct drm_connector *connector,
-
 
2857
				  struct drm_property *property, uint64_t *val)
2191
			break;
2858
{
-
 
2859
	return drm_object_property_get_value(&connector->base, property, val);
Line -... Line 2860...
-
 
2860
}
-
 
2861
EXPORT_SYMBOL(drm_connector_property_get_value);
-
 
2862
 
-
 
2863
void drm_object_attach_property(struct drm_mode_object *obj,
-
 
2864
				struct drm_property *property,
-
 
2865
				uint64_t init_val)
2192
		}
2866
{
-
 
2867
	int count = obj->properties->count;
-
 
2868
 
-
 
2869
	if (count == DRM_OBJECT_MAX_PROPERTY) {
2193
	}
2870
		WARN(1, "Failed to attach object property (type: 0x%x). Please "
2194
 
2871
			"increase DRM_OBJECT_MAX_PROPERTY by 1 for each time "
2195
	if (i == DRM_CONNECTOR_MAX_PROPERTY)
2872
			"you see this message on the same object type.\n",
2196
		return -EINVAL;
-
 
Line -... Line 2873...
-
 
2873
			obj->type);
-
 
2874
		return;
-
 
2875
	}
-
 
2876
 
-
 
2877
	obj->properties->ids[count] = property->base.id;
-
 
2878
	obj->properties->values[count] = init_val;
2197
	return 0;
2879
	obj->properties->count++;
2198
}
2880
}
2199
EXPORT_SYMBOL(drm_connector_attach_property);
2881
EXPORT_SYMBOL(drm_object_attach_property);
2200
 
2882
 
Line 2201... Line 2883...
2201
int drm_connector_property_set_value(struct drm_connector *connector,
2883
int drm_object_property_set_value(struct drm_mode_object *obj,
2202
				  struct drm_property *property, uint64_t value)
2884
				  struct drm_property *property, uint64_t val)
2203
{
2885
{
2204
	int i;
2886
	int i;
2205
 
2887
 
2206
	for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
2888
	for (i = 0; i < obj->properties->count; i++) {
Line 2207... Line -...
2207
		if (connector->property_ids[i] == property->base.id) {
-
 
2208
			connector->property_values[i] = value;
2889
		if (obj->properties->ids[i] == property->base.id) {
2209
			break;
-
 
2210
		}
2890
			obj->properties->values[i] = val;
2211
	}
2891
			return 0;
Line 2212... Line 2892...
2212
 
2892
		}
2213
	if (i == DRM_CONNECTOR_MAX_PROPERTY)
2893
	}
2214
		return -EINVAL;
2894
 
2215
	return 0;
2895
		return -EINVAL;
Line 2216... Line 2896...
2216
}
2896
}
2217
EXPORT_SYMBOL(drm_connector_property_set_value);
2897
EXPORT_SYMBOL(drm_object_property_set_value);
2218
 
2898
 
2219
int drm_connector_property_get_value(struct drm_connector *connector,
2899
int drm_object_property_get_value(struct drm_mode_object *obj,
2220
				  struct drm_property *property, uint64_t *val)
2900
				  struct drm_property *property, uint64_t *val)
2221
{
2901
{
Line 2222... Line -...
2222
	int i;
-
 
2223
 
2902
	int i;
2224
	for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
-
 
2225
		if (connector->property_ids[i] == property->base.id) {
2903
 
2226
			*val = connector->property_values[i];
2904
	for (i = 0; i < obj->properties->count; i++) {
Line 2227... Line 2905...
2227
			break;
2905
		if (obj->properties->ids[i] == property->base.id) {
2228
		}
2906
			*val = obj->properties->values[i];
2229
	}
2907
			return 0;
2230
 
2908
		}
Line 2247... Line 2925...
2247
	int ret = 0, i;
2925
	int ret = 0, i;
2248
	int copied;
2926
	int copied;
2249
	struct drm_property_enum *prop_enum;
2927
	struct drm_property_enum *prop_enum;
2250
	struct drm_mode_property_enum __user *enum_ptr;
2928
	struct drm_mode_property_enum __user *enum_ptr;
2251
	struct drm_property_blob *prop_blob;
2929
	struct drm_property_blob *prop_blob;
2252
	uint32_t *blob_id_ptr;
2930
	uint32_t __user *blob_id_ptr;
2253
	uint64_t __user *values_ptr;
2931
	uint64_t __user *values_ptr;
2254
	uint32_t __user *blob_length_ptr;
2932
	uint32_t __user *blob_length_ptr;
Line 2255... Line 2933...
2255
 
2933
 
2256
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
2934
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line 2262... Line 2940...
2262
		ret = -EINVAL;
2940
		ret = -EINVAL;
2263
		goto done;
2941
		goto done;
2264
	}
2942
	}
2265
	property = obj_to_property(obj);
2943
	property = obj_to_property(obj);
Line 2266... Line 2944...
2266
 
2944
 
2267
	if (property->flags & DRM_MODE_PROP_ENUM) {
2945
	if (property->flags & (DRM_MODE_PROP_ENUM | DRM_MODE_PROP_BITMASK)) {
2268
		list_for_each_entry(prop_enum, &property->enum_blob_list, head)
2946
		list_for_each_entry(prop_enum, &property->enum_blob_list, head)
2269
			enum_count++;
2947
			enum_count++;
2270
	} else if (property->flags & DRM_MODE_PROP_BLOB) {
2948
	} else if (property->flags & DRM_MODE_PROP_BLOB) {
2271
		list_for_each_entry(prop_blob, &property->enum_blob_list, head)
2949
		list_for_each_entry(prop_blob, &property->enum_blob_list, head)
Line 2277... Line 2955...
2277
	strncpy(out_resp->name, property->name, DRM_PROP_NAME_LEN);
2955
	strncpy(out_resp->name, property->name, DRM_PROP_NAME_LEN);
2278
	out_resp->name[DRM_PROP_NAME_LEN-1] = 0;
2956
	out_resp->name[DRM_PROP_NAME_LEN-1] = 0;
2279
	out_resp->flags = property->flags;
2957
	out_resp->flags = property->flags;
Line 2280... Line 2958...
2280
 
2958
 
2281
	if ((out_resp->count_values >= value_count) && value_count) {
2959
	if ((out_resp->count_values >= value_count) && value_count) {
2282
		values_ptr = (uint64_t *)(unsigned long)out_resp->values_ptr;
2960
		values_ptr = (uint64_t __user *)(unsigned long)out_resp->values_ptr;
2283
		for (i = 0; i < value_count; i++) {
2961
		for (i = 0; i < value_count; i++) {
2284
			if (copy_to_user(values_ptr + i, &property->values[i], sizeof(uint64_t))) {
2962
			if (copy_to_user(values_ptr + i, &property->values[i], sizeof(uint64_t))) {
2285
				ret = -EFAULT;
2963
				ret = -EFAULT;
2286
				goto done;
2964
				goto done;
2287
			}
2965
			}
2288
		}
2966
		}
2289
	}
2967
	}
Line 2290... Line 2968...
2290
	out_resp->count_values = value_count;
2968
	out_resp->count_values = value_count;
2291
 
2969
 
2292
	if (property->flags & DRM_MODE_PROP_ENUM) {
2970
	if (property->flags & (DRM_MODE_PROP_ENUM | DRM_MODE_PROP_BITMASK)) {
2293
		if ((out_resp->count_enum_blobs >= enum_count) && enum_count) {
2971
		if ((out_resp->count_enum_blobs >= enum_count) && enum_count) {
2294
			copied = 0;
2972
			copied = 0;
Line 2295... Line 2973...
2295
			enum_ptr = (struct drm_mode_property_enum *)(unsigned long)out_resp->enum_blob_ptr;
2973
			enum_ptr = (struct drm_mode_property_enum __user *)(unsigned long)out_resp->enum_blob_ptr;
2296
			list_for_each_entry(prop_enum, &property->enum_blob_list, head) {
2974
			list_for_each_entry(prop_enum, &property->enum_blob_list, head) {
2297
 
2975
 
Line 2312... Line 2990...
2312
	}
2990
	}
Line 2313... Line 2991...
2313
 
2991
 
2314
	if (property->flags & DRM_MODE_PROP_BLOB) {
2992
	if (property->flags & DRM_MODE_PROP_BLOB) {
2315
		if ((out_resp->count_enum_blobs >= blob_count) && blob_count) {
2993
		if ((out_resp->count_enum_blobs >= blob_count) && blob_count) {
2316
			copied = 0;
2994
			copied = 0;
2317
			blob_id_ptr = (uint32_t *)(unsigned long)out_resp->enum_blob_ptr;
2995
			blob_id_ptr = (uint32_t __user *)(unsigned long)out_resp->enum_blob_ptr;
Line 2318... Line 2996...
2318
			blob_length_ptr = (uint32_t *)(unsigned long)out_resp->values_ptr;
2996
			blob_length_ptr = (uint32_t __user *)(unsigned long)out_resp->values_ptr;
2319
 
2997
 
2320
			list_for_each_entry(prop_blob, &property->enum_blob_list, head) {
2998
			list_for_each_entry(prop_blob, &property->enum_blob_list, head) {
2321
				if (put_user(prop_blob->base.id, blob_id_ptr + copied)) {
2999
				if (put_user(prop_blob->base.id, blob_id_ptr + copied)) {
Line 2341... Line 3019...
2341
 
3019
 
2342
static struct drm_property_blob *drm_property_create_blob(struct drm_device *dev, int length,
3020
static struct drm_property_blob *drm_property_create_blob(struct drm_device *dev, int length,
2343
							  void *data)
3021
							  void *data)
2344
{
3022
{
-
 
3023
	struct drm_property_blob *blob;
Line 2345... Line 3024...
2345
	struct drm_property_blob *blob;
3024
	int ret;
2346
 
3025
 
Line 2347... Line 3026...
2347
	if (!length || !data)
3026
	if (!length || !data)
2348
		return NULL;
3027
		return NULL;
2349
 
3028
 
Line 2350... Line 3029...
2350
	blob = kzalloc(sizeof(struct drm_property_blob)+length, GFP_KERNEL);
3029
	blob = kzalloc(sizeof(struct drm_property_blob)+length, GFP_KERNEL);
-
 
3030
	if (!blob)
-
 
3031
		return NULL;
-
 
3032
 
-
 
3033
	ret = drm_mode_object_get(dev, &blob->base, DRM_MODE_OBJECT_BLOB);
-
 
3034
	if (ret) {
2351
	if (!blob)
3035
		kfree(blob);
Line 2352... Line 3036...
2352
		return NULL;
3036
		return NULL;
Line 2353... Line -...
2353
 
-
 
2354
	blob->data = (void *)((char *)blob + sizeof(struct drm_property_blob));
-
 
2355
	blob->length = length;
3037
	}
2356
 
3038
 
2357
	memcpy(blob->data, data, length);
3039
	blob->length = length;
Line 2358... Line 3040...
2358
 
3040
 
Line 2376... Line 3058...
2376
{
3058
{
2377
	struct drm_mode_object *obj;
3059
	struct drm_mode_object *obj;
2378
	struct drm_mode_get_blob *out_resp = data;
3060
	struct drm_mode_get_blob *out_resp = data;
2379
	struct drm_property_blob *blob;
3061
	struct drm_property_blob *blob;
2380
	int ret = 0;
3062
	int ret = 0;
2381
	void *blob_ptr;
3063
	void __user *blob_ptr;
Line 2382... Line 3064...
2382
 
3064
 
2383
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
3065
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line 2384... Line 3066...
2384
		return -EINVAL;
3066
		return -EINVAL;
Line 2390... Line 3072...
2390
		goto done;
3072
		goto done;
2391
	}
3073
	}
2392
	blob = obj_to_blob(obj);
3074
	blob = obj_to_blob(obj);
Line 2393... Line 3075...
2393
 
3075
 
2394
	if (out_resp->length == blob->length) {
3076
	if (out_resp->length == blob->length) {
2395
		blob_ptr = (void *)(unsigned long)out_resp->data;
3077
		blob_ptr = (void __user *)(unsigned long)out_resp->data;
2396
		if (copy_to_user(blob_ptr, blob->data, blob->length)){
3078
		if (copy_to_user(blob_ptr, blob->data, blob->length)){
2397
			ret = -EFAULT;
3079
			ret = -EFAULT;
2398
			goto done;
3080
			goto done;
2399
		}
3081
		}
Line 2408... Line 3090...
2408
 
3090
 
2409
int drm_mode_connector_update_edid_property(struct drm_connector *connector,
3091
int drm_mode_connector_update_edid_property(struct drm_connector *connector,
2410
					    struct edid *edid)
3092
					    struct edid *edid)
2411
{
3093
{
2412
	struct drm_device *dev = connector->dev;
3094
	struct drm_device *dev = connector->dev;
Line 2413... Line 3095...
2413
	int ret = 0, size;
3095
	int ret, size;
2414
 
3096
 
Line 2415... Line 3097...
2415
	if (connector->edid_blob_ptr)
3097
	if (connector->edid_blob_ptr)
Line 2433... Line 3115...
2433
	return ret;
3115
	return ret;
2434
}
3116
}
2435
EXPORT_SYMBOL(drm_mode_connector_update_edid_property);
3117
EXPORT_SYMBOL(drm_mode_connector_update_edid_property);
Line 2436... Line 3118...
2436
 
3118
 
-
 
3119
#if 0
2437
#if 0
3120
 
-
 
3121
static int drm_mode_connector_set_obj_prop(struct drm_mode_object *obj,
-
 
3122
					   struct drm_property *property,
-
 
3123
					   uint64_t value)
-
 
3124
{
-
 
3125
	int ret = -EINVAL;
-
 
3126
	struct drm_connector *connector = obj_to_connector(obj);
-
 
3127
 
-
 
3128
	/* Do DPMS ourselves */
-
 
3129
	if (property == connector->dev->mode_config.dpms_property) {
-
 
3130
		if (connector->funcs->dpms)
-
 
3131
			(*connector->funcs->dpms)(connector, (int)value);
-
 
3132
		ret = 0;
-
 
3133
	} else if (connector->funcs->set_property)
-
 
3134
		ret = connector->funcs->set_property(connector, property, value);
-
 
3135
 
-
 
3136
	/* store the property value if successful */
-
 
3137
	if (!ret)
-
 
3138
		drm_connector_property_set_value(connector, property, value);
-
 
3139
	return ret;
-
 
3140
}
-
 
3141
 
-
 
3142
static int drm_mode_crtc_set_obj_prop(struct drm_mode_object *obj,
-
 
3143
				      struct drm_property *property,
-
 
3144
				      uint64_t value)
-
 
3145
{
-
 
3146
	int ret = -EINVAL;
-
 
3147
	struct drm_crtc *crtc = obj_to_crtc(obj);
-
 
3148
 
-
 
3149
	if (crtc->funcs->set_property)
-
 
3150
		ret = crtc->funcs->set_property(crtc, property, value);
-
 
3151
	if (!ret)
-
 
3152
		drm_object_property_set_value(obj, property, value);
-
 
3153
 
-
 
3154
	return ret;
-
 
3155
}
-
 
3156
 
2438
int drm_mode_connector_property_set_ioctl(struct drm_device *dev,
3157
static int drm_mode_plane_set_obj_prop(struct drm_mode_object *obj,
-
 
3158
				      struct drm_property *property,
2439
				       void *data, struct drm_file *file_priv)
3159
				      uint64_t value)
2440
{
-
 
2441
	struct drm_mode_connector_set_property *out_resp = data;
-
 
2442
	struct drm_mode_object *obj;
-
 
2443
	struct drm_property *property;
-
 
2444
	struct drm_connector *connector;
3160
{
-
 
3161
	int ret = -EINVAL;
-
 
3162
	struct drm_plane *plane = obj_to_plane(obj);
-
 
3163
 
-
 
3164
	if (plane->funcs->set_property)
-
 
3165
		ret = plane->funcs->set_property(plane, property, value);
-
 
3166
	if (!ret)
-
 
3167
		drm_object_property_set_value(obj, property, value);
-
 
3168
 
-
 
3169
	return ret;
-
 
3170
}
-
 
3171
 
-
 
3172
int drm_mode_obj_get_properties_ioctl(struct drm_device *dev, void *data,
-
 
3173
				      struct drm_file *file_priv)
-
 
3174
{
-
 
3175
	struct drm_mode_obj_get_properties *arg = data;
-
 
3176
	struct drm_mode_object *obj;
2445
	int ret = -EINVAL;
3177
	int ret = 0;
-
 
3178
	int i;
-
 
3179
	int copied = 0;
-
 
3180
	int props_count = 0;
-
 
3181
	uint32_t __user *props_ptr;
Line 2446... Line 3182...
2446
	int i;
3182
	uint64_t __user *prop_values_ptr;
2447
 
3183
 
Line 2448... Line 3184...
2448
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
3184
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
Line 2449... Line 3185...
2449
		return -EINVAL;
3185
		return -EINVAL;
2450
 
3186
 
-
 
3187
	mutex_lock(&dev->mode_config.mutex);
2451
	mutex_lock(&dev->mode_config.mutex);
3188
 
2452
 
3189
	obj = drm_mode_object_find(dev, arg->obj_id, arg->obj_type);
2453
	obj = drm_mode_object_find(dev, out_resp->connector_id, DRM_MODE_OBJECT_CONNECTOR);
3190
	if (!obj) {
2454
	if (!obj) {
-
 
2455
		goto out;
3191
		ret = -EINVAL;
2456
	}
-
 
2457
	connector = obj_to_connector(obj);
3192
		goto out;
2458
 
3193
	}
Line -... Line 3194...
-
 
3194
	if (!obj->properties) {
-
 
3195
		ret = -EINVAL;
-
 
3196
		goto out;
-
 
3197
	}
-
 
3198
 
-
 
3199
	props_count = obj->properties->count;
-
 
3200
 
-
 
3201
	/* This ioctl is called twice, once to determine how much space is
-
 
3202
	 * needed, and the 2nd time to fill it. */
2459
	for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
3203
	if ((arg->count_props >= props_count) && props_count) {
-
 
3204
		copied = 0;
-
 
3205
		props_ptr = (uint32_t __user *)(unsigned long)(arg->props_ptr);
-
 
3206
		prop_values_ptr = (uint64_t __user *)(unsigned long)
2460
		if (connector->property_ids[i] == out_resp->prop_id)
3207
				  (arg->prop_values_ptr);
2461
			break;
3208
		for (i = 0; i < props_count; i++) {
2462
	}
-
 
2463
 
3209
			if (put_user(obj->properties->ids[i],
-
 
3210
				     props_ptr + copied)) {
2464
	if (i == DRM_CONNECTOR_MAX_PROPERTY) {
3211
				ret = -EFAULT;
2465
		goto out;
3212
				goto out;
2466
	}
3213
	}
-
 
3214
			if (put_user(obj->properties->values[i],
-
 
3215
				     prop_values_ptr + copied)) {
-
 
3216
				ret = -EFAULT;
2467
 
3217
		goto out;
-
 
3218
	}
-
 
3219
			copied++;
-
 
3220
		}
-
 
3221
	}
Line -... Line 3222...
-
 
3222
	arg->count_props = props_count;
-
 
3223
out:
-
 
3224
	mutex_unlock(&dev->mode_config.mutex);
-
 
3225
	return ret;
-
 
3226
}
-
 
3227
 
-
 
3228
int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data,
-
 
3229
				    struct drm_file *file_priv)
-
 
3230
{
-
 
3231
	struct drm_mode_obj_set_property *arg = data;
2468
	obj = drm_mode_object_find(dev, out_resp->prop_id, DRM_MODE_OBJECT_PROPERTY);
3232
	struct drm_mode_object *arg_obj;
-
 
3233
	struct drm_mode_object *prop_obj;
-
 
3234
	struct drm_property *property;
-
 
3235
	int ret = -EINVAL;
-
 
3236
	int i;
-
 
3237
 
-
 
3238
	if (!drm_core_check_feature(dev, DRIVER_MODESET))
-
 
3239
		return -EINVAL;
-
 
3240
 
2469
	if (!obj) {
3241
	mutex_lock(&dev->mode_config.mutex);
Line -... Line 3242...
-
 
3242
 
2470
		goto out;
3243
	arg_obj = drm_mode_object_find(dev, arg->obj_id, arg->obj_type);
-
 
3244
	if (!arg_obj)
-
 
3245
		goto out;
2471
	}
3246
	if (!arg_obj->properties)
2472
	property = obj_to_property(obj);
3247
		goto out;
Line 2473... Line 3248...
2473
 
3248
 
-
 
3249
	for (i = 0; i < arg_obj->properties->count; i++)
-
 
3250
		if (arg_obj->properties->ids[i] == arg->prop_id)
2474
	if (property->flags & DRM_MODE_PROP_IMMUTABLE)
3251
			break;
2475
		goto out;
-
 
2476
 
-
 
2477
	if (property->flags & DRM_MODE_PROP_RANGE) {
3252
 
2478
		if (out_resp->value < property->values[0])
-
 
2479
			goto out;
-
 
2480
 
-
 
2481
		if (out_resp->value > property->values[1])
-
 
2482
			goto out;
3253
	if (i == arg_obj->properties->count)
2483
	} else {
3254
		goto out;
2484
		int found = 0;
3255
 
2485
		for (i = 0; i < property->num_values; i++) {
-
 
2486
			if (property->values[i] == out_resp->value) {
-
 
Line 2487... Line 3256...
2487
				found = 1;
3256
	prop_obj = drm_mode_object_find(dev, arg->prop_id,
-
 
3257
					DRM_MODE_OBJECT_PROPERTY);
2488
				break;
3258
	if (!prop_obj)
2489
			}
3259
			goto out;
-
 
3260
	property = obj_to_property(prop_obj);
-
 
3261
 
2490
		}
3262
	if (!drm_property_change_is_valid(property, arg->value))
2491
		if (!found) {
3263
			goto out;
2492
			goto out;
3264
 
2493
		}
3265
	switch (arg_obj->type) {
-
 
3266
	case DRM_MODE_OBJECT_CONNECTOR:
-
 
3267
		ret = drm_mode_connector_set_obj_prop(arg_obj, property,
Line 2494... Line -...
2494
	}
-
 
2495
 
-
 
2496
	/* Do DPMS ourselves */
-
 
2497
	if (property == connector->dev->mode_config.dpms_property) {
3268
						      arg->value);
2498
		if (connector->funcs->dpms)
3269
		break;
2499
			(*connector->funcs->dpms)(connector, (int) out_resp->value);
3270
	case DRM_MODE_OBJECT_CRTC:
2500
		ret = 0;
3271
		ret = drm_mode_crtc_set_obj_prop(arg_obj, property, arg->value);
2501
	} else if (connector->funcs->set_property)
3272
		break;
Line 2538... Line 3309...
2538
		}
3309
		}
2539
	}
3310
	}
2540
}
3311
}
2541
EXPORT_SYMBOL(drm_mode_connector_detach_encoder);
3312
EXPORT_SYMBOL(drm_mode_connector_detach_encoder);
Line 2542... Line 3313...
2542
 
3313
 
2543
bool drm_mode_crtc_set_gamma_size(struct drm_crtc *crtc,
3314
int drm_mode_crtc_set_gamma_size(struct drm_crtc *crtc,
2544
				  int gamma_size)
3315
				  int gamma_size)
2545
{
3316
{
Line 2546... Line 3317...
2546
	crtc->gamma_size = gamma_size;
3317
	crtc->gamma_size = gamma_size;
2547
 
3318
 
2548
	crtc->gamma_store = kzalloc(gamma_size * sizeof(uint16_t) * 3, GFP_KERNEL);
3319
	crtc->gamma_store = kzalloc(gamma_size * sizeof(uint16_t) * 3, GFP_KERNEL);
2549
	if (!crtc->gamma_store) {
3320
	if (!crtc->gamma_store) {
2550
		crtc->gamma_size = 0;
3321
		crtc->gamma_size = 0;
Line 2551... Line 3322...
2551
		return false;
3322
		return -ENOMEM;
2552
	}
3323
	}
2553
 
3324
 
Line 2554... Line 3325...
2554
	return true;
3325
	return 0;
2555
}
3326
}
Line 2575... Line 3346...
2575
		ret = -EINVAL;
3346
		ret = -EINVAL;
2576
		goto out;
3347
		goto out;
2577
	}
3348
	}
2578
	crtc = obj_to_crtc(obj);
3349
	crtc = obj_to_crtc(obj);
Line -... Line 3350...
-
 
3350
 
-
 
3351
	if (crtc->funcs->gamma_set == NULL) {
-
 
3352
		ret = -ENOSYS;
-
 
3353
		goto out;
-
 
3354
	}
2579
 
3355
 
2580
	/* memcpy into gamma store */
3356
	/* memcpy into gamma store */
2581
	if (crtc_lut->gamma_size != crtc->gamma_size) {
3357
	if (crtc_lut->gamma_size != crtc->gamma_size) {
2582
		ret = -EINVAL;
3358
		ret = -EINVAL;
2583
		goto out;
3359
		goto out;
Line 2680... Line 3456...
2680
	list_for_each_entry(connector, &dev->mode_config.connector_list, head)
3456
	list_for_each_entry(connector, &dev->mode_config.connector_list, head)
2681
		if (connector->funcs->reset)
3457
		if (connector->funcs->reset)
2682
			connector->funcs->reset(connector);
3458
			connector->funcs->reset(connector);
2683
}
3459
}
2684
EXPORT_SYMBOL(drm_mode_config_reset);
3460
EXPORT_SYMBOL(drm_mode_config_reset);
-
 
3461
/*
-
 
3462
 * Just need to support RGB formats here for compat with code that doesn't
-
 
3463
 * use pixel formats directly yet.
-
 
3464
 */
-
 
3465
void drm_fb_get_bpp_depth(uint32_t format, unsigned int *depth,
-
 
3466
			  int *bpp)
-
 
3467
{
-
 
3468
	switch (format) {
-
 
3469
	case DRM_FORMAT_RGB332:
-
 
3470
	case DRM_FORMAT_BGR233:
-
 
3471
		*depth = 8;
-
 
3472
		*bpp = 8;
-
 
3473
		break;
-
 
3474
	case DRM_FORMAT_XRGB1555:
-
 
3475
	case DRM_FORMAT_XBGR1555:
-
 
3476
	case DRM_FORMAT_RGBX5551:
-
 
3477
	case DRM_FORMAT_BGRX5551:
-
 
3478
	case DRM_FORMAT_ARGB1555:
-
 
3479
	case DRM_FORMAT_ABGR1555:
-
 
3480
	case DRM_FORMAT_RGBA5551:
-
 
3481
	case DRM_FORMAT_BGRA5551:
-
 
3482
		*depth = 15;
-
 
3483
		*bpp = 16;
-
 
3484
		break;
-
 
3485
	case DRM_FORMAT_RGB565:
-
 
3486
	case DRM_FORMAT_BGR565:
-
 
3487
		*depth = 16;
-
 
3488
		*bpp = 16;
-
 
3489
		break;
-
 
3490
	case DRM_FORMAT_RGB888:
-
 
3491
	case DRM_FORMAT_BGR888:
-
 
3492
		*depth = 24;
-
 
3493
		*bpp = 24;
-
 
3494
		break;
-
 
3495
	case DRM_FORMAT_XRGB8888:
-
 
3496
	case DRM_FORMAT_XBGR8888:
-
 
3497
	case DRM_FORMAT_RGBX8888:
-
 
3498
	case DRM_FORMAT_BGRX8888:
-
 
3499
		*depth = 24;
-
 
3500
		*bpp = 32;
-
 
3501
		break;
-
 
3502
	case DRM_FORMAT_XRGB2101010:
-
 
3503
	case DRM_FORMAT_XBGR2101010:
-
 
3504
	case DRM_FORMAT_RGBX1010102:
-
 
3505
	case DRM_FORMAT_BGRX1010102:
-
 
3506
	case DRM_FORMAT_ARGB2101010:
-
 
3507
	case DRM_FORMAT_ABGR2101010:
-
 
3508
	case DRM_FORMAT_RGBA1010102:
-
 
3509
	case DRM_FORMAT_BGRA1010102:
-
 
3510
		*depth = 30;
-
 
3511
		*bpp = 32;
-
 
3512
		break;
-
 
3513
	case DRM_FORMAT_ARGB8888:
-
 
3514
	case DRM_FORMAT_ABGR8888:
-
 
3515
	case DRM_FORMAT_RGBA8888:
-
 
3516
	case DRM_FORMAT_BGRA8888:
-
 
3517
		*depth = 32;
-
 
3518
		*bpp = 32;
-
 
3519
		break;
-
 
3520
	default:
-
 
3521
		DRM_DEBUG_KMS("unsupported pixel format\n");
-
 
3522
		*depth = 0;
-
 
3523
		*bpp = 0;
-
 
3524
		break;
-
 
3525
	}
-
 
3526
}
-
 
3527
EXPORT_SYMBOL(drm_fb_get_bpp_depth);
-
 
3528
 
-
 
3529
/**
-
 
3530
 * drm_format_num_planes - get the number of planes for format
-
 
3531
 * @format: pixel format (DRM_FORMAT_*)
-
 
3532
 *
-
 
3533
 * RETURNS:
-
 
3534
 * The number of planes used by the specified pixel format.
-
 
3535
 */
-
 
3536
int drm_format_num_planes(uint32_t format)
-
 
3537
{
-
 
3538
	switch (format) {
-
 
3539
	case DRM_FORMAT_YUV410:
-
 
3540
	case DRM_FORMAT_YVU410:
-
 
3541
	case DRM_FORMAT_YUV411:
-
 
3542
	case DRM_FORMAT_YVU411:
-
 
3543
	case DRM_FORMAT_YUV420:
-
 
3544
	case DRM_FORMAT_YVU420:
-
 
3545
	case DRM_FORMAT_YUV422:
-
 
3546
	case DRM_FORMAT_YVU422:
-
 
3547
	case DRM_FORMAT_YUV444:
-
 
3548
	case DRM_FORMAT_YVU444:
-
 
3549
		return 3;
-
 
3550
	case DRM_FORMAT_NV12:
-
 
3551
	case DRM_FORMAT_NV21:
-
 
3552
	case DRM_FORMAT_NV16:
-
 
3553
	case DRM_FORMAT_NV61:
-
 
3554
	case DRM_FORMAT_NV24:
-
 
3555
	case DRM_FORMAT_NV42:
-
 
3556
		return 2;
-
 
3557
	default:
-
 
3558
		return 1;
-
 
3559
	}
-
 
3560
}
-
 
3561
EXPORT_SYMBOL(drm_format_num_planes);
-
 
3562
 
-
 
3563
/**
-
 
3564
 * drm_format_plane_cpp - determine the bytes per pixel value
-
 
3565
 * @format: pixel format (DRM_FORMAT_*)
-
 
3566
 * @plane: plane index
-
 
3567
 *
-
 
3568
 * RETURNS:
-
 
3569
 * The bytes per pixel value for the specified plane.
-
 
3570
 */
-
 
3571
int drm_format_plane_cpp(uint32_t format, int plane)
-
 
3572
{
-
 
3573
	unsigned int depth;
-
 
3574
	int bpp;
-
 
3575
 
-
 
3576
	if (plane >= drm_format_num_planes(format))
-
 
3577
		return 0;
-
 
3578
 
-
 
3579
	switch (format) {
-
 
3580
	case DRM_FORMAT_YUYV:
-
 
3581
	case DRM_FORMAT_YVYU:
-
 
3582
	case DRM_FORMAT_UYVY:
-
 
3583
	case DRM_FORMAT_VYUY:
-
 
3584
		return 2;
-
 
3585
	case DRM_FORMAT_NV12:
-
 
3586
	case DRM_FORMAT_NV21:
-
 
3587
	case DRM_FORMAT_NV16:
-
 
3588
	case DRM_FORMAT_NV61:
-
 
3589
	case DRM_FORMAT_NV24:
-
 
3590
	case DRM_FORMAT_NV42:
-
 
3591
		return plane ? 2 : 1;
-
 
3592
	case DRM_FORMAT_YUV410:
-
 
3593
	case DRM_FORMAT_YVU410:
-
 
3594
	case DRM_FORMAT_YUV411:
-
 
3595
	case DRM_FORMAT_YVU411:
-
 
3596
	case DRM_FORMAT_YUV420:
-
 
3597
	case DRM_FORMAT_YVU420:
-
 
3598
	case DRM_FORMAT_YUV422:
-
 
3599
	case DRM_FORMAT_YVU422:
-
 
3600
	case DRM_FORMAT_YUV444:
-
 
3601
	case DRM_FORMAT_YVU444:
-
 
3602
		return 1;
-
 
3603
	default:
-
 
3604
		drm_fb_get_bpp_depth(format, &depth, &bpp);
-
 
3605
		return bpp >> 3;
-
 
3606
	}
-
 
3607
}
-
 
3608
EXPORT_SYMBOL(drm_format_plane_cpp);
-
 
3609
 
-
 
3610
/**
-
 
3611
 * drm_format_horz_chroma_subsampling - get the horizontal chroma subsampling factor
-
 
3612
 * @format: pixel format (DRM_FORMAT_*)
-
 
3613
 *
-
 
3614
 * RETURNS:
-
 
3615
 * The horizontal chroma subsampling factor for the
-
 
3616
 * specified pixel format.
-
 
3617
 */
-
 
3618
int drm_format_horz_chroma_subsampling(uint32_t format)
-
 
3619
{
-
 
3620
	switch (format) {
-
 
3621
	case DRM_FORMAT_YUV411:
-
 
3622
	case DRM_FORMAT_YVU411:
-
 
3623
	case DRM_FORMAT_YUV410:
-
 
3624
	case DRM_FORMAT_YVU410:
-
 
3625
		return 4;
-
 
3626
	case DRM_FORMAT_YUYV:
-
 
3627
	case DRM_FORMAT_YVYU:
-
 
3628
	case DRM_FORMAT_UYVY:
-
 
3629
	case DRM_FORMAT_VYUY:
-
 
3630
	case DRM_FORMAT_NV12:
-
 
3631
	case DRM_FORMAT_NV21:
-
 
3632
	case DRM_FORMAT_NV16:
-
 
3633
	case DRM_FORMAT_NV61:
-
 
3634
	case DRM_FORMAT_YUV422:
-
 
3635
	case DRM_FORMAT_YVU422:
-
 
3636
	case DRM_FORMAT_YUV420:
-
 
3637
	case DRM_FORMAT_YVU420:
-
 
3638
		return 2;
-
 
3639
	default:
-
 
3640
		return 1;
-
 
3641
	}
-
 
3642
}
-
 
3643
EXPORT_SYMBOL(drm_format_horz_chroma_subsampling);
-
 
3644
 
-
 
3645
/**
-
 
3646
 * drm_format_vert_chroma_subsampling - get the vertical chroma subsampling factor
-
 
3647
 * @format: pixel format (DRM_FORMAT_*)
-
 
3648
 *
-
 
3649
 * RETURNS:
-
 
3650
 * The vertical chroma subsampling factor for the
-
 
3651
 * specified pixel format.
-
 
3652
 */
-
 
3653
int drm_format_vert_chroma_subsampling(uint32_t format)
-
 
3654
{
-
 
3655
	switch (format) {
-
 
3656
	case DRM_FORMAT_YUV410:
-
 
3657
	case DRM_FORMAT_YVU410:
-
 
3658
		return 4;
-
 
3659
	case DRM_FORMAT_YUV420:
-
 
3660
	case DRM_FORMAT_YVU420:
-
 
3661
	case DRM_FORMAT_NV12:
-
 
3662
	case DRM_FORMAT_NV21:
-
 
3663
		return 2;
-
 
3664
	default:
-
 
3665
		return 1;
-
 
3666
	}
-
 
3667
}
-
 
3668
EXPORT_SYMBOL(drm_format_vert_chroma_subsampling);