Subversion Repositories Kolibri OS

Rev

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

Rev 5271 Rev 6084
Line 33... Line 33...
33
#include 
33
#include 
34
#include 
34
#include 
35
#include 
35
#include 
36
#include 
36
#include 
37
#include 
37
#include 
-
 
38
#include 
-
 
39
#include 
38
#include 
40
#include 
Line 39... Line 41...
39
 
41
 
Line 40... Line 42...
40
#include "drm_crtc_internal.h"
42
#include "drm_crtc_internal.h"
Line 274... Line 276...
274
		if (hblank_percentage < 20 * HV_FACTOR)
276
		if (hblank_percentage < 20 * HV_FACTOR)
275
			hblank_percentage = 20 * HV_FACTOR;
277
			hblank_percentage = 20 * HV_FACTOR;
276
		hblank = drm_mode->hdisplay * hblank_percentage /
278
		hblank = drm_mode->hdisplay * hblank_percentage /
277
			 (100 * HV_FACTOR - hblank_percentage);
279
			 (100 * HV_FACTOR - hblank_percentage);
278
		hblank -= hblank % (2 * CVT_H_GRANULARITY);
280
		hblank -= hblank % (2 * CVT_H_GRANULARITY);
279
		/* 14. find the total pixes per line */
281
		/* 14. find the total pixels per line */
280
		drm_mode->htotal = drm_mode->hdisplay + hblank;
282
		drm_mode->htotal = drm_mode->hdisplay + hblank;
281
		drm_mode->hsync_end = drm_mode->hdisplay + hblank / 2;
283
		drm_mode->hsync_end = drm_mode->hdisplay + hblank / 2;
282
		drm_mode->hsync_start = drm_mode->hsync_end -
284
		drm_mode->hsync_start = drm_mode->hsync_end -
283
			(drm_mode->htotal * CVT_HSYNC_PERCENTAGE) / 100;
285
			(drm_mode->htotal * CVT_HSYNC_PERCENTAGE) / 100;
284
		drm_mode->hsync_start += CVT_H_GRANULARITY -
286
		drm_mode->hsync_start += CVT_H_GRANULARITY -
Line 611... Line 613...
611
		dmode->flags |= DRM_MODE_FLAG_DBLCLK;
613
		dmode->flags |= DRM_MODE_FLAG_DBLCLK;
612
	drm_mode_set_name(dmode);
614
	drm_mode_set_name(dmode);
613
}
615
}
614
EXPORT_SYMBOL_GPL(drm_display_mode_from_videomode);
616
EXPORT_SYMBOL_GPL(drm_display_mode_from_videomode);
Line -... Line 617...
-
 
617
 
-
 
618
/**
-
 
619
 * drm_display_mode_to_videomode - fill in @vm using @dmode,
-
 
620
 * @dmode: drm_display_mode structure to use as source
-
 
621
 * @vm: videomode structure to use as destination
-
 
622
 *
-
 
623
 * Fills out @vm using the display mode specified in @dmode.
-
 
624
 */
-
 
625
void drm_display_mode_to_videomode(const struct drm_display_mode *dmode,
-
 
626
				   struct videomode *vm)
-
 
627
{
-
 
628
	vm->hactive = dmode->hdisplay;
-
 
629
	vm->hfront_porch = dmode->hsync_start - dmode->hdisplay;
-
 
630
	vm->hsync_len = dmode->hsync_end - dmode->hsync_start;
-
 
631
	vm->hback_porch = dmode->htotal - dmode->hsync_end;
-
 
632
 
-
 
633
	vm->vactive = dmode->vdisplay;
-
 
634
	vm->vfront_porch = dmode->vsync_start - dmode->vdisplay;
-
 
635
	vm->vsync_len = dmode->vsync_end - dmode->vsync_start;
-
 
636
	vm->vback_porch = dmode->vtotal - dmode->vsync_end;
-
 
637
 
-
 
638
	vm->pixelclock = dmode->clock * 1000;
-
 
639
 
-
 
640
	vm->flags = 0;
-
 
641
	if (dmode->flags & DRM_MODE_FLAG_PHSYNC)
-
 
642
		vm->flags |= DISPLAY_FLAGS_HSYNC_HIGH;
-
 
643
	else if (dmode->flags & DRM_MODE_FLAG_NHSYNC)
-
 
644
		vm->flags |= DISPLAY_FLAGS_HSYNC_LOW;
-
 
645
	if (dmode->flags & DRM_MODE_FLAG_PVSYNC)
-
 
646
		vm->flags |= DISPLAY_FLAGS_VSYNC_HIGH;
-
 
647
	else if (dmode->flags & DRM_MODE_FLAG_NVSYNC)
-
 
648
		vm->flags |= DISPLAY_FLAGS_VSYNC_LOW;
-
 
649
	if (dmode->flags & DRM_MODE_FLAG_INTERLACE)
-
 
650
		vm->flags |= DISPLAY_FLAGS_INTERLACED;
-
 
651
	if (dmode->flags & DRM_MODE_FLAG_DBLSCAN)
-
 
652
		vm->flags |= DISPLAY_FLAGS_DOUBLESCAN;
-
 
653
	if (dmode->flags & DRM_MODE_FLAG_DBLCLK)
-
 
654
		vm->flags |= DISPLAY_FLAGS_DOUBLECLK;
-
 
655
}
-
 
656
EXPORT_SYMBOL_GPL(drm_display_mode_to_videomode);
615
 
657
 
616
#ifdef CONFIG_OF
658
#ifdef CONFIG_OF
617
/**
659
/**
618
 * of_get_drm_display_mode - get a drm_display_mode from devicetree
660
 * of_get_drm_display_mode - get a drm_display_mode from devicetree
619
 * @np: device_node with the timing specification
661
 * @np: device_node with the timing specification
Line 735... Line 777...
735
 * - The CRTC_INTERLACE_HALVE_V flag can be used to halve vertical timings of
777
 * - The CRTC_INTERLACE_HALVE_V flag can be used to halve vertical timings of
736
 *   interlaced modes.
778
 *   interlaced modes.
737
 * - The CRTC_STEREO_DOUBLE flag can be used to compute the timings for
779
 * - The CRTC_STEREO_DOUBLE flag can be used to compute the timings for
738
 *   buffers containing two eyes (only adjust the timings when needed, eg. for
780
 *   buffers containing two eyes (only adjust the timings when needed, eg. for
739
 *   "frame packing" or "side by side full").
781
 *   "frame packing" or "side by side full").
-
 
782
 * - The CRTC_NO_DBLSCAN and CRTC_NO_VSCAN flags request that adjustment *not*
-
 
783
 *   be performed for doublescan and vscan > 1 modes respectively.
740
 */
784
 */
741
void drm_mode_set_crtcinfo(struct drm_display_mode *p, int adjust_flags)
785
void drm_mode_set_crtcinfo(struct drm_display_mode *p, int adjust_flags)
742
{
786
{
743
	if ((p == NULL) || ((p->type & DRM_MODE_TYPE_CRTC_C) == DRM_MODE_TYPE_BUILTIN))
787
	if ((p == NULL) || ((p->type & DRM_MODE_TYPE_CRTC_C) == DRM_MODE_TYPE_BUILTIN))
744
		return;
788
		return;
Line 761... Line 805...
761
			p->crtc_vsync_end /= 2;
805
			p->crtc_vsync_end /= 2;
762
			p->crtc_vtotal /= 2;
806
			p->crtc_vtotal /= 2;
763
		}
807
		}
764
	}
808
	}
Line -... Line 809...
-
 
809
 
765
 
810
	if (!(adjust_flags & CRTC_NO_DBLSCAN)) {
766
	if (p->flags & DRM_MODE_FLAG_DBLSCAN) {
811
		if (p->flags & DRM_MODE_FLAG_DBLSCAN) {
767
		p->crtc_vdisplay *= 2;
812
			p->crtc_vdisplay *= 2;
768
		p->crtc_vsync_start *= 2;
813
			p->crtc_vsync_start *= 2;
769
		p->crtc_vsync_end *= 2;
814
			p->crtc_vsync_end *= 2;
770
		p->crtc_vtotal *= 2;
815
			p->crtc_vtotal *= 2;
-
 
816
		}
Line -... Line 817...
-
 
817
	}
771
	}
818
 
772
 
819
	if (!(adjust_flags & CRTC_NO_VSCAN)) {
773
	if (p->vscan > 1) {
820
		if (p->vscan > 1) {
774
		p->crtc_vdisplay *= p->vscan;
821
			p->crtc_vdisplay *= p->vscan;
775
		p->crtc_vsync_start *= p->vscan;
822
			p->crtc_vsync_start *= p->vscan;
776
		p->crtc_vsync_end *= p->vscan;
823
			p->crtc_vsync_end *= p->vscan;
-
 
824
			p->crtc_vtotal *= p->vscan;
Line 777... Line 825...
777
		p->crtc_vtotal *= p->vscan;
825
		}
778
	}
826
	}
Line 779... Line 827...
779
 
827
 
Line 853... Line 901...
853
 * Returns:
901
 * Returns:
854
 * True if the modes are equal, false otherwise.
902
 * True if the modes are equal, false otherwise.
855
 */
903
 */
856
bool drm_mode_equal(const struct drm_display_mode *mode1, const struct drm_display_mode *mode2)
904
bool drm_mode_equal(const struct drm_display_mode *mode1, const struct drm_display_mode *mode2)
857
{
905
{
-
 
906
	if (!mode1 && !mode2)
-
 
907
		return true;
-
 
908
 
-
 
909
	if (!mode1 || !mode2)
-
 
910
		return false;
-
 
911
 
858
	/* do clock check convert to PICOS so fb modes get matched
912
	/* do clock check convert to PICOS so fb modes get matched
859
	 * the same */
913
	 * the same */
860
	if (mode1->clock && mode2->clock) {
914
	if (mode1->clock && mode2->clock) {
861
		if (KHZ2PICOS(mode1->clock) != KHZ2PICOS(mode2->clock))
915
		if (KHZ2PICOS(mode1->clock) != KHZ2PICOS(mode2->clock))
862
			return false;
916
			return false;
Line 902... Line 956...
902
	return false;
956
	return false;
903
}
957
}
904
EXPORT_SYMBOL(drm_mode_equal_no_clocks_no_stereo);
958
EXPORT_SYMBOL(drm_mode_equal_no_clocks_no_stereo);
Line 905... Line 959...
905
 
959
 
-
 
960
/**
-
 
961
 * drm_mode_validate_basic - make sure the mode is somewhat sane
-
 
962
 * @mode: mode to check
-
 
963
 *
-
 
964
 * Check that the mode timings are at least somewhat reasonable.
-
 
965
 * Any hardware specific limits are left up for each driver to check.
-
 
966
 *
-
 
967
 * Returns:
-
 
968
 * The mode status
-
 
969
 */
-
 
970
enum drm_mode_status
-
 
971
drm_mode_validate_basic(const struct drm_display_mode *mode)
-
 
972
{
-
 
973
	if (mode->clock == 0)
-
 
974
		return MODE_CLOCK_LOW;
-
 
975
 
-
 
976
	if (mode->hdisplay == 0 ||
-
 
977
	    mode->hsync_start < mode->hdisplay ||
-
 
978
	    mode->hsync_end < mode->hsync_start ||
-
 
979
	    mode->htotal < mode->hsync_end)
-
 
980
		return MODE_H_ILLEGAL;
-
 
981
 
-
 
982
	if (mode->vdisplay == 0 ||
-
 
983
	    mode->vsync_start < mode->vdisplay ||
-
 
984
	    mode->vsync_end < mode->vsync_start ||
-
 
985
	    mode->vtotal < mode->vsync_end)
-
 
986
		return MODE_V_ILLEGAL;
-
 
987
 
-
 
988
	return MODE_OK;
-
 
989
}
-
 
990
EXPORT_SYMBOL(drm_mode_validate_basic);
-
 
991
 
906
/**
992
/**
907
 * drm_mode_validate_size - make sure modes adhere to size constraints
-
 
908
 * @dev: DRM device
993
 * drm_mode_validate_size - make sure modes adhere to size constraints
909
 * @mode_list: list of modes to check
994
 * @mode: mode to check
910
 * @maxX: maximum width
995
 * @maxX: maximum width
911
 * @maxY: maximum height
996
 * @maxY: maximum height
912
 *
997
 *
913
 * This function is a helper which can be used to validate modes against size
998
 * This function is a helper which can be used to validate modes against size
914
 * limitations of the DRM device/connector. If a mode is too big its status
999
 * limitations of the DRM device/connector. If a mode is too big its status
915
 * member is updated with the appropriate validation failure code. The list
1000
 * member is updated with the appropriate validation failure code. The list
-
 
1001
 * itself is not changed.
-
 
1002
 *
-
 
1003
 * Returns:
916
 * itself is not changed.
1004
 * The mode status
917
 */
1005
 */
918
void drm_mode_validate_size(struct drm_device *dev,
1006
enum drm_mode_status
919
			    struct list_head *mode_list,
1007
drm_mode_validate_size(const struct drm_display_mode *mode,
920
			    int maxX, int maxY)
1008
		       int maxX, int maxY)
921
{
-
 
922
	struct drm_display_mode *mode;
-
 
923
 
-
 
924
	list_for_each_entry(mode, mode_list, head) {
1009
{
925
		if (maxX > 0 && mode->hdisplay > maxX)
1010
	if (maxX > 0 && mode->hdisplay > maxX)
Line 926... Line 1011...
926
			mode->status = MODE_VIRTUAL_X;
1011
		return MODE_VIRTUAL_X;
927
 
1012
 
928
		if (maxY > 0 && mode->vdisplay > maxY)
1013
	if (maxY > 0 && mode->vdisplay > maxY)
-
 
1014
		return MODE_VIRTUAL_Y;
929
			mode->status = MODE_VIRTUAL_Y;
1015
 
930
	}
1016
	return MODE_OK;
Line -... Line 1017...
-
 
1017
}
-
 
1018
EXPORT_SYMBOL(drm_mode_validate_size);
-
 
1019
 
-
 
1020
#define MODE_STATUS(status) [MODE_ ## status + 3] = #status
-
 
1021
 
-
 
1022
static const char * const drm_mode_status_names[] = {
-
 
1023
	MODE_STATUS(OK),
-
 
1024
	MODE_STATUS(HSYNC),
-
 
1025
	MODE_STATUS(VSYNC),
-
 
1026
	MODE_STATUS(H_ILLEGAL),
-
 
1027
	MODE_STATUS(V_ILLEGAL),
-
 
1028
	MODE_STATUS(BAD_WIDTH),
-
 
1029
	MODE_STATUS(NOMODE),
-
 
1030
	MODE_STATUS(NO_INTERLACE),
-
 
1031
	MODE_STATUS(NO_DBLESCAN),
-
 
1032
	MODE_STATUS(NO_VSCAN),
-
 
1033
	MODE_STATUS(MEM),
-
 
1034
	MODE_STATUS(VIRTUAL_X),
-
 
1035
	MODE_STATUS(VIRTUAL_Y),
-
 
1036
	MODE_STATUS(MEM_VIRT),
-
 
1037
	MODE_STATUS(NOCLOCK),
-
 
1038
	MODE_STATUS(CLOCK_HIGH),
-
 
1039
	MODE_STATUS(CLOCK_LOW),
-
 
1040
	MODE_STATUS(CLOCK_RANGE),
-
 
1041
	MODE_STATUS(BAD_HVALUE),
-
 
1042
	MODE_STATUS(BAD_VVALUE),
-
 
1043
	MODE_STATUS(BAD_VSCAN),
-
 
1044
	MODE_STATUS(HSYNC_NARROW),
-
 
1045
	MODE_STATUS(HSYNC_WIDE),
-
 
1046
	MODE_STATUS(HBLANK_NARROW),
-
 
1047
	MODE_STATUS(HBLANK_WIDE),
-
 
1048
	MODE_STATUS(VSYNC_NARROW),
-
 
1049
	MODE_STATUS(VSYNC_WIDE),
-
 
1050
	MODE_STATUS(VBLANK_NARROW),
-
 
1051
	MODE_STATUS(VBLANK_WIDE),
-
 
1052
	MODE_STATUS(PANEL),
-
 
1053
	MODE_STATUS(INTERLACE_WIDTH),
-
 
1054
	MODE_STATUS(ONE_WIDTH),
-
 
1055
	MODE_STATUS(ONE_HEIGHT),
-
 
1056
	MODE_STATUS(ONE_SIZE),
-
 
1057
	MODE_STATUS(NO_REDUCED),
-
 
1058
	MODE_STATUS(NO_STEREO),
-
 
1059
	MODE_STATUS(UNVERIFIED),
-
 
1060
	MODE_STATUS(BAD),
-
 
1061
	MODE_STATUS(ERROR),
-
 
1062
};
-
 
1063
 
-
 
1064
#undef MODE_STATUS
-
 
1065
 
-
 
1066
static const char *drm_get_mode_status_name(enum drm_mode_status status)
-
 
1067
{
-
 
1068
	int index = status + 3;
-
 
1069
 
-
 
1070
	if (WARN_ON(index < 0 || index >= ARRAY_SIZE(drm_mode_status_names)))
-
 
1071
		return "";
-
 
1072
 
931
}
1073
	return drm_mode_status_names[index];
932
EXPORT_SYMBOL(drm_mode_validate_size);
1074
}
933
 
1075
 
934
/**
1076
/**
935
 * drm_mode_prune_invalid - remove invalid modes from mode list
1077
 * drm_mode_prune_invalid - remove invalid modes from mode list
Line 950... Line 1092...
950
	list_for_each_entry_safe(mode, t, mode_list, head) {
1092
	list_for_each_entry_safe(mode, t, mode_list, head) {
951
		if (mode->status != MODE_OK) {
1093
		if (mode->status != MODE_OK) {
952
			list_del(&mode->head);
1094
			list_del(&mode->head);
953
			if (verbose) {
1095
			if (verbose) {
954
				drm_mode_debug_printmodeline(mode);
1096
				drm_mode_debug_printmodeline(mode);
955
				DRM_DEBUG_KMS("Not using %s mode %d\n",
1097
				DRM_DEBUG_KMS("Not using %s mode: %s\n",
-
 
1098
					      mode->name,
956
					mode->name, mode->status);
1099
					      drm_get_mode_status_name(mode->status));
957
			}
1100
			}
958
			drm_mode_destroy(dev, mode);
1101
			drm_mode_destroy(dev, mode);
959
		}
1102
		}
960
	}
1103
	}
961
}
1104
}
Line 1009... Line 1152...
1009
EXPORT_SYMBOL(drm_mode_sort);
1152
EXPORT_SYMBOL(drm_mode_sort);
Line 1010... Line 1153...
1010
 
1153
 
1011
/**
1154
/**
1012
 * drm_mode_connector_list_update - update the mode list for the connector
1155
 * drm_mode_connector_list_update - update the mode list for the connector
1013
 * @connector: the connector to update
1156
 * @connector: the connector to update
1014
 * @merge_type_bits: whether to merge or overright type bits.
1157
 * @merge_type_bits: whether to merge or overwrite type bits
1015
 *
1158
 *
1016
 * This moves the modes from the @connector probed_modes list
1159
 * This moves the modes from the @connector probed_modes list
1017
 * to the actual mode list. It compares the probed mode against the current
1160
 * to the actual mode list. It compares the probed mode against the current
1018
 * list and only adds different/new modes.
1161
 * list and only adds different/new modes.
Line 1053... Line 1196...
1053
			list_move_tail(&pmode->head, &connector->modes);
1196
			list_move_tail(&pmode->head, &connector->modes);
1054
		}
1197
		}
1055
	}
1198
	}
1056
}
1199
}
1057
EXPORT_SYMBOL(drm_mode_connector_list_update);
1200
EXPORT_SYMBOL(drm_mode_connector_list_update);
-
 
1201
/**
-
 
1202
 * drm_crtc_convert_to_umode - convert a drm_display_mode into a modeinfo
-
 
1203
 * @out: drm_mode_modeinfo struct to return to the user
-
 
1204
 * @in: drm_display_mode to use
-
 
1205
 *
-
 
1206
 * Convert a drm_display_mode into a drm_mode_modeinfo structure to return to
-
 
1207
 * the user.
-
 
1208
 */
-
 
1209
void drm_mode_convert_to_umode(struct drm_mode_modeinfo *out,
-
 
1210
			       const struct drm_display_mode *in)
-
 
1211
{
-
 
1212
	WARN(in->hdisplay > USHRT_MAX || in->hsync_start > USHRT_MAX ||
-
 
1213
	     in->hsync_end > USHRT_MAX || in->htotal > USHRT_MAX ||
-
 
1214
	     in->hskew > USHRT_MAX || in->vdisplay > USHRT_MAX ||
-
 
1215
	     in->vsync_start > USHRT_MAX || in->vsync_end > USHRT_MAX ||
-
 
1216
	     in->vtotal > USHRT_MAX || in->vscan > USHRT_MAX,
-
 
1217
	     "timing values too large for mode info\n");
-
 
1218
 
-
 
1219
	out->clock = in->clock;
-
 
1220
	out->hdisplay = in->hdisplay;
-
 
1221
	out->hsync_start = in->hsync_start;
-
 
1222
	out->hsync_end = in->hsync_end;
-
 
1223
	out->htotal = in->htotal;
-
 
1224
	out->hskew = in->hskew;
-
 
1225
	out->vdisplay = in->vdisplay;
-
 
1226
	out->vsync_start = in->vsync_start;
-
 
1227
	out->vsync_end = in->vsync_end;
-
 
1228
	out->vtotal = in->vtotal;
-
 
1229
	out->vscan = in->vscan;
-
 
1230
	out->vrefresh = in->vrefresh;
-
 
1231
	out->flags = in->flags;
-
 
1232
	out->type = in->type;
-
 
1233
	strncpy(out->name, in->name, DRM_DISPLAY_MODE_LEN);
-
 
1234
	out->name[DRM_DISPLAY_MODE_LEN-1] = 0;
-
 
1235
}
-
 
1236
 
-
 
1237
/**
-
 
1238
 * drm_crtc_convert_umode - convert a modeinfo into a drm_display_mode
-
 
1239
 * @out: drm_display_mode to return to the user
-
 
1240
 * @in: drm_mode_modeinfo to use
-
 
1241
 *
-
 
1242
 * Convert a drm_mode_modeinfo into a drm_display_mode structure to return to
-
 
1243
 * the caller.
-
 
1244
 *
-
 
1245
 * Returns:
-
 
1246
 * Zero on success, negative errno on failure.
-
 
1247
 */
-
 
1248
int drm_mode_convert_umode(struct drm_display_mode *out,
-
 
1249
			   const struct drm_mode_modeinfo *in)
-
 
1250
{
-
 
1251
	int ret = -EINVAL;
-
 
1252
 
-
 
1253
	if (in->clock > INT_MAX || in->vrefresh > INT_MAX) {
-
 
1254
		ret = -ERANGE;
-
 
1255
		goto out;
-
 
1256
	}
-
 
1257
 
-
 
1258
	if ((in->flags & DRM_MODE_FLAG_3D_MASK) > DRM_MODE_FLAG_3D_MAX)
-
 
1259
		goto out;
-
 
1260
 
-
 
1261
	out->clock = in->clock;
-
 
1262
	out->hdisplay = in->hdisplay;
-
 
1263
	out->hsync_start = in->hsync_start;
-
 
1264
	out->hsync_end = in->hsync_end;
-
 
1265
	out->htotal = in->htotal;
-
 
1266
	out->hskew = in->hskew;
-
 
1267
	out->vdisplay = in->vdisplay;
-
 
1268
	out->vsync_start = in->vsync_start;
-
 
1269
	out->vsync_end = in->vsync_end;
-
 
1270
	out->vtotal = in->vtotal;
-
 
1271
	out->vscan = in->vscan;
-
 
1272
	out->vrefresh = in->vrefresh;
-
 
1273
	out->flags = in->flags;
-
 
1274
	out->type = in->type;
-
 
1275
	strncpy(out->name, in->name, DRM_DISPLAY_MODE_LEN);
-
 
1276
	out->name[DRM_DISPLAY_MODE_LEN-1] = 0;
-
 
1277
 
-
 
1278
	out->status = drm_mode_validate_basic(out);
-
 
1279
	if (out->status != MODE_OK)
-
 
1280
		goto out;
-
 
1281
 
-
 
1282
	ret = 0;
-
 
1283
 
-
 
1284
out:
-
 
1285
	return ret;
-
 
1286
}
1058
1287