Subversion Repositories Kolibri OS

Rev

Rev 5271 | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 5271 Rev 6104
1
/*
1
/*
2
 * Copyright 2007-8 Advanced Micro Devices, Inc.
2
 * Copyright 2007-8 Advanced Micro Devices, Inc.
3
 * Copyright 2008 Red Hat Inc.
3
 * Copyright 2008 Red Hat Inc.
4
 *
4
 *
5
 * Permission is hereby granted, free of charge, to any person obtaining a
5
 * Permission is hereby granted, free of charge, to any person obtaining a
6
 * copy of this software and associated documentation files (the "Software"),
6
 * copy of this software and associated documentation files (the "Software"),
7
 * to deal in the Software without restriction, including without limitation
7
 * to deal in the Software without restriction, including without limitation
8
 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8
 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9
 * and/or sell copies of the Software, and to permit persons to whom the
9
 * and/or sell copies of the Software, and to permit persons to whom the
10
 * Software is furnished to do so, subject to the following conditions:
10
 * Software is furnished to do so, subject to the following conditions:
11
 *
11
 *
12
 * The above copyright notice and this permission notice shall be included in
12
 * The above copyright notice and this permission notice shall be included in
13
 * all copies or substantial portions of the Software.
13
 * all copies or substantial portions of the Software.
14
 *
14
 *
15
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
17
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18
 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
18
 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
19
 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19
 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
20
 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20
 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
21
 * OTHER DEALINGS IN THE SOFTWARE.
21
 * OTHER DEALINGS IN THE SOFTWARE.
22
 *
22
 *
23
 * Authors: Dave Airlie
23
 * Authors: Dave Airlie
24
 *          Alex Deucher
24
 *          Alex Deucher
25
 */
25
 */
26
#include 
26
#include 
27
#include 
27
#include 
28
#include 
28
#include 
29
#include "radeon.h"
29
#include "radeon.h"
30
#include "atom.h"
30
#include "atom.h"
31
 
31
 
32
extern void
32
extern void
33
radeon_legacy_backlight_init(struct radeon_encoder *radeon_encoder,
33
radeon_legacy_backlight_init(struct radeon_encoder *radeon_encoder,
34
			     struct drm_connector *drm_connector);
34
			     struct drm_connector *drm_connector);
35
extern void
35
extern void
36
radeon_atom_backlight_init(struct radeon_encoder *radeon_encoder,
36
radeon_atom_backlight_init(struct radeon_encoder *radeon_encoder,
37
			   struct drm_connector *drm_connector);
37
			   struct drm_connector *drm_connector);
38
 
38
 
39
 
39
 
40
static uint32_t radeon_encoder_clones(struct drm_encoder *encoder)
40
static uint32_t radeon_encoder_clones(struct drm_encoder *encoder)
41
{
41
{
42
	struct drm_device *dev = encoder->dev;
42
	struct drm_device *dev = encoder->dev;
43
	struct radeon_device *rdev = dev->dev_private;
43
	struct radeon_device *rdev = dev->dev_private;
44
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
44
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
45
	struct drm_encoder *clone_encoder;
45
	struct drm_encoder *clone_encoder;
46
	uint32_t index_mask = 0;
46
	uint32_t index_mask = 0;
47
	int count;
47
	int count;
48
 
48
 
49
	/* DIG routing gets problematic */
49
	/* DIG routing gets problematic */
50
	if (rdev->family >= CHIP_R600)
50
	if (rdev->family >= CHIP_R600)
51
		return index_mask;
51
		return index_mask;
52
	/* LVDS/TV are too wacky */
52
	/* LVDS/TV are too wacky */
53
	if (radeon_encoder->devices & ATOM_DEVICE_LCD_SUPPORT)
53
	if (radeon_encoder->devices & ATOM_DEVICE_LCD_SUPPORT)
54
		return index_mask;
54
		return index_mask;
55
	/* DVO requires 2x ppll clocks depending on tmds chip */
55
	/* DVO requires 2x ppll clocks depending on tmds chip */
56
	if (radeon_encoder->devices & ATOM_DEVICE_DFP2_SUPPORT)
56
	if (radeon_encoder->devices & ATOM_DEVICE_DFP2_SUPPORT)
57
		return index_mask;
57
		return index_mask;
58
 
58
 
59
	count = -1;
59
	count = -1;
60
	list_for_each_entry(clone_encoder, &dev->mode_config.encoder_list, head) {
60
	list_for_each_entry(clone_encoder, &dev->mode_config.encoder_list, head) {
61
		struct radeon_encoder *radeon_clone = to_radeon_encoder(clone_encoder);
61
		struct radeon_encoder *radeon_clone = to_radeon_encoder(clone_encoder);
62
		count++;
62
		count++;
63
 
63
 
64
		if (clone_encoder == encoder)
64
		if (clone_encoder == encoder)
65
			continue;
65
			continue;
66
		if (radeon_clone->devices & (ATOM_DEVICE_LCD_SUPPORT))
66
		if (radeon_clone->devices & (ATOM_DEVICE_LCD_SUPPORT))
67
			continue;
67
			continue;
68
		if (radeon_clone->devices & ATOM_DEVICE_DFP2_SUPPORT)
68
		if (radeon_clone->devices & ATOM_DEVICE_DFP2_SUPPORT)
69
			continue;
69
			continue;
70
		else
70
		else
71
			index_mask |= (1 << count);
71
			index_mask |= (1 << count);
72
	}
72
	}
73
	return index_mask;
73
	return index_mask;
74
}
74
}
75
 
75
 
76
void radeon_setup_encoder_clones(struct drm_device *dev)
76
void radeon_setup_encoder_clones(struct drm_device *dev)
77
{
77
{
78
	struct drm_encoder *encoder;
78
	struct drm_encoder *encoder;
79
 
79
 
80
	list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
80
	list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
81
		encoder->possible_clones = radeon_encoder_clones(encoder);
81
		encoder->possible_clones = radeon_encoder_clones(encoder);
82
	}
82
	}
83
}
83
}
84
 
84
 
85
uint32_t
85
uint32_t
86
radeon_get_encoder_enum(struct drm_device *dev, uint32_t supported_device, uint8_t dac)
86
radeon_get_encoder_enum(struct drm_device *dev, uint32_t supported_device, uint8_t dac)
87
{
87
{
88
	struct radeon_device *rdev = dev->dev_private;
88
	struct radeon_device *rdev = dev->dev_private;
89
	uint32_t ret = 0;
89
	uint32_t ret = 0;
90
 
90
 
91
	switch (supported_device) {
91
	switch (supported_device) {
92
	case ATOM_DEVICE_CRT1_SUPPORT:
92
	case ATOM_DEVICE_CRT1_SUPPORT:
93
	case ATOM_DEVICE_TV1_SUPPORT:
93
	case ATOM_DEVICE_TV1_SUPPORT:
94
	case ATOM_DEVICE_TV2_SUPPORT:
94
	case ATOM_DEVICE_TV2_SUPPORT:
95
	case ATOM_DEVICE_CRT2_SUPPORT:
95
	case ATOM_DEVICE_CRT2_SUPPORT:
96
	case ATOM_DEVICE_CV_SUPPORT:
96
	case ATOM_DEVICE_CV_SUPPORT:
97
		switch (dac) {
97
		switch (dac) {
98
		case 1: /* dac a */
98
		case 1: /* dac a */
99
			if ((rdev->family == CHIP_RS300) ||
99
			if ((rdev->family == CHIP_RS300) ||
100
			    (rdev->family == CHIP_RS400) ||
100
			    (rdev->family == CHIP_RS400) ||
101
			    (rdev->family == CHIP_RS480))
101
			    (rdev->family == CHIP_RS480))
102
				ret = ENCODER_INTERNAL_DAC2_ENUM_ID1;
102
				ret = ENCODER_INTERNAL_DAC2_ENUM_ID1;
103
			else if (ASIC_IS_AVIVO(rdev))
103
			else if (ASIC_IS_AVIVO(rdev))
104
				ret = ENCODER_INTERNAL_KLDSCP_DAC1_ENUM_ID1;
104
				ret = ENCODER_INTERNAL_KLDSCP_DAC1_ENUM_ID1;
105
			else
105
			else
106
				ret = ENCODER_INTERNAL_DAC1_ENUM_ID1;
106
				ret = ENCODER_INTERNAL_DAC1_ENUM_ID1;
107
			break;
107
			break;
108
		case 2: /* dac b */
108
		case 2: /* dac b */
109
			if (ASIC_IS_AVIVO(rdev))
109
			if (ASIC_IS_AVIVO(rdev))
110
				ret = ENCODER_INTERNAL_KLDSCP_DAC2_ENUM_ID1;
110
				ret = ENCODER_INTERNAL_KLDSCP_DAC2_ENUM_ID1;
111
			else {
111
			else {
112
				/*if (rdev->family == CHIP_R200)
112
				/*if (rdev->family == CHIP_R200)
113
				  ret = ENCODER_INTERNAL_DVO1_ENUM_ID1;
113
				  ret = ENCODER_INTERNAL_DVO1_ENUM_ID1;
114
				  else*/
114
				  else*/
115
				ret = ENCODER_INTERNAL_DAC2_ENUM_ID1;
115
				ret = ENCODER_INTERNAL_DAC2_ENUM_ID1;
116
			}
116
			}
117
			break;
117
			break;
118
		case 3: /* external dac */
118
		case 3: /* external dac */
119
			if (ASIC_IS_AVIVO(rdev))
119
			if (ASIC_IS_AVIVO(rdev))
120
				ret = ENCODER_INTERNAL_KLDSCP_DVO1_ENUM_ID1;
120
				ret = ENCODER_INTERNAL_KLDSCP_DVO1_ENUM_ID1;
121
			else
121
			else
122
				ret = ENCODER_INTERNAL_DVO1_ENUM_ID1;
122
				ret = ENCODER_INTERNAL_DVO1_ENUM_ID1;
123
			break;
123
			break;
124
		}
124
		}
125
		break;
125
		break;
126
	case ATOM_DEVICE_LCD1_SUPPORT:
126
	case ATOM_DEVICE_LCD1_SUPPORT:
127
		if (ASIC_IS_AVIVO(rdev))
127
		if (ASIC_IS_AVIVO(rdev))
128
			ret = ENCODER_INTERNAL_LVTM1_ENUM_ID1;
128
			ret = ENCODER_INTERNAL_LVTM1_ENUM_ID1;
129
		else
129
		else
130
			ret = ENCODER_INTERNAL_LVDS_ENUM_ID1;
130
			ret = ENCODER_INTERNAL_LVDS_ENUM_ID1;
131
		break;
131
		break;
132
	case ATOM_DEVICE_DFP1_SUPPORT:
132
	case ATOM_DEVICE_DFP1_SUPPORT:
133
		if ((rdev->family == CHIP_RS300) ||
133
		if ((rdev->family == CHIP_RS300) ||
134
		    (rdev->family == CHIP_RS400) ||
134
		    (rdev->family == CHIP_RS400) ||
135
		    (rdev->family == CHIP_RS480))
135
		    (rdev->family == CHIP_RS480))
136
			ret = ENCODER_INTERNAL_DVO1_ENUM_ID1;
136
			ret = ENCODER_INTERNAL_DVO1_ENUM_ID1;
137
		else if (ASIC_IS_AVIVO(rdev))
137
		else if (ASIC_IS_AVIVO(rdev))
138
			ret = ENCODER_INTERNAL_KLDSCP_TMDS1_ENUM_ID1;
138
			ret = ENCODER_INTERNAL_KLDSCP_TMDS1_ENUM_ID1;
139
		else
139
		else
140
			ret = ENCODER_INTERNAL_TMDS1_ENUM_ID1;
140
			ret = ENCODER_INTERNAL_TMDS1_ENUM_ID1;
141
		break;
141
		break;
142
	case ATOM_DEVICE_LCD2_SUPPORT:
142
	case ATOM_DEVICE_LCD2_SUPPORT:
143
	case ATOM_DEVICE_DFP2_SUPPORT:
143
	case ATOM_DEVICE_DFP2_SUPPORT:
144
		if ((rdev->family == CHIP_RS600) ||
144
		if ((rdev->family == CHIP_RS600) ||
145
		    (rdev->family == CHIP_RS690) ||
145
		    (rdev->family == CHIP_RS690) ||
146
		    (rdev->family == CHIP_RS740))
146
		    (rdev->family == CHIP_RS740))
147
			ret = ENCODER_INTERNAL_DDI_ENUM_ID1;
147
			ret = ENCODER_INTERNAL_DDI_ENUM_ID1;
148
		else if (ASIC_IS_AVIVO(rdev))
148
		else if (ASIC_IS_AVIVO(rdev))
149
			ret = ENCODER_INTERNAL_KLDSCP_DVO1_ENUM_ID1;
149
			ret = ENCODER_INTERNAL_KLDSCP_DVO1_ENUM_ID1;
150
		else
150
		else
151
			ret = ENCODER_INTERNAL_DVO1_ENUM_ID1;
151
			ret = ENCODER_INTERNAL_DVO1_ENUM_ID1;
152
		break;
152
		break;
153
	case ATOM_DEVICE_DFP3_SUPPORT:
153
	case ATOM_DEVICE_DFP3_SUPPORT:
154
		ret = ENCODER_INTERNAL_LVTM1_ENUM_ID1;
154
		ret = ENCODER_INTERNAL_LVTM1_ENUM_ID1;
155
		break;
155
		break;
156
	}
156
	}
157
 
157
 
158
	return ret;
158
	return ret;
159
}
159
}
160
 
160
 
161
static void radeon_encoder_add_backlight(struct radeon_encoder *radeon_encoder,
161
static void radeon_encoder_add_backlight(struct radeon_encoder *radeon_encoder,
162
					 struct drm_connector *connector)
162
					 struct drm_connector *connector)
163
{
163
{
164
	struct drm_device *dev = radeon_encoder->base.dev;
164
	struct drm_device *dev = radeon_encoder->base.dev;
165
	struct radeon_device *rdev = dev->dev_private;
165
	struct radeon_device *rdev = dev->dev_private;
166
	bool use_bl = false;
166
	bool use_bl = false;
167
 
167
 
168
	if (!(radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT)))
168
	if (!(radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT)))
169
		return;
169
		return;
170
 
170
 
171
	if (radeon_backlight == 0) {
171
	if (radeon_backlight == 0) {
172
		return;
172
		return;
173
	} else if (radeon_backlight == 1) {
173
	} else if (radeon_backlight == 1) {
174
		use_bl = true;
174
		use_bl = true;
175
	} else if (radeon_backlight == -1) {
175
	} else if (radeon_backlight == -1) {
176
		/* Quirks */
176
		/* Quirks */
177
		/* Amilo Xi 2550 only works with acpi bl */
177
		/* Amilo Xi 2550 only works with acpi bl */
178
		if ((rdev->pdev->device == 0x9583) &&
178
		if ((rdev->pdev->device == 0x9583) &&
179
		    (rdev->pdev->subsystem_vendor == 0x1734) &&
179
		    (rdev->pdev->subsystem_vendor == 0x1734) &&
180
		    (rdev->pdev->subsystem_device == 0x1107))
180
		    (rdev->pdev->subsystem_device == 0x1107))
181
			use_bl = false;
181
			use_bl = false;
-
 
182
/* Older PPC macs use on-GPU backlight controller */
-
 
183
#ifndef CONFIG_PPC_PMAC
182
		/* disable native backlight control on older asics */
184
		/* disable native backlight control on older asics */
183
		else if (rdev->family < CHIP_R600)
185
		else if (rdev->family < CHIP_R600)
184
			use_bl = false;
186
			use_bl = false;
-
 
187
#endif
185
		else
188
		else
186
			use_bl = true;
189
			use_bl = true;
187
	}
190
	}
188
 
191
 
189
	if (use_bl) {
192
	if (use_bl) {
190
		if (rdev->is_atom_bios)
193
		if (rdev->is_atom_bios)
191
			radeon_atom_backlight_init(radeon_encoder, connector);
194
			radeon_atom_backlight_init(radeon_encoder, connector);
192
		else
195
		else
193
			radeon_legacy_backlight_init(radeon_encoder, connector);
196
			radeon_legacy_backlight_init(radeon_encoder, connector);
194
		rdev->mode_info.bl_encoder = radeon_encoder;
-
 
195
	}
197
	}
196
}
198
}
197
 
199
 
198
void
200
void
199
radeon_link_encoder_connector(struct drm_device *dev)
201
radeon_link_encoder_connector(struct drm_device *dev)
200
{
202
{
201
	struct drm_connector *connector;
203
	struct drm_connector *connector;
202
	struct radeon_connector *radeon_connector;
204
	struct radeon_connector *radeon_connector;
203
	struct drm_encoder *encoder;
205
	struct drm_encoder *encoder;
204
	struct radeon_encoder *radeon_encoder;
206
	struct radeon_encoder *radeon_encoder;
205
 
207
 
206
	/* walk the list and link encoders to connectors */
208
	/* walk the list and link encoders to connectors */
207
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
209
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
208
		radeon_connector = to_radeon_connector(connector);
210
		radeon_connector = to_radeon_connector(connector);
209
		list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
211
		list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
210
			radeon_encoder = to_radeon_encoder(encoder);
212
			radeon_encoder = to_radeon_encoder(encoder);
211
			if (radeon_encoder->devices & radeon_connector->devices) {
213
			if (radeon_encoder->devices & radeon_connector->devices) {
212
				drm_mode_connector_attach_encoder(connector, encoder);
214
				drm_mode_connector_attach_encoder(connector, encoder);
213
				if (radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT))
215
				if (radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT))
214
					radeon_encoder_add_backlight(radeon_encoder, connector);
216
					radeon_encoder_add_backlight(radeon_encoder, connector);
215
			}
217
			}
216
		}
218
		}
217
	}
219
	}
218
}
220
}
219
 
221
 
220
void radeon_encoder_set_active_device(struct drm_encoder *encoder)
222
void radeon_encoder_set_active_device(struct drm_encoder *encoder)
221
{
223
{
222
	struct drm_device *dev = encoder->dev;
224
	struct drm_device *dev = encoder->dev;
223
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
225
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
224
	struct drm_connector *connector;
226
	struct drm_connector *connector;
225
 
227
 
226
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
228
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
227
		if (connector->encoder == encoder) {
229
		if (connector->encoder == encoder) {
228
			struct radeon_connector *radeon_connector = to_radeon_connector(connector);
230
			struct radeon_connector *radeon_connector = to_radeon_connector(connector);
229
			radeon_encoder->active_device = radeon_encoder->devices & radeon_connector->devices;
231
			radeon_encoder->active_device = radeon_encoder->devices & radeon_connector->devices;
230
			DRM_DEBUG_KMS("setting active device to %08x from %08x %08x for encoder %d\n",
232
			DRM_DEBUG_KMS("setting active device to %08x from %08x %08x for encoder %d\n",
231
				  radeon_encoder->active_device, radeon_encoder->devices,
233
				  radeon_encoder->active_device, radeon_encoder->devices,
232
				  radeon_connector->devices, encoder->encoder_type);
234
				  radeon_connector->devices, encoder->encoder_type);
233
		}
235
		}
234
	}
236
	}
235
}
237
}
236
 
238
 
237
struct drm_connector *
239
struct drm_connector *
238
radeon_get_connector_for_encoder(struct drm_encoder *encoder)
240
radeon_get_connector_for_encoder(struct drm_encoder *encoder)
239
{
241
{
240
	struct drm_device *dev = encoder->dev;
242
	struct drm_device *dev = encoder->dev;
241
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
243
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
242
	struct drm_connector *connector;
244
	struct drm_connector *connector;
243
	struct radeon_connector *radeon_connector;
245
	struct radeon_connector *radeon_connector;
244
 
246
 
245
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
247
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
246
		radeon_connector = to_radeon_connector(connector);
248
		radeon_connector = to_radeon_connector(connector);
-
 
249
		if (radeon_encoder->is_mst_encoder) {
-
 
250
			struct radeon_encoder_mst *mst_enc;
-
 
251
 
-
 
252
			if (!radeon_connector->is_mst_connector)
-
 
253
				continue;
-
 
254
 
-
 
255
			mst_enc = radeon_encoder->enc_priv;
-
 
256
			if (mst_enc->connector == radeon_connector->mst_port)
-
 
257
				return connector;
247
		if (radeon_encoder->active_device & radeon_connector->devices)
258
		} else if (radeon_encoder->active_device & radeon_connector->devices)
248
			return connector;
259
			return connector;
249
	}
260
	}
250
	return NULL;
261
	return NULL;
251
}
262
}
252
 
263
 
253
struct drm_connector *
264
struct drm_connector *
254
radeon_get_connector_for_encoder_init(struct drm_encoder *encoder)
265
radeon_get_connector_for_encoder_init(struct drm_encoder *encoder)
255
{
266
{
256
	struct drm_device *dev = encoder->dev;
267
	struct drm_device *dev = encoder->dev;
257
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
268
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
258
	struct drm_connector *connector;
269
	struct drm_connector *connector;
259
	struct radeon_connector *radeon_connector;
270
	struct radeon_connector *radeon_connector;
260
 
271
 
261
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
272
	list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
262
		radeon_connector = to_radeon_connector(connector);
273
		radeon_connector = to_radeon_connector(connector);
263
		if (radeon_encoder->devices & radeon_connector->devices)
274
		if (radeon_encoder->devices & radeon_connector->devices)
264
			return connector;
275
			return connector;
265
	}
276
	}
266
	return NULL;
277
	return NULL;
267
}
278
}
268
 
279
 
269
struct drm_encoder *radeon_get_external_encoder(struct drm_encoder *encoder)
280
struct drm_encoder *radeon_get_external_encoder(struct drm_encoder *encoder)
270
{
281
{
271
	struct drm_device *dev = encoder->dev;
282
	struct drm_device *dev = encoder->dev;
272
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
283
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
273
	struct drm_encoder *other_encoder;
284
	struct drm_encoder *other_encoder;
274
	struct radeon_encoder *other_radeon_encoder;
285
	struct radeon_encoder *other_radeon_encoder;
275
 
286
 
276
	if (radeon_encoder->is_ext_encoder)
287
	if (radeon_encoder->is_ext_encoder)
277
		return NULL;
288
		return NULL;
278
 
289
 
279
	list_for_each_entry(other_encoder, &dev->mode_config.encoder_list, head) {
290
	list_for_each_entry(other_encoder, &dev->mode_config.encoder_list, head) {
280
		if (other_encoder == encoder)
291
		if (other_encoder == encoder)
281
			continue;
292
			continue;
282
		other_radeon_encoder = to_radeon_encoder(other_encoder);
293
		other_radeon_encoder = to_radeon_encoder(other_encoder);
283
		if (other_radeon_encoder->is_ext_encoder &&
294
		if (other_radeon_encoder->is_ext_encoder &&
284
		    (radeon_encoder->devices & other_radeon_encoder->devices))
295
		    (radeon_encoder->devices & other_radeon_encoder->devices))
285
			return other_encoder;
296
			return other_encoder;
286
	}
297
	}
287
	return NULL;
298
	return NULL;
288
}
299
}
289
 
300
 
290
u16 radeon_encoder_get_dp_bridge_encoder_id(struct drm_encoder *encoder)
301
u16 radeon_encoder_get_dp_bridge_encoder_id(struct drm_encoder *encoder)
291
{
302
{
292
	struct drm_encoder *other_encoder = radeon_get_external_encoder(encoder);
303
	struct drm_encoder *other_encoder = radeon_get_external_encoder(encoder);
293
 
304
 
294
	if (other_encoder) {
305
	if (other_encoder) {
295
		struct radeon_encoder *radeon_encoder = to_radeon_encoder(other_encoder);
306
		struct radeon_encoder *radeon_encoder = to_radeon_encoder(other_encoder);
296
 
307
 
297
		switch (radeon_encoder->encoder_id) {
308
		switch (radeon_encoder->encoder_id) {
298
		case ENCODER_OBJECT_ID_TRAVIS:
309
		case ENCODER_OBJECT_ID_TRAVIS:
299
		case ENCODER_OBJECT_ID_NUTMEG:
310
		case ENCODER_OBJECT_ID_NUTMEG:
300
			return radeon_encoder->encoder_id;
311
			return radeon_encoder->encoder_id;
301
		default:
312
		default:
302
			return ENCODER_OBJECT_ID_NONE;
313
			return ENCODER_OBJECT_ID_NONE;
303
		}
314
		}
304
	}
315
	}
305
	return ENCODER_OBJECT_ID_NONE;
316
	return ENCODER_OBJECT_ID_NONE;
306
}
317
}
307
 
318
 
308
void radeon_panel_mode_fixup(struct drm_encoder *encoder,
319
void radeon_panel_mode_fixup(struct drm_encoder *encoder,
309
			     struct drm_display_mode *adjusted_mode)
320
			     struct drm_display_mode *adjusted_mode)
310
{
321
{
311
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
322
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
312
	struct drm_device *dev = encoder->dev;
323
	struct drm_device *dev = encoder->dev;
313
	struct radeon_device *rdev = dev->dev_private;
324
	struct radeon_device *rdev = dev->dev_private;
314
	struct drm_display_mode *native_mode = &radeon_encoder->native_mode;
325
	struct drm_display_mode *native_mode = &radeon_encoder->native_mode;
315
	unsigned hblank = native_mode->htotal - native_mode->hdisplay;
326
	unsigned hblank = native_mode->htotal - native_mode->hdisplay;
316
	unsigned vblank = native_mode->vtotal - native_mode->vdisplay;
327
	unsigned vblank = native_mode->vtotal - native_mode->vdisplay;
317
	unsigned hover = native_mode->hsync_start - native_mode->hdisplay;
328
	unsigned hover = native_mode->hsync_start - native_mode->hdisplay;
318
	unsigned vover = native_mode->vsync_start - native_mode->vdisplay;
329
	unsigned vover = native_mode->vsync_start - native_mode->vdisplay;
319
	unsigned hsync_width = native_mode->hsync_end - native_mode->hsync_start;
330
	unsigned hsync_width = native_mode->hsync_end - native_mode->hsync_start;
320
	unsigned vsync_width = native_mode->vsync_end - native_mode->vsync_start;
331
	unsigned vsync_width = native_mode->vsync_end - native_mode->vsync_start;
321
 
332
 
322
	adjusted_mode->clock = native_mode->clock;
333
	adjusted_mode->clock = native_mode->clock;
323
	adjusted_mode->flags = native_mode->flags;
334
	adjusted_mode->flags = native_mode->flags;
324
 
335
 
325
	if (ASIC_IS_AVIVO(rdev)) {
336
	if (ASIC_IS_AVIVO(rdev)) {
326
		adjusted_mode->hdisplay = native_mode->hdisplay;
337
		adjusted_mode->hdisplay = native_mode->hdisplay;
327
		adjusted_mode->vdisplay = native_mode->vdisplay;
338
		adjusted_mode->vdisplay = native_mode->vdisplay;
328
	}
339
	}
329
 
340
 
330
	adjusted_mode->htotal = native_mode->hdisplay + hblank;
341
	adjusted_mode->htotal = native_mode->hdisplay + hblank;
331
	adjusted_mode->hsync_start = native_mode->hdisplay + hover;
342
	adjusted_mode->hsync_start = native_mode->hdisplay + hover;
332
	adjusted_mode->hsync_end = adjusted_mode->hsync_start + hsync_width;
343
	adjusted_mode->hsync_end = adjusted_mode->hsync_start + hsync_width;
333
 
344
 
334
	adjusted_mode->vtotal = native_mode->vdisplay + vblank;
345
	adjusted_mode->vtotal = native_mode->vdisplay + vblank;
335
	adjusted_mode->vsync_start = native_mode->vdisplay + vover;
346
	adjusted_mode->vsync_start = native_mode->vdisplay + vover;
336
	adjusted_mode->vsync_end = adjusted_mode->vsync_start + vsync_width;
347
	adjusted_mode->vsync_end = adjusted_mode->vsync_start + vsync_width;
337
 
348
 
338
	drm_mode_set_crtcinfo(adjusted_mode, CRTC_INTERLACE_HALVE_V);
349
	drm_mode_set_crtcinfo(adjusted_mode, CRTC_INTERLACE_HALVE_V);
339
 
350
 
340
	if (ASIC_IS_AVIVO(rdev)) {
351
	if (ASIC_IS_AVIVO(rdev)) {
341
		adjusted_mode->crtc_hdisplay = native_mode->hdisplay;
352
		adjusted_mode->crtc_hdisplay = native_mode->hdisplay;
342
		adjusted_mode->crtc_vdisplay = native_mode->vdisplay;
353
		adjusted_mode->crtc_vdisplay = native_mode->vdisplay;
343
	}
354
	}
344
 
355
 
345
	adjusted_mode->crtc_htotal = adjusted_mode->crtc_hdisplay + hblank;
356
	adjusted_mode->crtc_htotal = adjusted_mode->crtc_hdisplay + hblank;
346
	adjusted_mode->crtc_hsync_start = adjusted_mode->crtc_hdisplay + hover;
357
	adjusted_mode->crtc_hsync_start = adjusted_mode->crtc_hdisplay + hover;
347
	adjusted_mode->crtc_hsync_end = adjusted_mode->crtc_hsync_start + hsync_width;
358
	adjusted_mode->crtc_hsync_end = adjusted_mode->crtc_hsync_start + hsync_width;
348
 
359
 
349
	adjusted_mode->crtc_vtotal = adjusted_mode->crtc_vdisplay + vblank;
360
	adjusted_mode->crtc_vtotal = adjusted_mode->crtc_vdisplay + vblank;
350
	adjusted_mode->crtc_vsync_start = adjusted_mode->crtc_vdisplay + vover;
361
	adjusted_mode->crtc_vsync_start = adjusted_mode->crtc_vdisplay + vover;
351
	adjusted_mode->crtc_vsync_end = adjusted_mode->crtc_vsync_start + vsync_width;
362
	adjusted_mode->crtc_vsync_end = adjusted_mode->crtc_vsync_start + vsync_width;
352
 
363
 
353
}
364
}
354
 
365
 
355
bool radeon_dig_monitor_is_duallink(struct drm_encoder *encoder,
366
bool radeon_dig_monitor_is_duallink(struct drm_encoder *encoder,
356
				    u32 pixel_clock)
367
				    u32 pixel_clock)
357
{
368
{
358
	struct drm_device *dev = encoder->dev;
369
	struct drm_device *dev = encoder->dev;
359
	struct radeon_device *rdev = dev->dev_private;
370
	struct radeon_device *rdev = dev->dev_private;
360
	struct drm_connector *connector;
371
	struct drm_connector *connector;
361
	struct radeon_connector *radeon_connector;
372
	struct radeon_connector *radeon_connector;
362
	struct radeon_connector_atom_dig *dig_connector;
373
	struct radeon_connector_atom_dig *dig_connector;
363
 
374
 
364
	connector = radeon_get_connector_for_encoder(encoder);
375
	connector = radeon_get_connector_for_encoder(encoder);
365
	/* if we don't have an active device yet, just use one of
376
	/* if we don't have an active device yet, just use one of
366
	 * the connectors tied to the encoder.
377
	 * the connectors tied to the encoder.
367
	 */
378
	 */
368
	if (!connector)
379
	if (!connector)
369
		connector = radeon_get_connector_for_encoder_init(encoder);
380
		connector = radeon_get_connector_for_encoder_init(encoder);
370
	radeon_connector = to_radeon_connector(connector);
381
	radeon_connector = to_radeon_connector(connector);
371
 
382
 
372
	switch (connector->connector_type) {
383
	switch (connector->connector_type) {
373
	case DRM_MODE_CONNECTOR_DVII:
384
	case DRM_MODE_CONNECTOR_DVII:
374
	case DRM_MODE_CONNECTOR_HDMIB:
385
	case DRM_MODE_CONNECTOR_HDMIB:
375
		if (radeon_connector->use_digital) {
386
		if (radeon_connector->use_digital) {
376
			/* HDMI 1.3 supports up to 340 Mhz over single link */
387
			/* HDMI 1.3 supports up to 340 Mhz over single link */
377
			if (ASIC_IS_DCE6(rdev) && drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
388
			if (ASIC_IS_DCE6(rdev) && drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
378
				if (pixel_clock > 340000)
389
				if (pixel_clock > 340000)
379
					return true;
390
					return true;
380
			else
391
				else
381
					return false;
392
					return false;
382
			} else {
393
			} else {
383
				if (pixel_clock > 165000)
394
				if (pixel_clock > 165000)
384
					return true;
395
					return true;
385
		else
396
				else
386
					return false;
397
					return false;
387
			}
398
			}
388
		} else
399
		} else
389
			return false;
400
			return false;
390
	case DRM_MODE_CONNECTOR_DVID:
401
	case DRM_MODE_CONNECTOR_DVID:
391
	case DRM_MODE_CONNECTOR_HDMIA:
402
	case DRM_MODE_CONNECTOR_HDMIA:
392
	case DRM_MODE_CONNECTOR_DisplayPort:
403
	case DRM_MODE_CONNECTOR_DisplayPort:
-
 
404
		if (radeon_connector->is_mst_connector)
-
 
405
			return false;
-
 
406
 
393
		dig_connector = radeon_connector->con_priv;
407
		dig_connector = radeon_connector->con_priv;
394
		if ((dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_DISPLAYPORT) ||
408
		if ((dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_DISPLAYPORT) ||
395
		    (dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_eDP))
409
		    (dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_eDP))
396
			return false;
410
			return false;
397
	else {
411
		else {
398
			/* HDMI 1.3 supports up to 340 Mhz over single link */
412
			/* HDMI 1.3 supports up to 340 Mhz over single link */
399
			if (ASIC_IS_DCE6(rdev) && drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
413
			if (ASIC_IS_DCE6(rdev) && drm_detect_hdmi_monitor(radeon_connector_edid(connector))) {
400
				if (pixel_clock > 340000)
414
				if (pixel_clock > 340000)
401
					return true;
415
					return true;
402
		else
416
				else
403
					return false;
417
					return false;
404
	} else {
418
			} else {
405
				if (pixel_clock > 165000)
419
				if (pixel_clock > 165000)
406
					return true;
420
					return true;
407
				else
421
				else
408
		return false;
422
					return false;
409
	}
423
			}
410
		}
424
		}
411
		default:
425
	default:
412
			return false;
426
		return false;
413
		}
427
	}
414
}
428
}
415
 
429
 
416
bool radeon_encoder_is_digital(struct drm_encoder *encoder)
430
bool radeon_encoder_is_digital(struct drm_encoder *encoder)
417
{
431
{
418
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
432
	struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
419
	switch (radeon_encoder->encoder_id) {
433
	switch (radeon_encoder->encoder_id) {
420
	case ENCODER_OBJECT_ID_INTERNAL_LVDS:
434
	case ENCODER_OBJECT_ID_INTERNAL_LVDS:
421
	case ENCODER_OBJECT_ID_INTERNAL_TMDS1:
435
	case ENCODER_OBJECT_ID_INTERNAL_TMDS1:
422
	case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_TMDS1:
436
	case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_TMDS1:
423
	case ENCODER_OBJECT_ID_INTERNAL_LVTM1:
437
	case ENCODER_OBJECT_ID_INTERNAL_LVTM1:
424
	case ENCODER_OBJECT_ID_INTERNAL_DVO1:
438
	case ENCODER_OBJECT_ID_INTERNAL_DVO1:
425
	case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DVO1:
439
	case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DVO1:
426
	case ENCODER_OBJECT_ID_INTERNAL_DDI:
440
	case ENCODER_OBJECT_ID_INTERNAL_DDI:
427
	case ENCODER_OBJECT_ID_INTERNAL_UNIPHY:
441
	case ENCODER_OBJECT_ID_INTERNAL_UNIPHY:
428
	case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_LVTMA:
442
	case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_LVTMA:
429
	case ENCODER_OBJECT_ID_INTERNAL_UNIPHY1:
443
	case ENCODER_OBJECT_ID_INTERNAL_UNIPHY1:
430
	case ENCODER_OBJECT_ID_INTERNAL_UNIPHY2:
444
	case ENCODER_OBJECT_ID_INTERNAL_UNIPHY2:
431
	case ENCODER_OBJECT_ID_INTERNAL_UNIPHY3:
445
	case ENCODER_OBJECT_ID_INTERNAL_UNIPHY3:
432
		return true;
446
		return true;
433
	default:
447
	default:
434
		return false;
448
		return false;
435
	}
449
	}
436
}
450
}