Rev 1430 | Rev 1986 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 1430 | Rev 1963 | ||
---|---|---|---|
Line 30... | Line 30... | ||
30 | #include "atom.h" |
30 | #include "atom.h" |
31 | #include "atom-bits.h" |
31 | #include "atom-bits.h" |
Line 32... | Line 32... | ||
32 | 32 | ||
33 | /* from radeon_encoder.c */ |
33 | /* from radeon_encoder.c */ |
34 | extern uint32_t |
34 | extern uint32_t |
35 | radeon_get_encoder_id(struct drm_device *dev, uint32_t supported_device, |
35 | radeon_get_encoder_enum(struct drm_device *dev, uint32_t supported_device, |
36 | uint8_t dac); |
36 | uint8_t dac); |
37 | extern void radeon_link_encoder_connector(struct drm_device *dev); |
37 | extern void radeon_link_encoder_connector(struct drm_device *dev); |
38 | extern void |
38 | extern void |
39 | radeon_add_atom_encoder(struct drm_device *dev, uint32_t encoder_id, |
39 | radeon_add_atom_encoder(struct drm_device *dev, uint32_t encoder_enum, |
Line 40... | Line 40... | ||
40 | uint32_t supported_device); |
40 | uint32_t supported_device, u16 caps); |
41 | 41 | ||
42 | /* from radeon_connector.c */ |
42 | /* from radeon_connector.c */ |
43 | extern void |
43 | extern void |
44 | radeon_add_atom_connector(struct drm_device *dev, |
44 | radeon_add_atom_connector(struct drm_device *dev, |
45 | uint32_t connector_id, |
45 | uint32_t connector_id, |
46 | uint32_t supported_device, |
46 | uint32_t supported_device, |
47 | int connector_type, |
47 | int connector_type, |
48 | struct radeon_i2c_bus_rec *i2c_bus, |
48 | struct radeon_i2c_bus_rec *i2c_bus, |
49 | bool linkb, uint32_t igp_lane_info, |
49 | uint32_t igp_lane_info, |
- | 50 | uint16_t connector_object_id, |
|
Line 50... | Line 51... | ||
50 | uint16_t connector_object_id, |
51 | struct radeon_hpd *hpd, |
51 | struct radeon_hpd *hpd); |
52 | struct radeon_router *router); |
52 | 53 | ||
53 | /* from radeon_legacy_encoder.c */ |
54 | /* from radeon_legacy_encoder.c */ |
Line 54... | Line 55... | ||
54 | extern void |
55 | extern void |
55 | radeon_add_legacy_encoder(struct drm_device *dev, uint32_t encoder_id, |
56 | radeon_add_legacy_encoder(struct drm_device *dev, uint32_t encoder_enum, |
56 | uint32_t supported_device); |
57 | uint32_t supported_device); |
Line 67... | Line 68... | ||
67 | struct atom_context *ctx = rdev->mode_info.atom_context; |
68 | struct atom_context *ctx = rdev->mode_info.atom_context; |
68 | ATOM_GPIO_I2C_ASSIGMENT *gpio; |
69 | ATOM_GPIO_I2C_ASSIGMENT *gpio; |
69 | struct radeon_i2c_bus_rec i2c; |
70 | struct radeon_i2c_bus_rec i2c; |
70 | int index = GetIndexIntoMasterTable(DATA, GPIO_I2C_Info); |
71 | int index = GetIndexIntoMasterTable(DATA, GPIO_I2C_Info); |
71 | struct _ATOM_GPIO_I2C_INFO *i2c_info; |
72 | struct _ATOM_GPIO_I2C_INFO *i2c_info; |
72 | uint16_t data_offset; |
73 | uint16_t data_offset, size; |
73 | int i; |
74 | int i, num_indices; |
Line 74... | Line 75... | ||
74 | 75 | ||
75 | memset(&i2c, 0, sizeof(struct radeon_i2c_bus_rec)); |
76 | memset(&i2c, 0, sizeof(struct radeon_i2c_bus_rec)); |
Line 76... | Line 77... | ||
76 | i2c.valid = false; |
77 | i2c.valid = false; |
77 | - | ||
78 | atom_parse_data_header(ctx, index, NULL, NULL, NULL, &data_offset); |
78 | |
Line -... | Line 79... | ||
- | 79 | if (atom_parse_data_header(ctx, index, &size, NULL, NULL, &data_offset)) { |
|
- | 80 | i2c_info = (struct _ATOM_GPIO_I2C_INFO *)(ctx->bios + data_offset); |
|
Line 79... | Line 81... | ||
79 | 81 | ||
80 | i2c_info = (struct _ATOM_GPIO_I2C_INFO *)(ctx->bios + data_offset); |
82 | num_indices = (size - sizeof(ATOM_COMMON_TABLE_HEADER)) / |
Line -... | Line 83... | ||
- | 83 | sizeof(ATOM_GPIO_I2C_ASSIGMENT); |
|
- | 84 | ||
- | 85 | for (i = 0; i < num_indices; i++) { |
|
- | 86 | gpio = &i2c_info->asGPIO_Info[i]; |
|
- | 87 | ||
- | 88 | /* some evergreen boards have bad data for this entry */ |
|
- | 89 | if (ASIC_IS_DCE4(rdev)) { |
|
- | 90 | if ((i == 7) && |
|
- | 91 | (le16_to_cpu(gpio->usClkMaskRegisterIndex) == 0x1936) && |
|
- | 92 | (gpio->sucI2cId.ucAccess == 0)) { |
|
- | 93 | gpio->sucI2cId.ucAccess = 0x97; |
|
- | 94 | gpio->ucDataMaskShift = 8; |
|
- | 95 | gpio->ucDataEnShift = 8; |
|
- | 96 | gpio->ucDataY_Shift = 8; |
|
- | 97 | gpio->ucDataA_Shift = 8; |
|
- | 98 | } |
|
- | 99 | } |
|
- | 100 | ||
- | 101 | /* some DCE3 boards have bad data for this entry */ |
|
- | 102 | if (ASIC_IS_DCE3(rdev)) { |
|
- | 103 | if ((i == 4) && |
|
81 | 104 | (le16_to_cpu(gpio->usClkMaskRegisterIndex) == 0x1fda) && |
|
82 | 105 | (gpio->sucI2cId.ucAccess == 0x94)) |
|
83 | for (i = 0; i < ATOM_MAX_SUPPORTED_DEVICE; i++) { |
106 | gpio->sucI2cId.ucAccess = 0x14; |
84 | gpio = &i2c_info->asGPIO_Info[i]; |
107 | } |
85 | 108 | ||
Line 111... | Line 134... | ||
111 | else |
134 | else |
112 | i2c.mm_i2c = false; |
135 | i2c.mm_i2c = false; |
Line 113... | Line 136... | ||
113 | 136 | ||
Line -... | Line 137... | ||
- | 137 | i2c.i2c_id = gpio->sucI2cId.ucAccess; |
|
114 | i2c.i2c_id = gpio->sucI2cId.ucAccess; |
138 | |
115 | 139 | if (i2c.mask_clk_reg) |
|
116 | i2c.valid = true; |
140 | i2c.valid = true; |
117 | break; |
141 | break; |
- | 142 | } |
|
Line 118... | Line 143... | ||
118 | } |
143 | } |
119 | } |
144 | } |
Line -... | Line 145... | ||
- | 145 | ||
- | 146 | return i2c; |
|
- | 147 | } |
|
- | 148 | ||
- | 149 | void radeon_atombios_i2c_init(struct radeon_device *rdev) |
|
- | 150 | { |
|
- | 151 | struct atom_context *ctx = rdev->mode_info.atom_context; |
|
- | 152 | ATOM_GPIO_I2C_ASSIGMENT *gpio; |
|
- | 153 | struct radeon_i2c_bus_rec i2c; |
|
- | 154 | int index = GetIndexIntoMasterTable(DATA, GPIO_I2C_Info); |
|
- | 155 | struct _ATOM_GPIO_I2C_INFO *i2c_info; |
|
- | 156 | uint16_t data_offset, size; |
|
- | 157 | int i, num_indices; |
|
- | 158 | char stmp[32]; |
|
- | 159 | ||
- | 160 | memset(&i2c, 0, sizeof(struct radeon_i2c_bus_rec)); |
|
- | 161 | ||
- | 162 | if (atom_parse_data_header(ctx, index, &size, NULL, NULL, &data_offset)) { |
|
- | 163 | i2c_info = (struct _ATOM_GPIO_I2C_INFO *)(ctx->bios + data_offset); |
|
- | 164 | ||
- | 165 | num_indices = (size - sizeof(ATOM_COMMON_TABLE_HEADER)) / |
|
- | 166 | sizeof(ATOM_GPIO_I2C_ASSIGMENT); |
|
- | 167 | ||
- | 168 | for (i = 0; i < num_indices; i++) { |
|
- | 169 | gpio = &i2c_info->asGPIO_Info[i]; |
|
- | 170 | i2c.valid = false; |
|
- | 171 | ||
- | 172 | /* some evergreen boards have bad data for this entry */ |
|
- | 173 | if (ASIC_IS_DCE4(rdev)) { |
|
- | 174 | if ((i == 7) && |
|
- | 175 | (le16_to_cpu(gpio->usClkMaskRegisterIndex) == 0x1936) && |
|
- | 176 | (gpio->sucI2cId.ucAccess == 0)) { |
|
- | 177 | gpio->sucI2cId.ucAccess = 0x97; |
|
- | 178 | gpio->ucDataMaskShift = 8; |
|
- | 179 | gpio->ucDataEnShift = 8; |
|
- | 180 | gpio->ucDataY_Shift = 8; |
|
- | 181 | gpio->ucDataA_Shift = 8; |
|
- | 182 | } |
|
- | 183 | } |
|
- | 184 | ||
- | 185 | /* some DCE3 boards have bad data for this entry */ |
|
- | 186 | if (ASIC_IS_DCE3(rdev)) { |
|
- | 187 | if ((i == 4) && |
|
- | 188 | (le16_to_cpu(gpio->usClkMaskRegisterIndex) == 0x1fda) && |
|
- | 189 | (gpio->sucI2cId.ucAccess == 0x94)) |
|
- | 190 | gpio->sucI2cId.ucAccess = 0x14; |
|
- | 191 | } |
|
- | 192 | ||
- | 193 | i2c.mask_clk_reg = le16_to_cpu(gpio->usClkMaskRegisterIndex) * 4; |
|
- | 194 | i2c.mask_data_reg = le16_to_cpu(gpio->usDataMaskRegisterIndex) * 4; |
|
- | 195 | i2c.en_clk_reg = le16_to_cpu(gpio->usClkEnRegisterIndex) * 4; |
|
- | 196 | i2c.en_data_reg = le16_to_cpu(gpio->usDataEnRegisterIndex) * 4; |
|
- | 197 | i2c.y_clk_reg = le16_to_cpu(gpio->usClkY_RegisterIndex) * 4; |
|
- | 198 | i2c.y_data_reg = le16_to_cpu(gpio->usDataY_RegisterIndex) * 4; |
|
- | 199 | i2c.a_clk_reg = le16_to_cpu(gpio->usClkA_RegisterIndex) * 4; |
|
- | 200 | i2c.a_data_reg = le16_to_cpu(gpio->usDataA_RegisterIndex) * 4; |
|
- | 201 | i2c.mask_clk_mask = (1 << gpio->ucClkMaskShift); |
|
- | 202 | i2c.mask_data_mask = (1 << gpio->ucDataMaskShift); |
|
- | 203 | i2c.en_clk_mask = (1 << gpio->ucClkEnShift); |
|
- | 204 | i2c.en_data_mask = (1 << gpio->ucDataEnShift); |
|
- | 205 | i2c.y_clk_mask = (1 << gpio->ucClkY_Shift); |
|
- | 206 | i2c.y_data_mask = (1 << gpio->ucDataY_Shift); |
|
- | 207 | i2c.a_clk_mask = (1 << gpio->ucClkA_Shift); |
|
- | 208 | i2c.a_data_mask = (1 << gpio->ucDataA_Shift); |
|
- | 209 | ||
- | 210 | if (gpio->sucI2cId.sbfAccess.bfHW_Capable) |
|
- | 211 | i2c.hw_capable = true; |
|
- | 212 | else |
|
- | 213 | i2c.hw_capable = false; |
|
- | 214 | ||
- | 215 | if (gpio->sucI2cId.ucAccess == 0xa0) |
|
- | 216 | i2c.mm_i2c = true; |
|
- | 217 | else |
|
- | 218 | i2c.mm_i2c = false; |
|
- | 219 | ||
- | 220 | i2c.i2c_id = gpio->sucI2cId.ucAccess; |
|
- | 221 | ||
- | 222 | if (i2c.mask_clk_reg) { |
|
- | 223 | i2c.valid = true; |
|
- | 224 | sprintf(stmp, "0x%x", i2c.i2c_id); |
|
- | 225 | rdev->i2c_bus[i] = radeon_i2c_create(rdev->ddev, &i2c, stmp); |
|
- | 226 | } |
|
120 | 227 | } |
|
121 | return i2c; |
228 | } |
122 | } |
229 | } |
123 | 230 | ||
124 | static inline struct radeon_gpio_rec radeon_lookup_gpio(struct radeon_device *rdev, |
231 | static inline struct radeon_gpio_rec radeon_lookup_gpio(struct radeon_device *rdev, |
Line 133... | Line 240... | ||
133 | int i, num_indices; |
240 | int i, num_indices; |
Line 134... | Line 241... | ||
134 | 241 | ||
135 | memset(&gpio, 0, sizeof(struct radeon_gpio_rec)); |
242 | memset(&gpio, 0, sizeof(struct radeon_gpio_rec)); |
Line 136... | Line 243... | ||
136 | gpio.valid = false; |
243 | gpio.valid = false; |
137 | - | ||
138 | atom_parse_data_header(ctx, index, &size, NULL, NULL, &data_offset); |
244 | |
Line 139... | Line 245... | ||
139 | 245 | if (atom_parse_data_header(ctx, index, &size, NULL, NULL, &data_offset)) { |
|
- | 246 | gpio_info = (struct _ATOM_GPIO_PIN_LUT *)(ctx->bios + data_offset); |
|
Line 140... | Line 247... | ||
140 | gpio_info = (struct _ATOM_GPIO_PIN_LUT *)(ctx->bios + data_offset); |
247 | |
141 | 248 | num_indices = (size - sizeof(ATOM_COMMON_TABLE_HEADER)) / |
|
142 | num_indices = (size - sizeof(ATOM_COMMON_TABLE_HEADER)) / sizeof(ATOM_GPIO_PIN_ASSIGNMENT); |
249 | sizeof(ATOM_GPIO_PIN_ASSIGNMENT); |
143 | 250 | ||
144 | for (i = 0; i < num_indices; i++) { |
251 | for (i = 0; i < num_indices; i++) { |
145 | pin = &gpio_info->asGPIO_Pin[i]; |
252 | pin = &gpio_info->asGPIO_Pin[i]; |
146 | if (id == pin->ucGPIO_ID) { |
253 | if (id == pin->ucGPIO_ID) { |
147 | gpio.id = pin->ucGPIO_ID; |
254 | gpio.id = pin->ucGPIO_ID; |
148 | gpio.reg = pin->usGpioPin_AIndex * 4; |
255 | gpio.reg = le16_to_cpu(pin->usGpioPin_AIndex) * 4; |
149 | gpio.mask = (1 << pin->ucGpioPinBitShift); |
256 | gpio.mask = (1 << pin->ucGpioPinBitShift); |
- | 257 | gpio.valid = true; |
|
Line 150... | Line 258... | ||
150 | gpio.valid = true; |
258 | break; |
151 | break; |
259 | } |
Line 152... | Line 260... | ||
152 | } |
260 | } |
153 | } |
261 | } |
154 | 262 | ||
155 | return gpio; |
263 | return gpio; |
156 | } |
264 | } |
Line -... | Line 265... | ||
- | 265 | ||
- | 266 | static struct radeon_hpd radeon_atom_get_hpd_info_from_gpio(struct radeon_device *rdev, |
|
157 | 267 | struct radeon_gpio_rec *gpio) |
|
158 | static struct radeon_hpd radeon_atom_get_hpd_info_from_gpio(struct radeon_device *rdev, |
268 | { |
159 | struct radeon_gpio_rec *gpio) |
269 | struct radeon_hpd hpd; |
160 | { |
270 | u32 reg; |
Line 220... | Line 330... | ||
220 | if ((*connector_type == DRM_MODE_CONNECTOR_HDMIA) && |
330 | if ((*connector_type == DRM_MODE_CONNECTOR_HDMIA) && |
221 | (supported_device == ATOM_DEVICE_DFP3_SUPPORT)) |
331 | (supported_device == ATOM_DEVICE_DFP3_SUPPORT)) |
222 | *connector_type = DRM_MODE_CONNECTOR_DVID; |
332 | *connector_type = DRM_MODE_CONNECTOR_DVID; |
223 | } |
333 | } |
Line -... | Line 334... | ||
- | 334 | ||
- | 335 | /* MSI K9A2GM V2/V3 board has no HDMI or DVI */ |
|
- | 336 | if ((dev->pdev->device == 0x796e) && |
|
- | 337 | (dev->pdev->subsystem_vendor == 0x1462) && |
|
- | 338 | (dev->pdev->subsystem_device == 0x7302)) { |
|
- | 339 | if ((supported_device == ATOM_DEVICE_DFP2_SUPPORT) || |
|
- | 340 | (supported_device == ATOM_DEVICE_DFP3_SUPPORT)) |
|
- | 341 | return false; |
|
- | 342 | } |
|
224 | 343 | ||
225 | /* a-bit f-i90hd - ciaranm on #radeonhd - this board has no DVI */ |
344 | /* a-bit f-i90hd - ciaranm on #radeonhd - this board has no DVI */ |
226 | if ((dev->pdev->device == 0x7941) && |
345 | if ((dev->pdev->device == 0x7941) && |
227 | (dev->pdev->subsystem_vendor == 0x147b) && |
346 | (dev->pdev->subsystem_vendor == 0x147b) && |
228 | (dev->pdev->subsystem_device == 0x2412)) { |
347 | (dev->pdev->subsystem_device == 0x2412)) { |
Line 262... | Line 381... | ||
262 | (dev->pdev->subsystem_vendor == 0x106b) && |
381 | (dev->pdev->subsystem_vendor == 0x106b) && |
263 | (dev->pdev->subsystem_device == 0x0080)) { |
382 | (dev->pdev->subsystem_device == 0x0080)) { |
264 | if ((supported_device == ATOM_DEVICE_CRT1_SUPPORT) || |
383 | if ((supported_device == ATOM_DEVICE_CRT1_SUPPORT) || |
265 | (supported_device == ATOM_DEVICE_DFP2_SUPPORT)) |
384 | (supported_device == ATOM_DEVICE_DFP2_SUPPORT)) |
266 | return false; |
385 | return false; |
- | 386 | if (supported_device == ATOM_DEVICE_CRT2_SUPPORT) |
|
- | 387 | *line_mux = 0x90; |
|
- | 388 | } |
|
- | 389 | ||
- | 390 | /* mac rv630, rv730, others */ |
|
- | 391 | if ((supported_device == ATOM_DEVICE_TV1_SUPPORT) && |
|
- | 392 | (*connector_type == DRM_MODE_CONNECTOR_DVII)) { |
|
- | 393 | *connector_type = DRM_MODE_CONNECTOR_9PinDIN; |
|
- | 394 | *line_mux = CONNECTOR_7PIN_DIN_ENUM_ID1; |
|
267 | } |
395 | } |
Line 268... | Line 396... | ||
268 | 396 | ||
269 | /* ASUS HD 3600 XT board lists the DVI port as HDMI */ |
397 | /* ASUS HD 3600 XT board lists the DVI port as HDMI */ |
270 | if ((dev->pdev->device == 0x9598) && |
398 | if ((dev->pdev->device == 0x9598) && |
Line 273... | Line 401... | ||
273 | if (*connector_type == DRM_MODE_CONNECTOR_HDMIA) { |
401 | if (*connector_type == DRM_MODE_CONNECTOR_HDMIA) { |
274 | *connector_type = DRM_MODE_CONNECTOR_DVII; |
402 | *connector_type = DRM_MODE_CONNECTOR_DVII; |
275 | } |
403 | } |
276 | } |
404 | } |
Line -... | Line 405... | ||
- | 405 | ||
- | 406 | /* ASUS HD 3600 board lists the DVI port as HDMI */ |
|
- | 407 | if ((dev->pdev->device == 0x9598) && |
|
- | 408 | (dev->pdev->subsystem_vendor == 0x1043) && |
|
- | 409 | (dev->pdev->subsystem_device == 0x01e4)) { |
|
- | 410 | if (*connector_type == DRM_MODE_CONNECTOR_HDMIA) { |
|
- | 411 | *connector_type = DRM_MODE_CONNECTOR_DVII; |
|
- | 412 | } |
|
- | 413 | } |
|
277 | 414 | ||
278 | /* ASUS HD 3450 board lists the DVI port as HDMI */ |
415 | /* ASUS HD 3450 board lists the DVI port as HDMI */ |
279 | if ((dev->pdev->device == 0x95C5) && |
416 | if ((dev->pdev->device == 0x95C5) && |
280 | (dev->pdev->subsystem_vendor == 0x1043) && |
417 | (dev->pdev->subsystem_vendor == 0x1043) && |
281 | (dev->pdev->subsystem_device == 0x01e2)) { |
418 | (dev->pdev->subsystem_device == 0x01e2)) { |
Line 292... | Line 429... | ||
292 | *connector_type = DRM_MODE_CONNECTOR_VGA; |
429 | *connector_type = DRM_MODE_CONNECTOR_VGA; |
293 | *line_mux = 0; |
430 | *line_mux = 0; |
294 | } |
431 | } |
295 | } |
432 | } |
Line 296... | Line 433... | ||
296 | 433 | ||
- | 434 | /* Acer laptop (Acer TravelMate 5730/5730G) has an HDMI port |
|
- | 435 | * on the laptop and a DVI port on the docking station and |
|
- | 436 | * both share the same encoder, hpd pin, and ddc line. |
|
- | 437 | * So while the bios table is technically correct, |
|
- | 438 | * we drop the DVI port here since xrandr has no concept of |
|
- | 439 | * encoders and will try and drive both connectors |
|
- | 440 | * with different crtcs which isn't possible on the hardware |
|
- | 441 | * side and leaves no crtcs for LVDS or VGA. |
|
297 | /* Acer laptop reports DVI-D as DVI-I */ |
442 | */ |
298 | if ((dev->pdev->device == 0x95c4) && |
443 | if (((dev->pdev->device == 0x95c4) || (dev->pdev->device == 0x9591)) && |
299 | (dev->pdev->subsystem_vendor == 0x1025) && |
444 | (dev->pdev->subsystem_vendor == 0x1025) && |
300 | (dev->pdev->subsystem_device == 0x013c)) { |
445 | (dev->pdev->subsystem_device == 0x013c)) { |
301 | if ((*connector_type == DRM_MODE_CONNECTOR_DVII) && |
446 | if ((*connector_type == DRM_MODE_CONNECTOR_DVII) && |
- | 447 | (supported_device == ATOM_DEVICE_DFP1_SUPPORT)) { |
|
302 | (supported_device == ATOM_DEVICE_DFP1_SUPPORT)) |
448 | /* actually it's a DVI-D port not DVI-I */ |
- | 449 | *connector_type = DRM_MODE_CONNECTOR_DVID; |
|
- | 450 | return false; |
|
303 | *connector_type = DRM_MODE_CONNECTOR_DVID; |
451 | } |
Line 304... | Line 452... | ||
304 | } |
452 | } |
305 | 453 | ||
306 | /* XFX Pine Group device rv730 reports no VGA DDC lines |
454 | /* XFX Pine Group device rv730 reports no VGA DDC lines |
Line 383... | Line 531... | ||
383 | struct atom_context *ctx = mode_info->atom_context; |
531 | struct atom_context *ctx = mode_info->atom_context; |
384 | int index = GetIndexIntoMasterTable(DATA, Object_Header); |
532 | int index = GetIndexIntoMasterTable(DATA, Object_Header); |
385 | u16 size, data_offset; |
533 | u16 size, data_offset; |
386 | u8 frev, crev; |
534 | u8 frev, crev; |
387 | ATOM_CONNECTOR_OBJECT_TABLE *con_obj; |
535 | ATOM_CONNECTOR_OBJECT_TABLE *con_obj; |
- | 536 | ATOM_ENCODER_OBJECT_TABLE *enc_obj; |
|
- | 537 | ATOM_OBJECT_TABLE *router_obj; |
|
388 | ATOM_DISPLAY_OBJECT_PATH_TABLE *path_obj; |
538 | ATOM_DISPLAY_OBJECT_PATH_TABLE *path_obj; |
389 | ATOM_OBJECT_HEADER *obj_header; |
539 | ATOM_OBJECT_HEADER *obj_header; |
390 | int i, j, path_size, device_support; |
540 | int i, j, k, path_size, device_support; |
391 | int connector_type; |
541 | int connector_type; |
392 | u16 igp_lane_info, conn_id, connector_object_id; |
542 | u16 igp_lane_info, conn_id, connector_object_id; |
393 | bool linkb; |
- | |
394 | struct radeon_i2c_bus_rec ddc_bus; |
543 | struct radeon_i2c_bus_rec ddc_bus; |
- | 544 | struct radeon_router router; |
|
395 | struct radeon_gpio_rec gpio; |
545 | struct radeon_gpio_rec gpio; |
396 | struct radeon_hpd hpd; |
546 | struct radeon_hpd hpd; |
Line 397... | Line 547... | ||
397 | 547 | ||
398 | atom_parse_data_header(ctx, index, &size, &frev, &crev, &data_offset); |
- | |
399 | - | ||
400 | if (data_offset == 0) |
548 | if (!atom_parse_data_header(ctx, index, &size, &frev, &crev, &data_offset)) |
Line 401... | Line 549... | ||
401 | return false; |
549 | return false; |
402 | 550 | ||
Line 408... | Line 556... | ||
408 | (ctx->bios + data_offset + |
556 | (ctx->bios + data_offset + |
409 | le16_to_cpu(obj_header->usDisplayPathTableOffset)); |
557 | le16_to_cpu(obj_header->usDisplayPathTableOffset)); |
410 | con_obj = (ATOM_CONNECTOR_OBJECT_TABLE *) |
558 | con_obj = (ATOM_CONNECTOR_OBJECT_TABLE *) |
411 | (ctx->bios + data_offset + |
559 | (ctx->bios + data_offset + |
412 | le16_to_cpu(obj_header->usConnectorObjectTableOffset)); |
560 | le16_to_cpu(obj_header->usConnectorObjectTableOffset)); |
- | 561 | enc_obj = (ATOM_ENCODER_OBJECT_TABLE *) |
|
- | 562 | (ctx->bios + data_offset + |
|
- | 563 | le16_to_cpu(obj_header->usEncoderObjectTableOffset)); |
|
- | 564 | router_obj = (ATOM_OBJECT_TABLE *) |
|
- | 565 | (ctx->bios + data_offset + |
|
- | 566 | le16_to_cpu(obj_header->usRouterObjectTableOffset)); |
|
413 | device_support = le16_to_cpu(obj_header->usDeviceSupport); |
567 | device_support = le16_to_cpu(obj_header->usDeviceSupport); |
Line 414... | Line 568... | ||
414 | 568 | ||
415 | path_size = 0; |
569 | path_size = 0; |
416 | for (i = 0; i < path_obj->ucNumOfDispPath; i++) { |
570 | for (i = 0; i < path_obj->ucNumOfDispPath; i++) { |
417 | uint8_t *addr = (uint8_t *) path_obj->asDispPath; |
571 | uint8_t *addr = (uint8_t *) path_obj->asDispPath; |
418 | ATOM_DISPLAY_OBJECT_PATH *path; |
572 | ATOM_DISPLAY_OBJECT_PATH *path; |
419 | addr += path_size; |
573 | addr += path_size; |
420 | path = (ATOM_DISPLAY_OBJECT_PATH *) addr; |
574 | path = (ATOM_DISPLAY_OBJECT_PATH *) addr; |
421 | path_size += le16_to_cpu(path->usSize); |
- | |
- | 575 | path_size += le16_to_cpu(path->usSize); |
|
422 | linkb = false; |
576 | |
423 | if (device_support & le16_to_cpu(path->usDeviceTag)) { |
577 | if (device_support & le16_to_cpu(path->usDeviceTag)) { |
Line 424... | Line 578... | ||
424 | uint8_t con_obj_id, con_obj_num, con_obj_type; |
578 | uint8_t con_obj_id, con_obj_num, con_obj_type; |
425 | 579 | ||
Line 447... | Line 601... | ||
447 | 601 | ||
448 | index = |
602 | index = |
449 | GetIndexIntoMasterTable(DATA, |
603 | GetIndexIntoMasterTable(DATA, |
Line 450... | Line 604... | ||
450 | IntegratedSystemInfo); |
604 | IntegratedSystemInfo); |
451 | 605 | ||
Line 452... | Line 606... | ||
452 | atom_parse_data_header(ctx, index, &size, &frev, |
606 | if (atom_parse_data_header(ctx, index, &size, &frev, |
453 | &crev, &igp_offset); |
607 | &crev, &igp_offset)) { |
454 | 608 | ||
455 | if (crev >= 2) { |
609 | if (crev >= 2) { |
Line 484... | Line 638... | ||
484 | igp_lane_info = 0; |
638 | igp_lane_info = 0; |
485 | connector_type = |
639 | connector_type = |
486 | object_connector_convert[con_obj_id]; |
640 | object_connector_convert[con_obj_id]; |
487 | connector_object_id = con_obj_id; |
641 | connector_object_id = con_obj_id; |
488 | } |
642 | } |
- | 643 | } else { |
|
- | 644 | igp_lane_info = 0; |
|
- | 645 | connector_type = |
|
- | 646 | object_connector_convert[con_obj_id]; |
|
- | 647 | connector_object_id = con_obj_id; |
|
- | 648 | } |
|
Line 489... | Line 649... | ||
489 | 649 | ||
490 | if (connector_type == DRM_MODE_CONNECTOR_Unknown) |
650 | if (connector_type == DRM_MODE_CONNECTOR_Unknown) |
Line -... | Line 651... | ||
- | 651 | continue; |
|
- | 652 | ||
491 | continue; |
653 | router.ddc_valid = false; |
492 | - | ||
493 | for (j = 0; j < ((le16_to_cpu(path->usSize) - 8) / 2); |
654 | router.cd_valid = false; |
Line 494... | Line 655... | ||
494 | j++) { |
655 | for (j = 0; j < ((le16_to_cpu(path->usSize) - 8) / 2); j++) { |
495 | uint8_t enc_obj_id, enc_obj_num, enc_obj_type; |
656 | uint8_t grph_obj_id, grph_obj_num, grph_obj_type; |
496 | 657 | ||
497 | enc_obj_id = |
658 | grph_obj_id = |
498 | (le16_to_cpu(path->usGraphicObjIds[j]) & |
659 | (le16_to_cpu(path->usGraphicObjIds[j]) & |
499 | OBJECT_ID_MASK) >> OBJECT_ID_SHIFT; |
660 | OBJECT_ID_MASK) >> OBJECT_ID_SHIFT; |
500 | enc_obj_num = |
661 | grph_obj_num = |
501 | (le16_to_cpu(path->usGraphicObjIds[j]) & |
662 | (le16_to_cpu(path->usGraphicObjIds[j]) & |
502 | ENUM_ID_MASK) >> ENUM_ID_SHIFT; |
663 | ENUM_ID_MASK) >> ENUM_ID_SHIFT; |
Line 503... | Line -... | ||
503 | enc_obj_type = |
- | |
504 | (le16_to_cpu(path->usGraphicObjIds[j]) & |
664 | grph_obj_type = |
505 | OBJECT_TYPE_MASK) >> OBJECT_TYPE_SHIFT; |
665 | (le16_to_cpu(path->usGraphicObjIds[j]) & |
- | 666 | OBJECT_TYPE_MASK) >> OBJECT_TYPE_SHIFT; |
|
- | 667 | ||
- | 668 | if (grph_obj_type == GRAPH_OBJECT_TYPE_ENCODER) { |
|
506 | 669 | for (k = 0; k < enc_obj->ucNumberOfObjects; k++) { |
|
- | 670 | u16 encoder_obj = le16_to_cpu(enc_obj->asObjects[k].usObjectID); |
|
507 | /* FIXME: add support for router objects */ |
671 | if (le16_to_cpu(path->usGraphicObjIds[j]) == encoder_obj) { |
508 | if (enc_obj_type == GRAPH_OBJECT_TYPE_ENCODER) { |
672 | ATOM_COMMON_RECORD_HEADER *record = (ATOM_COMMON_RECORD_HEADER *) |
509 | if (enc_obj_num == 2) |
673 | (ctx->bios + data_offset + |
- | 674 | le16_to_cpu(enc_obj->asObjects[k].usRecordOffset)); |
|
- | 675 | ATOM_ENCODER_CAP_RECORD *cap_record; |
|
- | 676 | u16 caps = 0; |
|
- | 677 | ||
- | 678 | while (record->ucRecordSize > 0 && |
|
- | 679 | record->ucRecordType > 0 && |
|
- | 680 | record->ucRecordType <= ATOM_MAX_OBJECT_RECORD_NUMBER) { |
|
- | 681 | switch (record->ucRecordType) { |
|
- | 682 | case ATOM_ENCODER_CAP_RECORD_TYPE: |
|
- | 683 | cap_record =(ATOM_ENCODER_CAP_RECORD *) |
|
- | 684 | record; |
|
- | 685 | caps = le16_to_cpu(cap_record->usEncoderCap); |
|
- | 686 | break; |
|
510 | linkb = true; |
687 | } |
511 | else |
688 | record = (ATOM_COMMON_RECORD_HEADER *) |
512 | linkb = false; |
689 | ((char *)record + record->ucRecordSize); |
513 | 690 | } |
|
514 | radeon_add_atom_encoder(dev, |
691 | radeon_add_atom_encoder(dev, |
- | 692 | encoder_obj, |
|
- | 693 | le16_to_cpu |
|
- | 694 | (path-> |
|
- | 695 | usDeviceTag), |
|
- | 696 | caps); |
|
- | 697 | } |
|
- | 698 | } |
|
- | 699 | } else if (grph_obj_type == GRAPH_OBJECT_TYPE_ROUTER) { |
|
- | 700 | for (k = 0; k < router_obj->ucNumberOfObjects; k++) { |
|
- | 701 | u16 router_obj_id = le16_to_cpu(router_obj->asObjects[k].usObjectID); |
|
- | 702 | if (le16_to_cpu(path->usGraphicObjIds[j]) == router_obj_id) { |
|
- | 703 | ATOM_COMMON_RECORD_HEADER *record = (ATOM_COMMON_RECORD_HEADER *) |
|
- | 704 | (ctx->bios + data_offset + |
|
- | 705 | le16_to_cpu(router_obj->asObjects[k].usRecordOffset)); |
|
- | 706 | ATOM_I2C_RECORD *i2c_record; |
|
- | 707 | ATOM_I2C_ID_CONFIG_ACCESS *i2c_config; |
|
- | 708 | ATOM_ROUTER_DDC_PATH_SELECT_RECORD *ddc_path; |
|
- | 709 | ATOM_ROUTER_DATA_CLOCK_PATH_SELECT_RECORD *cd_path; |
|
- | 710 | ATOM_SRC_DST_TABLE_FOR_ONE_OBJECT *router_src_dst_table = |
|
- | 711 | (ATOM_SRC_DST_TABLE_FOR_ONE_OBJECT *) |
|
- | 712 | (ctx->bios + data_offset + |
|
- | 713 | le16_to_cpu(router_obj->asObjects[k].usSrcDstTableOffset)); |
|
- | 714 | int enum_id; |
|
- | 715 | ||
- | 716 | router.router_id = router_obj_id; |
|
- | 717 | for (enum_id = 0; enum_id < router_src_dst_table->ucNumberOfDst; |
|
- | 718 | enum_id++) { |
|
Line -... | Line 719... | ||
- | 719 | if (le16_to_cpu(path->usConnObjectId) == |
|
- | 720 | le16_to_cpu(router_src_dst_table->usDstObjectID[enum_id])) |
|
- | 721 | break; |
|
- | 722 | } |
|
- | 723 | ||
- | 724 | while (record->ucRecordSize > 0 && |
|
- | 725 | record->ucRecordType > 0 && |
|
- | 726 | record->ucRecordType <= ATOM_MAX_OBJECT_RECORD_NUMBER) { |
|
- | 727 | switch (record->ucRecordType) { |
|
- | 728 | case ATOM_I2C_RECORD_TYPE: |
|
- | 729 | i2c_record = |
|
- | 730 | (ATOM_I2C_RECORD *) |
|
- | 731 | record; |
|
- | 732 | i2c_config = |
|
- | 733 | (ATOM_I2C_ID_CONFIG_ACCESS *) |
|
- | 734 | &i2c_record->sucI2cId; |
|
- | 735 | router.i2c_info = |
|
- | 736 | radeon_lookup_i2c_gpio(rdev, |
|
- | 737 | i2c_config-> |
|
- | 738 | ucAccess); |
|
- | 739 | router.i2c_addr = i2c_record->ucI2CAddr >> 1; |
|
- | 740 | break; |
|
- | 741 | case ATOM_ROUTER_DDC_PATH_SELECT_RECORD_TYPE: |
|
- | 742 | ddc_path = (ATOM_ROUTER_DDC_PATH_SELECT_RECORD *) |
|
- | 743 | record; |
|
- | 744 | router.ddc_valid = true; |
|
- | 745 | router.ddc_mux_type = ddc_path->ucMuxType; |
|
- | 746 | router.ddc_mux_control_pin = ddc_path->ucMuxControlPin; |
|
- | 747 | router.ddc_mux_state = ddc_path->ucMuxState[enum_id]; |
|
- | 748 | break; |
|
- | 749 | case ATOM_ROUTER_DATA_CLOCK_PATH_SELECT_RECORD_TYPE: |
|
- | 750 | cd_path = (ATOM_ROUTER_DATA_CLOCK_PATH_SELECT_RECORD *) |
|
- | 751 | record; |
|
- | 752 | router.cd_valid = true; |
|
- | 753 | router.cd_mux_type = cd_path->ucMuxType; |
|
- | 754 | router.cd_mux_control_pin = cd_path->ucMuxControlPin; |
|
- | 755 | router.cd_mux_state = cd_path->ucMuxState[enum_id]; |
|
- | 756 | break; |
|
- | 757 | } |
|
515 | enc_obj_id, |
758 | record = (ATOM_COMMON_RECORD_HEADER *) |
516 | le16_to_cpu |
759 | ((char *)record + record->ucRecordSize); |
Line 517... | Line 760... | ||
517 | (path-> |
760 | } |
- | 761 | } |
|
- | 762 | } |
|
518 | usDeviceTag)); |
763 | } |
519 | 764 | } |
|
520 | } |
765 | |
521 | } |
766 | /* look up gpio for ddc, hpd */ |
522 | 767 | ddc_bus.valid = false; |
|
Line 536... | Line 781... | ||
536 | asObjects[j]. |
781 | asObjects[j]. |
537 | usRecordOffset)); |
782 | usRecordOffset)); |
538 | ATOM_I2C_RECORD *i2c_record; |
783 | ATOM_I2C_RECORD *i2c_record; |
539 | ATOM_HPD_INT_RECORD *hpd_record; |
784 | ATOM_HPD_INT_RECORD *hpd_record; |
540 | ATOM_I2C_ID_CONFIG_ACCESS *i2c_config; |
785 | ATOM_I2C_ID_CONFIG_ACCESS *i2c_config; |
541 | hpd.hpd = RADEON_HPD_NONE; |
- | |
Line 542... | Line 786... | ||
542 | 786 | ||
543 | while (record->ucRecordType > 0 |
- | |
544 | && record-> |
787 | while (record->ucRecordSize > 0 && |
545 | ucRecordType <= |
788 | record->ucRecordType > 0 && |
546 | ATOM_MAX_OBJECT_RECORD_NUMBER) { |
789 | record->ucRecordType <= ATOM_MAX_OBJECT_RECORD_NUMBER) { |
547 | switch (record->ucRecordType) { |
790 | switch (record->ucRecordType) { |
548 | case ATOM_I2C_RECORD_TYPE: |
791 | case ATOM_I2C_RECORD_TYPE: |
549 | i2c_record = |
792 | i2c_record = |
550 | (ATOM_I2C_RECORD *) |
793 | (ATOM_I2C_RECORD *) |
Line 574... | Line 817... | ||
574 | ucRecordSize); |
817 | ucRecordSize); |
575 | } |
818 | } |
576 | break; |
819 | break; |
577 | } |
820 | } |
578 | } |
821 | } |
579 | } else { |
- | |
580 | hpd.hpd = RADEON_HPD_NONE; |
- | |
581 | ddc_bus.valid = false; |
- | |
582 | } |
822 | } |
Line 583... | Line 823... | ||
583 | 823 | ||
584 | /* needed for aux chan transactions */ |
824 | /* needed for aux chan transactions */ |
Line 585... | Line 825... | ||
585 | ddc_bus.hpd_id = hpd.hpd ? (hpd.hpd - 1) : 0; |
825 | ddc_bus.hpd = hpd.hpd; |
Line 586... | Line 826... | ||
586 | 826 | ||
587 | conn_id = le16_to_cpu(path->usConnObjectId); |
827 | conn_id = le16_to_cpu(path->usConnObjectId); |
Line 594... | Line 834... | ||
594 | radeon_add_atom_connector(dev, |
834 | radeon_add_atom_connector(dev, |
595 | conn_id, |
835 | conn_id, |
596 | le16_to_cpu(path-> |
836 | le16_to_cpu(path-> |
597 | usDeviceTag), |
837 | usDeviceTag), |
598 | connector_type, &ddc_bus, |
838 | connector_type, &ddc_bus, |
599 | linkb, igp_lane_info, |
839 | igp_lane_info, |
600 | connector_object_id, |
840 | connector_object_id, |
601 | &hpd); |
841 | &hpd, |
- | 842 | &router); |
|
Line 602... | Line 843... | ||
602 | 843 | ||
603 | } |
844 | } |
Line 604... | Line 845... | ||
604 | } |
845 | } |
Line 625... | Line 866... | ||
625 | int index = GetIndexIntoMasterTable(DATA, XTMDS_Info); |
866 | int index = GetIndexIntoMasterTable(DATA, XTMDS_Info); |
626 | uint16_t size, data_offset; |
867 | uint16_t size, data_offset; |
627 | uint8_t frev, crev; |
868 | uint8_t frev, crev; |
628 | ATOM_XTMDS_INFO *xtmds; |
869 | ATOM_XTMDS_INFO *xtmds; |
Line 629... | Line 870... | ||
629 | 870 | ||
630 | atom_parse_data_header(ctx, index, &size, &frev, &crev, &data_offset); |
871 | if (atom_parse_data_header(ctx, index, &size, &frev, &crev, &data_offset)) { |
Line 631... | Line 872... | ||
631 | xtmds = (ATOM_XTMDS_INFO *)(ctx->bios + data_offset); |
872 | xtmds = (ATOM_XTMDS_INFO *)(ctx->bios + data_offset); |
632 | 873 | ||
633 | if (xtmds->ucSupportedLink & ATOM_XTMDS_SUPPORTED_DUALLINK) { |
874 | if (xtmds->ucSupportedLink & ATOM_XTMDS_SUPPORTED_DUALLINK) { |
Line 639... | Line 880... | ||
639 | if (connector_type == DRM_MODE_CONNECTOR_DVII) |
880 | if (connector_type == DRM_MODE_CONNECTOR_DVII) |
640 | return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I; |
881 | return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I; |
641 | else |
882 | else |
642 | return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_D; |
883 | return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_D; |
643 | } |
884 | } |
- | 885 | } else |
|
- | 886 | return supported_devices_connector_object_id_convert |
|
- | 887 | [connector_type]; |
|
644 | } else { |
888 | } else { |
645 | return supported_devices_connector_object_id_convert |
889 | return supported_devices_connector_object_id_convert |
646 | [connector_type]; |
890 | [connector_type]; |
647 | } |
891 | } |
648 | } |
892 | } |
Line 668... | Line 912... | ||
668 | uint8_t frev, crev; |
912 | uint8_t frev, crev; |
669 | uint16_t device_support; |
913 | uint16_t device_support; |
670 | uint8_t dac; |
914 | uint8_t dac; |
671 | union atom_supported_devices *supported_devices; |
915 | union atom_supported_devices *supported_devices; |
672 | int i, j, max_device; |
916 | int i, j, max_device; |
- | 917 | struct bios_connector *bios_connectors; |
|
673 | struct bios_connector bios_connectors[ATOM_MAX_SUPPORTED_DEVICE]; |
918 | size_t bc_size = sizeof(*bios_connectors) * ATOM_MAX_SUPPORTED_DEVICE; |
- | 919 | struct radeon_router router; |
|
- | 920 | ||
- | 921 | router.ddc_valid = false; |
|
- | 922 | router.cd_valid = false; |
|
Line -... | Line 923... | ||
- | 923 | ||
- | 924 | bios_connectors = kzalloc(bc_size, GFP_KERNEL); |
|
- | 925 | if (!bios_connectors) |
|
- | 926 | return false; |
|
674 | 927 | ||
- | 928 | if (!atom_parse_data_header(ctx, index, &size, &frev, &crev, |
|
- | 929 | &data_offset)) { |
|
- | 930 | kfree(bios_connectors); |
|
- | 931 | return false; |
|
Line 675... | Line 932... | ||
675 | atom_parse_data_header(ctx, index, &size, &frev, &crev, &data_offset); |
932 | } |
676 | 933 | ||
Line 677... | Line 934... | ||
677 | supported_devices = |
934 | supported_devices = |
Line 693... | Line 950... | ||
693 | if (!(device_support & (1 << i))) { |
950 | if (!(device_support & (1 << i))) { |
694 | continue; |
951 | continue; |
695 | } |
952 | } |
Line 696... | Line 953... | ||
696 | 953 | ||
697 | if (i == ATOM_DEVICE_CV_INDEX) { |
954 | if (i == ATOM_DEVICE_CV_INDEX) { |
698 | DRM_DEBUG("Skipping Component Video\n"); |
955 | DRM_DEBUG_KMS("Skipping Component Video\n"); |
699 | continue; |
956 | continue; |
Line 700... | Line 957... | ||
700 | } |
957 | } |
701 | 958 | ||
Line 767... | Line 1024... | ||
767 | bios_connectors[i].valid = true; |
1024 | bios_connectors[i].valid = true; |
768 | bios_connectors[i].devices = (1 << i); |
1025 | bios_connectors[i].devices = (1 << i); |
Line 769... | Line 1026... | ||
769 | 1026 | ||
770 | if (ASIC_IS_AVIVO(rdev) || radeon_r4xx_atom) |
1027 | if (ASIC_IS_AVIVO(rdev) || radeon_r4xx_atom) |
771 | radeon_add_atom_encoder(dev, |
1028 | radeon_add_atom_encoder(dev, |
772 | radeon_get_encoder_id(dev, |
1029 | radeon_get_encoder_enum(dev, |
773 | (1 << i), |
1030 | (1 << i), |
774 | dac), |
1031 | dac), |
- | 1032 | (1 << i), |
|
775 | (1 << i)); |
1033 | 0); |
776 | else |
1034 | else |
777 | radeon_add_legacy_encoder(dev, |
1035 | radeon_add_legacy_encoder(dev, |
778 | radeon_get_encoder_id(dev, |
1036 | radeon_get_encoder_enum(dev, |
779 | (1 << i), |
1037 | (1 << i), |
780 | dac), |
1038 | dac), |
781 | (1 << i)); |
1039 | (1 << i)); |
Line 830... | Line 1088... | ||
830 | bios_connectors[i].line_mux, |
1088 | bios_connectors[i].line_mux, |
831 | bios_connectors[i].devices, |
1089 | bios_connectors[i].devices, |
832 | bios_connectors[i]. |
1090 | bios_connectors[i]. |
833 | connector_type, |
1091 | connector_type, |
834 | &bios_connectors[i].ddc_bus, |
1092 | &bios_connectors[i].ddc_bus, |
835 | false, 0, |
1093 | 0, |
836 | connector_object_id, |
1094 | connector_object_id, |
837 | &bios_connectors[i].hpd); |
1095 | &bios_connectors[i].hpd, |
- | 1096 | &router); |
|
838 | } |
1097 | } |
839 | } |
1098 | } |
Line 840... | Line 1099... | ||
840 | 1099 | ||
Line -... | Line 1100... | ||
- | 1100 | radeon_link_encoder_connector(dev); |
|
841 | radeon_link_encoder_connector(dev); |
1101 | |
842 | 1102 | kfree(bios_connectors); |
|
Line 843... | Line 1103... | ||
843 | return true; |
1103 | return true; |
844 | } |
1104 | } |
845 | 1105 | ||
846 | union firmware_info { |
1106 | union firmware_info { |
847 | ATOM_FIRMWARE_INFO info; |
1107 | ATOM_FIRMWARE_INFO info; |
848 | ATOM_FIRMWARE_INFO_V1_2 info_12; |
1108 | ATOM_FIRMWARE_INFO_V1_2 info_12; |
- | 1109 | ATOM_FIRMWARE_INFO_V1_3 info_13; |
|
849 | ATOM_FIRMWARE_INFO_V1_3 info_13; |
1110 | ATOM_FIRMWARE_INFO_V1_4 info_14; |
Line 850... | Line 1111... | ||
850 | ATOM_FIRMWARE_INFO_V1_4 info_14; |
1111 | ATOM_FIRMWARE_INFO_V2_1 info_21; |
851 | ATOM_FIRMWARE_INFO_V2_1 info_21; |
1112 | ATOM_FIRMWARE_INFO_V2_2 info_22; |
852 | }; |
1113 | }; |
Line 863... | Line 1124... | ||
863 | struct radeon_pll *dcpll = &rdev->clock.dcpll; |
1124 | struct radeon_pll *dcpll = &rdev->clock.dcpll; |
864 | struct radeon_pll *spll = &rdev->clock.spll; |
1125 | struct radeon_pll *spll = &rdev->clock.spll; |
865 | struct radeon_pll *mpll = &rdev->clock.mpll; |
1126 | struct radeon_pll *mpll = &rdev->clock.mpll; |
866 | uint16_t data_offset; |
1127 | uint16_t data_offset; |
Line 867... | Line 1128... | ||
867 | 1128 | ||
868 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, |
1129 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
869 | &crev, &data_offset); |
- | |
870 | 1130 | &frev, &crev, &data_offset)) { |
|
871 | firmware_info = |
1131 | firmware_info = |
872 | (union firmware_info *)(mode_info->atom_context->bios + |
1132 | (union firmware_info *)(mode_info->atom_context->bios + |
873 | data_offset); |
- | |
874 | - | ||
875 | if (firmware_info) { |
1133 | data_offset); |
876 | /* pixel clocks */ |
1134 | /* pixel clocks */ |
877 | p1pll->reference_freq = |
1135 | p1pll->reference_freq = |
878 | le16_to_cpu(firmware_info->info.usReferenceClock); |
1136 | le16_to_cpu(firmware_info->info.usReferenceClock); |
Line 885... | Line 1143... | ||
885 | p1pll->pll_out_min = |
1143 | p1pll->pll_out_min = |
886 | le32_to_cpu(firmware_info->info_12.ulMinPixelClockPLL_Output); |
1144 | le32_to_cpu(firmware_info->info_12.ulMinPixelClockPLL_Output); |
887 | p1pll->pll_out_max = |
1145 | p1pll->pll_out_max = |
888 | le32_to_cpu(firmware_info->info.ulMaxPixelClockPLL_Output); |
1146 | le32_to_cpu(firmware_info->info.ulMaxPixelClockPLL_Output); |
Line -... | Line 1147... | ||
- | 1147 | ||
- | 1148 | if (crev >= 4) { |
|
- | 1149 | p1pll->lcd_pll_out_min = |
|
- | 1150 | le16_to_cpu(firmware_info->info_14.usLcdMinPixelClockPLL_Output) * 100; |
|
- | 1151 | if (p1pll->lcd_pll_out_min == 0) |
|
- | 1152 | p1pll->lcd_pll_out_min = p1pll->pll_out_min; |
|
- | 1153 | p1pll->lcd_pll_out_max = |
|
- | 1154 | le16_to_cpu(firmware_info->info_14.usLcdMaxPixelClockPLL_Output) * 100; |
|
- | 1155 | if (p1pll->lcd_pll_out_max == 0) |
|
- | 1156 | p1pll->lcd_pll_out_max = p1pll->pll_out_max; |
|
- | 1157 | } else { |
|
- | 1158 | p1pll->lcd_pll_out_min = p1pll->pll_out_min; |
|
- | 1159 | p1pll->lcd_pll_out_max = p1pll->pll_out_max; |
|
- | 1160 | } |
|
889 | 1161 | ||
890 | if (p1pll->pll_out_min == 0) { |
1162 | if (p1pll->pll_out_min == 0) { |
891 | if (ASIC_IS_AVIVO(rdev)) |
1163 | if (ASIC_IS_AVIVO(rdev)) |
892 | p1pll->pll_out_min = 64800; |
1164 | p1pll->pll_out_min = 64800; |
893 | else |
1165 | else |
894 | p1pll->pll_out_min = 20000; |
- | |
895 | } else if (p1pll->pll_out_min > 64800) { |
- | |
896 | /* Limiting the pll output range is a good thing generally as |
- | |
897 | * it limits the number of possible pll combinations for a given |
- | |
898 | * frequency presumably to the ones that work best on each card. |
- | |
899 | * However, certain duallink DVI monitors seem to like |
- | |
900 | * pll combinations that would be limited by this at least on |
- | |
901 | * pre-DCE 3.0 r6xx hardware. This might need to be adjusted per |
- | |
902 | * family. |
- | |
903 | */ |
- | |
904 | if (!radeon_new_pll) |
- | |
905 | p1pll->pll_out_min = 64800; |
1166 | p1pll->pll_out_min = 20000; |
Line 906... | Line 1167... | ||
906 | } |
1167 | } |
907 | 1168 | ||
908 | p1pll->pll_in_min = |
1169 | p1pll->pll_in_min = |
909 | le16_to_cpu(firmware_info->info.usMinPixelClockPLL_Input); |
1170 | le16_to_cpu(firmware_info->info.usMinPixelClockPLL_Input); |
Line 910... | Line 1171... | ||
910 | p1pll->pll_in_max = |
1171 | p1pll->pll_in_max = |
Line 911... | Line 1172... | ||
911 | le16_to_cpu(firmware_info->info.usMaxPixelClockPLL_Input); |
1172 | le16_to_cpu(firmware_info->info.usMaxPixelClockPLL_Input); |
- | 1173 | ||
- | 1174 | *p2pll = *p1pll; |
|
- | 1175 | ||
- | 1176 | /* system clock */ |
|
912 | 1177 | if (ASIC_IS_DCE4(rdev)) |
|
913 | *p2pll = *p1pll; |
1178 | spll->reference_freq = |
914 | 1179 | le16_to_cpu(firmware_info->info_21.usCoreReferenceClock); |
|
Line 915... | Line 1180... | ||
915 | /* system clock */ |
1180 | else |
Line 934... | Line 1199... | ||
934 | le16_to_cpu(firmware_info->info.usMinEngineClockPLL_Input); |
1199 | le16_to_cpu(firmware_info->info.usMinEngineClockPLL_Input); |
935 | spll->pll_in_max = |
1200 | spll->pll_in_max = |
936 | le16_to_cpu(firmware_info->info.usMaxEngineClockPLL_Input); |
1201 | le16_to_cpu(firmware_info->info.usMaxEngineClockPLL_Input); |
Line 937... | Line 1202... | ||
937 | 1202 | ||
- | 1203 | /* memory clock */ |
|
- | 1204 | if (ASIC_IS_DCE4(rdev)) |
|
- | 1205 | mpll->reference_freq = |
|
- | 1206 | le16_to_cpu(firmware_info->info_21.usMemoryReferenceClock); |
|
938 | /* memory clock */ |
1207 | else |
939 | mpll->reference_freq = |
1208 | mpll->reference_freq = |
940 | le16_to_cpu(firmware_info->info.usReferenceClock); |
1209 | le16_to_cpu(firmware_info->info.usReferenceClock); |
Line 941... | Line 1210... | ||
941 | mpll->reference_div = 0; |
1210 | mpll->reference_div = 0; |
Line 964... | Line 1233... | ||
964 | le32_to_cpu(firmware_info->info.ulDefaultMemoryClock); |
1233 | le32_to_cpu(firmware_info->info.ulDefaultMemoryClock); |
Line 965... | Line 1234... | ||
965 | 1234 | ||
966 | if (ASIC_IS_DCE4(rdev)) { |
1235 | if (ASIC_IS_DCE4(rdev)) { |
967 | rdev->clock.default_dispclk = |
1236 | rdev->clock.default_dispclk = |
968 | le32_to_cpu(firmware_info->info_21.ulDefaultDispEngineClkFreq); |
1237 | le32_to_cpu(firmware_info->info_21.ulDefaultDispEngineClkFreq); |
- | 1238 | if (rdev->clock.default_dispclk == 0) { |
|
- | 1239 | if (ASIC_IS_DCE5(rdev)) |
|
- | 1240 | rdev->clock.default_dispclk = 54000; /* 540 Mhz */ |
|
969 | if (rdev->clock.default_dispclk == 0) |
1241 | else |
- | 1242 | rdev->clock.default_dispclk = 60000; /* 600 Mhz */ |
|
970 | rdev->clock.default_dispclk = 60000; /* 600 Mhz */ |
1243 | } |
971 | rdev->clock.dp_extclk = |
1244 | rdev->clock.dp_extclk = |
972 | le16_to_cpu(firmware_info->info_21.usUniphyDPModeExtClkFreq); |
1245 | le16_to_cpu(firmware_info->info_21.usUniphyDPModeExtClkFreq); |
973 | } |
1246 | } |
Line -... | Line 1247... | ||
- | 1247 | *dcpll = *p1pll; |
|
- | 1248 | ||
- | 1249 | rdev->clock.max_pixel_clock = le16_to_cpu(firmware_info->info.usMaxPixelClock); |
|
- | 1250 | if (rdev->clock.max_pixel_clock == 0) |
|
974 | *dcpll = *p1pll; |
1251 | rdev->clock.max_pixel_clock = 40000; |
975 | 1252 | ||
Line 976... | Line 1253... | ||
976 | return true; |
1253 | return true; |
977 | } |
1254 | } |
Line 990... | Line 1267... | ||
990 | int index = GetIndexIntoMasterTable(DATA, IntegratedSystemInfo); |
1267 | int index = GetIndexIntoMasterTable(DATA, IntegratedSystemInfo); |
991 | union igp_info *igp_info; |
1268 | union igp_info *igp_info; |
992 | u8 frev, crev; |
1269 | u8 frev, crev; |
993 | u16 data_offset; |
1270 | u16 data_offset; |
Line 994... | Line 1271... | ||
994 | 1271 | ||
995 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, |
1272 | /* sideport is AMD only */ |
- | 1273 | if (rdev->family == CHIP_RS600) |
|
Line -... | Line 1274... | ||
- | 1274 | return false; |
|
- | 1275 | ||
996 | &crev, &data_offset); |
1276 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
997 | 1277 | &frev, &crev, &data_offset)) { |
|
998 | igp_info = (union igp_info *)(mode_info->atom_context->bios + |
- | |
999 | data_offset); |
- | |
1000 | 1278 | igp_info = (union igp_info *)(mode_info->atom_context->bios + |
|
1001 | if (igp_info) { |
1279 | data_offset); |
1002 | switch (crev) { |
1280 | switch (crev) { |
1003 | case 1: |
1281 | case 1: |
1004 | if (igp_info->info.ucMemoryType & 0xf0) |
1282 | if (le32_to_cpu(igp_info->info.ulBootUpMemoryClock)) |
1005 | return true; |
1283 | return true; |
1006 | break; |
1284 | break; |
1007 | case 2: |
1285 | case 2: |
1008 | if (igp_info->info_2.ucMemoryType & 0x0f) |
1286 | if (le32_to_cpu(igp_info->info_2.ulBootUpSidePortClock)) |
1009 | return true; |
1287 | return true; |
1010 | break; |
1288 | break; |
1011 | default: |
1289 | default: |
Line 1027... | Line 1305... | ||
1027 | struct _ATOM_TMDS_INFO *tmds_info; |
1305 | struct _ATOM_TMDS_INFO *tmds_info; |
1028 | uint8_t frev, crev; |
1306 | uint8_t frev, crev; |
1029 | uint16_t maxfreq; |
1307 | uint16_t maxfreq; |
1030 | int i; |
1308 | int i; |
Line 1031... | Line 1309... | ||
1031 | 1309 | ||
1032 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, |
1310 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
1033 | &crev, &data_offset); |
- | |
1034 | 1311 | &frev, &crev, &data_offset)) { |
|
1035 | tmds_info = |
1312 | tmds_info = |
1036 | (struct _ATOM_TMDS_INFO *)(mode_info->atom_context->bios + |
1313 | (struct _ATOM_TMDS_INFO *)(mode_info->atom_context->bios + |
Line 1037... | Line -... | ||
1037 | data_offset); |
- | |
1038 | 1314 | data_offset); |
|
1039 | if (tmds_info) { |
1315 | |
1040 | maxfreq = le16_to_cpu(tmds_info->usMaxFrequency); |
1316 | maxfreq = le16_to_cpu(tmds_info->usMaxFrequency); |
1041 | for (i = 0; i < 4; i++) { |
1317 | for (i = 0; i < 4; i++) { |
1042 | tmds->tmds_pll[i].freq = |
1318 | tmds->tmds_pll[i].freq = |
Line 1051... | Line 1327... | ||
1051 | ucPLL_DutyCycle & 0xf) << 12; |
1327 | ucPLL_DutyCycle & 0xf) << 12; |
1052 | tmds->tmds_pll[i].value |= |
1328 | tmds->tmds_pll[i].value |= |
1053 | (tmds_info->asMiscInfo[i]. |
1329 | (tmds_info->asMiscInfo[i]. |
1054 | ucPLL_VoltageSwing & 0xf) << 16; |
1330 | ucPLL_VoltageSwing & 0xf) << 16; |
Line 1055... | Line 1331... | ||
1055 | 1331 | ||
1056 | DRM_DEBUG("TMDS PLL From ATOMBIOS %u %x\n", |
1332 | DRM_DEBUG_KMS("TMDS PLL From ATOMBIOS %u %x\n", |
1057 | tmds->tmds_pll[i].freq, |
1333 | tmds->tmds_pll[i].freq, |
Line 1058... | Line 1334... | ||
1058 | tmds->tmds_pll[i].value); |
1334 | tmds->tmds_pll[i].value); |
1059 | 1335 | ||
Line 1065... | Line 1341... | ||
1065 | return true; |
1341 | return true; |
1066 | } |
1342 | } |
1067 | return false; |
1343 | return false; |
1068 | } |
1344 | } |
Line 1069... | Line 1345... | ||
1069 | 1345 | ||
1070 | static struct radeon_atom_ss *radeon_atombios_get_ss_info(struct |
1346 | bool radeon_atombios_get_ppll_ss_info(struct radeon_device *rdev, |
1071 | radeon_encoder |
- | |
1072 | *encoder, |
1347 | struct radeon_atom_ss *ss, |
1073 | int id) |
1348 | int id) |
1074 | { |
- | |
1075 | struct drm_device *dev = encoder->base.dev; |
- | |
1076 | struct radeon_device *rdev = dev->dev_private; |
1349 | { |
1077 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
1350 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
1078 | int index = GetIndexIntoMasterTable(DATA, PPLL_SS_Info); |
1351 | int index = GetIndexIntoMasterTable(DATA, PPLL_SS_Info); |
1079 | uint16_t data_offset; |
1352 | uint16_t data_offset, size; |
1080 | struct _ATOM_SPREAD_SPECTRUM_INFO *ss_info; |
1353 | struct _ATOM_SPREAD_SPECTRUM_INFO *ss_info; |
1081 | uint8_t frev, crev; |
- | |
1082 | struct radeon_atom_ss *ss = NULL; |
1354 | uint8_t frev, crev; |
1083 | int i; |
- | |
1084 | - | ||
1085 | if (id > ATOM_MAX_SS_ENTRY) |
- | |
1086 | return NULL; |
- | |
1087 | - | ||
1088 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, |
- | |
Line -... | Line 1355... | ||
- | 1355 | int i, num_indices; |
|
- | 1356 | ||
- | 1357 | memset(ss, 0, sizeof(struct radeon_atom_ss)); |
|
1089 | &crev, &data_offset); |
1358 | if (atom_parse_data_header(mode_info->atom_context, index, &size, |
1090 | 1359 | &frev, &crev, &data_offset)) { |
|
Line 1091... | Line -... | ||
1091 | ss_info = |
- | |
1092 | (struct _ATOM_SPREAD_SPECTRUM_INFO *)(mode_info->atom_context->bios + data_offset); |
- | |
1093 | 1360 | ss_info = |
|
1094 | if (ss_info) { |
- | |
1095 | ss = |
- | |
1096 | kzalloc(sizeof(struct radeon_atom_ss), GFP_KERNEL); |
1361 | (struct _ATOM_SPREAD_SPECTRUM_INFO *)(mode_info->atom_context->bios + data_offset); |
Line 1097... | Line 1362... | ||
1097 | 1362 | ||
1098 | if (!ss) |
1363 | num_indices = (size - sizeof(ATOM_COMMON_TABLE_HEADER)) / |
1099 | return NULL; |
1364 | sizeof(ATOM_SPREAD_SPECTRUM_ASSIGNMENT); |
1100 | 1365 | ||
1101 | for (i = 0; i < ATOM_MAX_SS_ENTRY; i++) { |
1366 | for (i = 0; i < num_indices; i++) { |
1102 | if (ss_info->asSS_Info[i].ucSS_Id == id) { |
1367 | if (ss_info->asSS_Info[i].ucSS_Id == id) { |
1103 | ss->percentage = |
1368 | ss->percentage = |
1104 | le16_to_cpu(ss_info->asSS_Info[i].usSpreadSpectrumPercentage); |
1369 | le16_to_cpu(ss_info->asSS_Info[i].usSpreadSpectrumPercentage); |
1105 | ss->type = ss_info->asSS_Info[i].ucSpreadSpectrumType; |
1370 | ss->type = ss_info->asSS_Info[i].ucSpreadSpectrumType; |
1106 | ss->step = ss_info->asSS_Info[i].ucSS_Step; |
1371 | ss->step = ss_info->asSS_Info[i].ucSS_Step; |
1107 | ss->delay = ss_info->asSS_Info[i].ucSS_Delay; |
1372 | ss->delay = ss_info->asSS_Info[i].ucSS_Delay; |
1108 | ss->range = ss_info->asSS_Info[i].ucSS_Range; |
1373 | ss->range = ss_info->asSS_Info[i].ucSS_Range; |
1109 | ss->refdiv = ss_info->asSS_Info[i].ucRecommendedRef_Div; |
1374 | ss->refdiv = ss_info->asSS_Info[i].ucRecommendedRef_Div; |
1110 | break; |
1375 | return true; |
1111 | } |
1376 | } |
Line 1112... | Line 1377... | ||
1112 | } |
1377 | } |
1113 | } |
1378 | } |
- | 1379 | return false; |
|
1114 | return ss; |
1380 | } |
- | 1381 | ||
- | 1382 | static void radeon_atombios_get_igp_ss_overrides(struct radeon_device *rdev, |
|
- | 1383 | struct radeon_atom_ss *ss, |
|
- | 1384 | int id) |
|
- | 1385 | { |
|
- | 1386 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
|
Line -... | Line 1387... | ||
- | 1387 | int index = GetIndexIntoMasterTable(DATA, IntegratedSystemInfo); |
|
1115 | } |
1388 | u16 data_offset, size; |
1116 | 1389 | struct _ATOM_INTEGRATED_SYSTEM_INFO_V6 *igp_info; |
|
1117 | static void radeon_atom_apply_lvds_quirks(struct drm_device *dev, |
1390 | u8 frev, crev; |
1118 | struct radeon_encoder_atom_dig *lvds) |
1391 | u16 percentage = 0, rate = 0; |
- | 1392 | ||
- | 1393 | /* get any igp specific overrides */ |
|
- | 1394 | if (atom_parse_data_header(mode_info->atom_context, index, &size, |
|
1119 | { |
1395 | &frev, &crev, &data_offset)) { |
- | 1396 | igp_info = (struct _ATOM_INTEGRATED_SYSTEM_INFO_V6 *) |
|
- | 1397 | (mode_info->atom_context->bios + data_offset); |
|
- | 1398 | switch (id) { |
|
- | 1399 | case ASIC_INTERNAL_SS_ON_TMDS: |
|
- | 1400 | percentage = le16_to_cpu(igp_info->usDVISSPercentage); |
|
- | 1401 | rate = le16_to_cpu(igp_info->usDVISSpreadRateIn10Hz); |
|
- | 1402 | break; |
|
1120 | 1403 | case ASIC_INTERNAL_SS_ON_HDMI: |
|
- | 1404 | percentage = le16_to_cpu(igp_info->usHDMISSPercentage); |
|
- | 1405 | rate = le16_to_cpu(igp_info->usHDMISSpreadRateIn10Hz); |
|
- | 1406 | break; |
|
1121 | /* Toshiba A300-1BU laptop panel doesn't like new pll divider algo */ |
1407 | case ASIC_INTERNAL_SS_ON_LVDS: |
- | 1408 | percentage = le16_to_cpu(igp_info->usLvdsSSPercentage); |
|
- | 1409 | rate = le16_to_cpu(igp_info->usLvdsSSpreadRateIn10Hz); |
|
- | 1410 | break; |
|
1122 | if ((dev->pdev->device == 0x95c4) && |
1411 | } |
Line -... | Line 1412... | ||
- | 1412 | if (percentage) |
|
- | 1413 | ss->percentage = percentage; |
|
- | 1414 | if (rate) |
|
- | 1415 | ss->rate = rate; |
|
- | 1416 | } |
|
- | 1417 | } |
|
1123 | (dev->pdev->subsystem_vendor == 0x1179) && |
1418 | |
- | 1419 | union asic_ss_info { |
|
- | 1420 | struct _ATOM_ASIC_INTERNAL_SS_INFO info; |
|
- | 1421 | struct _ATOM_ASIC_INTERNAL_SS_INFO_V2 info_2; |
|
- | 1422 | struct _ATOM_ASIC_INTERNAL_SS_INFO_V3 info_3; |
|
- | 1423 | }; |
|
- | 1424 | ||
- | 1425 | bool radeon_atombios_get_asic_ss_info(struct radeon_device *rdev, |
|
- | 1426 | struct radeon_atom_ss *ss, |
|
- | 1427 | int id, u32 clock) |
|
- | 1428 | { |
|
- | 1429 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
|
- | 1430 | int index = GetIndexIntoMasterTable(DATA, ASIC_InternalSS_Info); |
|
1124 | (dev->pdev->subsystem_device == 0xff50)) { |
1431 | uint16_t data_offset, size; |
- | 1432 | union asic_ss_info *ss_info; |
|
- | 1433 | uint8_t frev, crev; |
|
- | 1434 | int i, num_indices; |
|
- | 1435 | ||
- | 1436 | memset(ss, 0, sizeof(struct radeon_atom_ss)); |
|
- | 1437 | if (atom_parse_data_header(mode_info->atom_context, index, &size, |
|
- | 1438 | &frev, &crev, &data_offset)) { |
|
- | 1439 | ||
- | 1440 | ss_info = |
|
1125 | if ((lvds->native_mode.hdisplay == 1280) && |
1441 | (union asic_ss_info *)(mode_info->atom_context->bios + data_offset); |
- | 1442 | ||
- | 1443 | switch (frev) { |
|
- | 1444 | case 1: |
|
- | 1445 | num_indices = (size - sizeof(ATOM_COMMON_TABLE_HEADER)) / |
|
- | 1446 | sizeof(ATOM_ASIC_SS_ASSIGNMENT); |
|
- | 1447 | ||
- | 1448 | for (i = 0; i < num_indices; i++) { |
|
- | 1449 | if ((ss_info->info.asSpreadSpectrum[i].ucClockIndication == id) && |
|
- | 1450 | (clock <= le32_to_cpu(ss_info->info.asSpreadSpectrum[i].ulTargetClockRange))) { |
|
- | 1451 | ss->percentage = |
|
- | 1452 | le16_to_cpu(ss_info->info.asSpreadSpectrum[i].usSpreadSpectrumPercentage); |
|
- | 1453 | ss->type = ss_info->info.asSpreadSpectrum[i].ucSpreadSpectrumMode; |
|
- | 1454 | ss->rate = le16_to_cpu(ss_info->info.asSpreadSpectrum[i].usSpreadRateInKhz); |
|
1126 | (lvds->native_mode.vdisplay == 800)) |
1455 | return true; |
1127 | lvds->pll_algo = PLL_ALGO_LEGACY; |
1456 | } |
- | 1457 | } |
|
- | 1458 | break; |
|
- | 1459 | case 2: |
|
- | 1460 | num_indices = (size - sizeof(ATOM_COMMON_TABLE_HEADER)) / |
|
- | 1461 | sizeof(ATOM_ASIC_SS_ASSIGNMENT_V2); |
|
- | 1462 | for (i = 0; i < num_indices; i++) { |
|
- | 1463 | if ((ss_info->info_2.asSpreadSpectrum[i].ucClockIndication == id) && |
|
- | 1464 | (clock <= le32_to_cpu(ss_info->info_2.asSpreadSpectrum[i].ulTargetClockRange))) { |
|
- | 1465 | ss->percentage = |
|
- | 1466 | le16_to_cpu(ss_info->info_2.asSpreadSpectrum[i].usSpreadSpectrumPercentage); |
|
- | 1467 | ss->type = ss_info->info_2.asSpreadSpectrum[i].ucSpreadSpectrumMode; |
|
- | 1468 | ss->rate = le16_to_cpu(ss_info->info_2.asSpreadSpectrum[i].usSpreadRateIn10Hz); |
|
1128 | } |
1469 | return true; |
- | 1470 | } |
|
- | 1471 | } |
|
- | 1472 | break; |
|
- | 1473 | case 3: |
|
- | 1474 | num_indices = (size - sizeof(ATOM_COMMON_TABLE_HEADER)) / |
|
- | 1475 | sizeof(ATOM_ASIC_SS_ASSIGNMENT_V3); |
|
1129 | 1476 | for (i = 0; i < num_indices; i++) { |
|
- | 1477 | if ((ss_info->info_3.asSpreadSpectrum[i].ucClockIndication == id) && |
|
- | 1478 | (clock <= le32_to_cpu(ss_info->info_3.asSpreadSpectrum[i].ulTargetClockRange))) { |
|
- | 1479 | ss->percentage = |
|
- | 1480 | le16_to_cpu(ss_info->info_3.asSpreadSpectrum[i].usSpreadSpectrumPercentage); |
|
- | 1481 | ss->type = ss_info->info_3.asSpreadSpectrum[i].ucSpreadSpectrumMode; |
|
- | 1482 | ss->rate = le16_to_cpu(ss_info->info_3.asSpreadSpectrum[i].usSpreadRateIn10Hz); |
|
- | 1483 | if (rdev->flags & RADEON_IS_IGP) |
|
- | 1484 | radeon_atombios_get_igp_ss_overrides(rdev, ss, id); |
|
1130 | /* Dell Studio 15 laptop panel doesn't like new pll divider algo */ |
1485 | return true; |
Line 1131... | Line 1486... | ||
1131 | if ((dev->pdev->device == 0x95c4) && |
1486 | } |
- | 1487 | } |
|
- | 1488 | break; |
|
Line 1132... | Line 1489... | ||
1132 | (dev->pdev->subsystem_vendor == 0x1028) && |
1489 | default: |
1133 | (dev->pdev->subsystem_device == 0x029f)) { |
1490 | DRM_ERROR("Unsupported ASIC_InternalSS_Info table: %d %d\n", frev, crev); |
1134 | if ((lvds->native_mode.hdisplay == 1280) && |
1491 | break; |
1135 | (lvds->native_mode.vdisplay == 800)) |
1492 | } |
Line 1153... | Line 1510... | ||
1153 | int index = GetIndexIntoMasterTable(DATA, LVDS_Info); |
1510 | int index = GetIndexIntoMasterTable(DATA, LVDS_Info); |
1154 | uint16_t data_offset, misc; |
1511 | uint16_t data_offset, misc; |
1155 | union lvds_info *lvds_info; |
1512 | union lvds_info *lvds_info; |
1156 | uint8_t frev, crev; |
1513 | uint8_t frev, crev; |
1157 | struct radeon_encoder_atom_dig *lvds = NULL; |
1514 | struct radeon_encoder_atom_dig *lvds = NULL; |
- | 1515 | int encoder_enum = (encoder->encoder_enum & ENUM_ID_MASK) >> ENUM_ID_SHIFT; |
|
Line 1158... | Line 1516... | ||
1158 | 1516 | ||
1159 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, |
1517 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
1160 | &crev, &data_offset); |
- | |
1161 | 1518 | &frev, &crev, &data_offset)) { |
|
1162 | lvds_info = |
1519 | lvds_info = |
1163 | (union lvds_info *)(mode_info->atom_context->bios + data_offset); |
- | |
1164 | - | ||
1165 | if (lvds_info) { |
1520 | (union lvds_info *)(mode_info->atom_context->bios + data_offset); |
1166 | lvds = |
1521 | lvds = |
Line 1167... | Line 1522... | ||
1167 | kzalloc(sizeof(struct radeon_encoder_atom_dig), GFP_KERNEL); |
1522 | kzalloc(sizeof(struct radeon_encoder_atom_dig), GFP_KERNEL); |
1168 | 1523 | ||
Line 1182... | Line 1537... | ||
1182 | lvds->native_mode.hsync_end = lvds->native_mode.hsync_start + |
1537 | lvds->native_mode.hsync_end = lvds->native_mode.hsync_start + |
1183 | le16_to_cpu(lvds_info->info.sLCDTiming.usHSyncWidth); |
1538 | le16_to_cpu(lvds_info->info.sLCDTiming.usHSyncWidth); |
1184 | lvds->native_mode.vtotal = lvds->native_mode.vdisplay + |
1539 | lvds->native_mode.vtotal = lvds->native_mode.vdisplay + |
1185 | le16_to_cpu(lvds_info->info.sLCDTiming.usVBlanking_Time); |
1540 | le16_to_cpu(lvds_info->info.sLCDTiming.usVBlanking_Time); |
1186 | lvds->native_mode.vsync_start = lvds->native_mode.vdisplay + |
1541 | lvds->native_mode.vsync_start = lvds->native_mode.vdisplay + |
1187 | le16_to_cpu(lvds_info->info.sLCDTiming.usVSyncWidth); |
1542 | le16_to_cpu(lvds_info->info.sLCDTiming.usVSyncOffset); |
1188 | lvds->native_mode.vsync_end = lvds->native_mode.vsync_start + |
1543 | lvds->native_mode.vsync_end = lvds->native_mode.vsync_start + |
1189 | le16_to_cpu(lvds_info->info.sLCDTiming.usVSyncWidth); |
1544 | le16_to_cpu(lvds_info->info.sLCDTiming.usVSyncWidth); |
1190 | lvds->panel_pwr_delay = |
1545 | lvds->panel_pwr_delay = |
1191 | le16_to_cpu(lvds_info->info.usOffDelayInMs); |
1546 | le16_to_cpu(lvds_info->info.usOffDelayInMs); |
1192 | lvds->lvds_misc = lvds_info->info.ucLVDS_Misc; |
1547 | lvds->lcd_misc = lvds_info->info.ucLVDS_Misc; |
Line 1193... | Line 1548... | ||
1193 | 1548 | ||
1194 | misc = le16_to_cpu(lvds_info->info.sLCDTiming.susModeMiscInfo.usAccess); |
1549 | misc = le16_to_cpu(lvds_info->info.sLCDTiming.susModeMiscInfo.usAccess); |
1195 | if (misc & ATOM_VSYNC_POLARITY) |
1550 | if (misc & ATOM_VSYNC_POLARITY) |
1196 | lvds->native_mode.flags |= DRM_MODE_FLAG_NVSYNC; |
1551 | lvds->native_mode.flags |= DRM_MODE_FLAG_NVSYNC; |
Line 1201... | Line 1556... | ||
1201 | if (misc & ATOM_INTERLACE) |
1556 | if (misc & ATOM_INTERLACE) |
1202 | lvds->native_mode.flags |= DRM_MODE_FLAG_INTERLACE; |
1557 | lvds->native_mode.flags |= DRM_MODE_FLAG_INTERLACE; |
1203 | if (misc & ATOM_DOUBLE_CLOCK_MODE) |
1558 | if (misc & ATOM_DOUBLE_CLOCK_MODE) |
1204 | lvds->native_mode.flags |= DRM_MODE_FLAG_DBLSCAN; |
1559 | lvds->native_mode.flags |= DRM_MODE_FLAG_DBLSCAN; |
Line -... | Line 1560... | ||
- | 1560 | ||
- | 1561 | lvds->native_mode.width_mm = le16_to_cpu(lvds_info->info.sLCDTiming.usImageHSize); |
|
- | 1562 | lvds->native_mode.height_mm = le16_to_cpu(lvds_info->info.sLCDTiming.usImageVSize); |
|
1205 | 1563 | ||
1206 | /* set crtc values */ |
1564 | /* set crtc values */ |
Line 1207... | Line 1565... | ||
1207 | drm_mode_set_crtcinfo(&lvds->native_mode, CRTC_INTERLACE_HALVE_V); |
1565 | drm_mode_set_crtcinfo(&lvds->native_mode, CRTC_INTERLACE_HALVE_V); |
- | 1566 | ||
- | 1567 | lvds->lcd_ss_id = lvds_info->info.ucSS_Id; |
|
Line 1208... | Line -... | ||
1208 | - | ||
1209 | lvds->ss = radeon_atombios_get_ss_info(encoder, lvds_info->info.ucSS_Id); |
1568 | |
1210 | 1569 | encoder->native_mode = lvds->native_mode; |
|
1211 | if (ASIC_IS_AVIVO(rdev)) { |
1570 | |
1212 | if (radeon_new_pll == 0) |
1571 | if (encoder_enum == 2) |
- | 1572 | lvds->linkb = true; |
|
- | 1573 | else |
|
- | 1574 | lvds->linkb = false; |
|
- | 1575 | ||
- | 1576 | /* parse the lcd record table */ |
|
- | 1577 | if (le16_to_cpu(lvds_info->info.usModePatchTableOffset)) { |
|
1213 | lvds->pll_algo = PLL_ALGO_LEGACY; |
1578 | ATOM_FAKE_EDID_PATCH_RECORD *fake_edid_record; |
- | 1579 | ATOM_PANEL_RESOLUTION_PATCH_RECORD *panel_res_record; |
|
1214 | else |
1580 | bool bad_record = false; |
- | 1581 | u8 *record; |
|
- | 1582 | ||
1215 | lvds->pll_algo = PLL_ALGO_NEW; |
1583 | if ((frev == 1) && (crev < 2)) |
1216 | } else { |
1584 | /* absolute */ |
- | 1585 | record = (u8 *)(mode_info->atom_context->bios + |
|
- | 1586 | le16_to_cpu(lvds_info->info.usModePatchTableOffset)); |
|
- | 1587 | else |
|
- | 1588 | /* relative */ |
|
- | 1589 | record = (u8 *)(mode_info->atom_context->bios + |
|
- | 1590 | data_offset + |
|
- | 1591 | le16_to_cpu(lvds_info->info.usModePatchTableOffset)); |
|
- | 1592 | while (*record != ATOM_RECORD_END_TYPE) { |
|
- | 1593 | switch (*record) { |
|
- | 1594 | case LCD_MODE_PATCH_RECORD_MODE_TYPE: |
|
- | 1595 | record += sizeof(ATOM_PATCH_RECORD_MODE); |
|
- | 1596 | break; |
|
- | 1597 | case LCD_RTS_RECORD_TYPE: |
|
- | 1598 | record += sizeof(ATOM_LCD_RTS_RECORD); |
|
- | 1599 | break; |
|
- | 1600 | case LCD_CAP_RECORD_TYPE: |
|
- | 1601 | record += sizeof(ATOM_LCD_MODE_CONTROL_CAP); |
|
- | 1602 | break; |
|
- | 1603 | case LCD_FAKE_EDID_PATCH_RECORD_TYPE: |
|
- | 1604 | fake_edid_record = (ATOM_FAKE_EDID_PATCH_RECORD *)record; |
|
- | 1605 | if (fake_edid_record->ucFakeEDIDLength) { |
|
1217 | if (radeon_new_pll == 1) |
1606 | struct edid *edid; |
- | 1607 | int edid_size = |
|
- | 1608 | max((int)EDID_LENGTH, (int)fake_edid_record->ucFakeEDIDLength); |
|
- | 1609 | edid = kmalloc(edid_size, GFP_KERNEL); |
|
- | 1610 | if (edid) { |
|
- | 1611 | memcpy((u8 *)edid, (u8 *)&fake_edid_record->ucFakeEDIDString[0], |
|
- | 1612 | fake_edid_record->ucFakeEDIDLength); |
|
- | 1613 | ||
- | 1614 | if (drm_edid_is_valid(edid)) { |
|
- | 1615 | rdev->mode_info.bios_hardcoded_edid = edid; |
|
- | 1616 | rdev->mode_info.bios_hardcoded_edid_size = edid_size; |
|
- | 1617 | } else |
|
- | 1618 | kfree(edid); |
|
- | 1619 | } |
|
- | 1620 | } |
|
- | 1621 | record += sizeof(ATOM_FAKE_EDID_PATCH_RECORD); |
|
- | 1622 | break; |
|
- | 1623 | case LCD_PANEL_RESOLUTION_RECORD_TYPE: |
|
- | 1624 | panel_res_record = (ATOM_PANEL_RESOLUTION_PATCH_RECORD *)record; |
|
- | 1625 | lvds->native_mode.width_mm = panel_res_record->usHSize; |
|
- | 1626 | lvds->native_mode.height_mm = panel_res_record->usVSize; |
|
- | 1627 | record += sizeof(ATOM_PANEL_RESOLUTION_PATCH_RECORD); |
|
- | 1628 | break; |
|
- | 1629 | default: |
|
- | 1630 | DRM_ERROR("Bad LCD record %d\n", *record); |
|
- | 1631 | bad_record = true; |
|
- | 1632 | break; |
|
- | 1633 | } |
|
1218 | lvds->pll_algo = PLL_ALGO_NEW; |
1634 | if (bad_record) |
1219 | else |
- | |
1220 | lvds->pll_algo = PLL_ALGO_LEGACY; |
- | |
1221 | } |
- | |
1222 | - | ||
1223 | /* LVDS quirks */ |
- | |
1224 | radeon_atom_apply_lvds_quirks(dev, lvds); |
1635 | break; |
1225 | 1636 | } |
|
1226 | encoder->native_mode = lvds->native_mode; |
1637 | } |
Line 1227... | Line 1638... | ||
1227 | } |
1638 | } |
Line 1239... | Line 1650... | ||
1239 | struct _COMPASSIONATE_DATA *dac_info; |
1650 | struct _COMPASSIONATE_DATA *dac_info; |
1240 | uint8_t frev, crev; |
1651 | uint8_t frev, crev; |
1241 | uint8_t bg, dac; |
1652 | uint8_t bg, dac; |
1242 | struct radeon_encoder_primary_dac *p_dac = NULL; |
1653 | struct radeon_encoder_primary_dac *p_dac = NULL; |
Line 1243... | Line 1654... | ||
1243 | 1654 | ||
- | 1655 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
|
- | 1656 | &frev, &crev, &data_offset)) { |
|
- | 1657 | dac_info = (struct _COMPASSIONATE_DATA *) |
|
Line 1244... | Line -... | ||
1244 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, &crev, &data_offset); |
- | |
1245 | - | ||
1246 | dac_info = (struct _COMPASSIONATE_DATA *)(mode_info->atom_context->bios + data_offset); |
- | |
1247 | 1658 | (mode_info->atom_context->bios + data_offset); |
|
Line 1248... | Line 1659... | ||
1248 | if (dac_info) { |
1659 | |
1249 | p_dac = kzalloc(sizeof(struct radeon_encoder_primary_dac), GFP_KERNEL); |
1660 | p_dac = kzalloc(sizeof(struct radeon_encoder_primary_dac), GFP_KERNEL); |
Line 1268... | Line 1679... | ||
1268 | ATOM_DTD_FORMAT *dtd_timings; |
1679 | ATOM_DTD_FORMAT *dtd_timings; |
1269 | int data_index = GetIndexIntoMasterTable(DATA, AnalogTV_Info); |
1680 | int data_index = GetIndexIntoMasterTable(DATA, AnalogTV_Info); |
1270 | u8 frev, crev; |
1681 | u8 frev, crev; |
1271 | u16 data_offset, misc; |
1682 | u16 data_offset, misc; |
Line 1272... | Line 1683... | ||
1272 | 1683 | ||
- | 1684 | if (!atom_parse_data_header(mode_info->atom_context, data_index, NULL, |
|
- | 1685 | &frev, &crev, &data_offset)) |
|
Line 1273... | Line 1686... | ||
1273 | atom_parse_data_header(mode_info->atom_context, data_index, NULL, &frev, &crev, &data_offset); |
1686 | return false; |
1274 | 1687 | ||
1275 | switch (crev) { |
1688 | switch (crev) { |
1276 | case 1: |
1689 | case 1: |
1277 | tv_info = (ATOM_ANALOG_TV_INFO *)(mode_info->atom_context->bios + data_offset); |
1690 | tv_info = (ATOM_ANALOG_TV_INFO *)(mode_info->atom_context->bios + data_offset); |
Line 1278... | Line 1691... | ||
1278 | if (index > MAX_SUPPORTED_TV_TIMING) |
1691 | if (index >= MAX_SUPPORTED_TV_TIMING) |
1279 | return false; |
1692 | return false; |
1280 | 1693 | ||
Line 1311... | Line 1724... | ||
1311 | mode->crtc_vtotal -= 1; |
1724 | mode->crtc_vtotal -= 1; |
1312 | } |
1725 | } |
1313 | break; |
1726 | break; |
1314 | case 2: |
1727 | case 2: |
1315 | tv_info_v1_2 = (ATOM_ANALOG_TV_INFO_V1_2 *)(mode_info->atom_context->bios + data_offset); |
1728 | tv_info_v1_2 = (ATOM_ANALOG_TV_INFO_V1_2 *)(mode_info->atom_context->bios + data_offset); |
1316 | if (index > MAX_SUPPORTED_TV_TIMING_V1_2) |
1729 | if (index >= MAX_SUPPORTED_TV_TIMING_V1_2) |
1317 | return false; |
1730 | return false; |
Line 1318... | Line 1731... | ||
1318 | 1731 | ||
1319 | dtd_timings = &tv_info_v1_2->aModeTimings[index]; |
1732 | dtd_timings = &tv_info_v1_2->aModeTimings[index]; |
1320 | mode->crtc_htotal = le16_to_cpu(dtd_timings->usHActive) + |
1733 | mode->crtc_htotal = le16_to_cpu(dtd_timings->usHActive) + |
Line 1360... | Line 1773... | ||
1360 | uint16_t data_offset; |
1773 | uint16_t data_offset; |
1361 | uint8_t frev, crev; |
1774 | uint8_t frev, crev; |
1362 | struct _ATOM_ANALOG_TV_INFO *tv_info; |
1775 | struct _ATOM_ANALOG_TV_INFO *tv_info; |
1363 | enum radeon_tv_std tv_std = TV_STD_NTSC; |
1776 | enum radeon_tv_std tv_std = TV_STD_NTSC; |
Line 1364... | Line 1777... | ||
1364 | 1777 | ||
- | 1778 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
|
Line -... | Line 1779... | ||
- | 1779 | &frev, &crev, &data_offset)) { |
|
1365 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, &crev, &data_offset); |
1780 | |
Line 1366... | Line 1781... | ||
1366 | 1781 | tv_info = (struct _ATOM_ANALOG_TV_INFO *) |
|
1367 | tv_info = (struct _ATOM_ANALOG_TV_INFO *)(mode_info->atom_context->bios + data_offset); |
1782 | (mode_info->atom_context->bios + data_offset); |
1368 | 1783 | ||
1369 | switch (tv_info->ucTV_BootUpDefaultStandard) { |
1784 | switch (tv_info->ucTV_BootUpDefaultStandard) { |
1370 | case ATOM_TV_NTSC: |
1785 | case ATOM_TV_NTSC: |
1371 | tv_std = TV_STD_NTSC; |
1786 | tv_std = TV_STD_NTSC; |
1372 | DRM_INFO("Default TV standard: NTSC\n"); |
1787 | DRM_DEBUG_KMS("Default TV standard: NTSC\n"); |
1373 | break; |
1788 | break; |
1374 | case ATOM_TV_NTSCJ: |
1789 | case ATOM_TV_NTSCJ: |
1375 | tv_std = TV_STD_NTSC_J; |
1790 | tv_std = TV_STD_NTSC_J; |
1376 | DRM_INFO("Default TV standard: NTSC-J\n"); |
1791 | DRM_DEBUG_KMS("Default TV standard: NTSC-J\n"); |
1377 | break; |
1792 | break; |
1378 | case ATOM_TV_PAL: |
1793 | case ATOM_TV_PAL: |
1379 | tv_std = TV_STD_PAL; |
1794 | tv_std = TV_STD_PAL; |
1380 | DRM_INFO("Default TV standard: PAL\n"); |
1795 | DRM_DEBUG_KMS("Default TV standard: PAL\n"); |
1381 | break; |
1796 | break; |
1382 | case ATOM_TV_PALM: |
1797 | case ATOM_TV_PALM: |
1383 | tv_std = TV_STD_PAL_M; |
1798 | tv_std = TV_STD_PAL_M; |
1384 | DRM_INFO("Default TV standard: PAL-M\n"); |
1799 | DRM_DEBUG_KMS("Default TV standard: PAL-M\n"); |
1385 | break; |
1800 | break; |
1386 | case ATOM_TV_PALN: |
1801 | case ATOM_TV_PALN: |
1387 | tv_std = TV_STD_PAL_N; |
1802 | tv_std = TV_STD_PAL_N; |
1388 | DRM_INFO("Default TV standard: PAL-N\n"); |
1803 | DRM_DEBUG_KMS("Default TV standard: PAL-N\n"); |
1389 | break; |
1804 | break; |
1390 | case ATOM_TV_PALCN: |
1805 | case ATOM_TV_PALCN: |
1391 | tv_std = TV_STD_PAL_CN; |
1806 | tv_std = TV_STD_PAL_CN; |
1392 | DRM_INFO("Default TV standard: PAL-CN\n"); |
1807 | DRM_DEBUG_KMS("Default TV standard: PAL-CN\n"); |
1393 | break; |
1808 | break; |
1394 | case ATOM_TV_PAL60: |
1809 | case ATOM_TV_PAL60: |
1395 | tv_std = TV_STD_PAL_60; |
1810 | tv_std = TV_STD_PAL_60; |
1396 | DRM_INFO("Default TV standard: PAL-60\n"); |
1811 | DRM_DEBUG_KMS("Default TV standard: PAL-60\n"); |
1397 | break; |
1812 | break; |
1398 | case ATOM_TV_SECAM: |
1813 | case ATOM_TV_SECAM: |
1399 | tv_std = TV_STD_SECAM; |
1814 | tv_std = TV_STD_SECAM; |
1400 | DRM_INFO("Default TV standard: SECAM\n"); |
1815 | DRM_DEBUG_KMS("Default TV standard: SECAM\n"); |
1401 | break; |
1816 | break; |
1402 | default: |
1817 | default: |
1403 | tv_std = TV_STD_NTSC; |
1818 | tv_std = TV_STD_NTSC; |
- | 1819 | DRM_DEBUG_KMS("Unknown TV standard; defaulting to NTSC\n"); |
|
1404 | DRM_INFO("Unknown TV standard; defaulting to NTSC\n"); |
1820 | break; |
1405 | break; |
1821 | } |
Line 1406... | Line 1822... | ||
1406 | } |
1822 | } |
1407 | return tv_std; |
1823 | return tv_std; |
Line 1418... | Line 1834... | ||
1418 | struct _COMPASSIONATE_DATA *dac_info; |
1834 | struct _COMPASSIONATE_DATA *dac_info; |
1419 | uint8_t frev, crev; |
1835 | uint8_t frev, crev; |
1420 | uint8_t bg, dac; |
1836 | uint8_t bg, dac; |
1421 | struct radeon_encoder_tv_dac *tv_dac = NULL; |
1837 | struct radeon_encoder_tv_dac *tv_dac = NULL; |
Line 1422... | Line 1838... | ||
1422 | 1838 | ||
- | 1839 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
|
Line -... | Line 1840... | ||
- | 1840 | &frev, &crev, &data_offset)) { |
|
1423 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, &crev, &data_offset); |
1841 | |
Line 1424... | Line -... | ||
1424 | - | ||
1425 | dac_info = (struct _COMPASSIONATE_DATA *)(mode_info->atom_context->bios + data_offset); |
1842 | dac_info = (struct _COMPASSIONATE_DATA *) |
Line 1426... | Line 1843... | ||
1426 | 1843 | (mode_info->atom_context->bios + data_offset); |
|
1427 | if (dac_info) { |
1844 | |
Line 1445... | Line 1862... | ||
1445 | tv_dac->tv_std = radeon_atombios_get_tv_info(rdev); |
1862 | tv_dac->tv_std = radeon_atombios_get_tv_info(rdev); |
1446 | } |
1863 | } |
1447 | return tv_dac; |
1864 | return tv_dac; |
1448 | } |
1865 | } |
Line -... | Line 1866... | ||
- | 1866 | ||
- | 1867 | static const char *thermal_controller_names[] = { |
|
- | 1868 | "NONE", |
|
- | 1869 | "lm63", |
|
- | 1870 | "adm1032", |
|
- | 1871 | "adm1030", |
|
- | 1872 | "max6649", |
|
- | 1873 | "lm64", |
|
- | 1874 | "f75375", |
|
- | 1875 | "asc7xxx", |
|
- | 1876 | }; |
|
- | 1877 | ||
- | 1878 | static const char *pp_lib_thermal_controller_names[] = { |
|
- | 1879 | "NONE", |
|
- | 1880 | "lm63", |
|
- | 1881 | "adm1032", |
|
- | 1882 | "adm1030", |
|
- | 1883 | "max6649", |
|
- | 1884 | "lm64", |
|
- | 1885 | "f75375", |
|
- | 1886 | "RV6xx", |
|
- | 1887 | "RV770", |
|
- | 1888 | "adt7473", |
|
- | 1889 | "NONE", |
|
- | 1890 | "External GPIO", |
|
- | 1891 | "Evergreen", |
|
- | 1892 | "emc2103", |
|
- | 1893 | "Sumo", |
|
- | 1894 | "Northern Islands", |
|
- | 1895 | }; |
|
1449 | 1896 | ||
1450 | union power_info { |
1897 | union power_info { |
1451 | struct _ATOM_POWERPLAY_INFO info; |
1898 | struct _ATOM_POWERPLAY_INFO info; |
1452 | struct _ATOM_POWERPLAY_INFO_V2 info_2; |
1899 | struct _ATOM_POWERPLAY_INFO_V2 info_2; |
1453 | struct _ATOM_POWERPLAY_INFO_V3 info_3; |
1900 | struct _ATOM_POWERPLAY_INFO_V3 info_3; |
- | 1901 | struct _ATOM_PPLIB_POWERPLAYTABLE pplib; |
|
- | 1902 | struct _ATOM_PPLIB_POWERPLAYTABLE2 pplib2; |
|
1454 | struct _ATOM_PPLIB_POWERPLAYTABLE info_4; |
1903 | struct _ATOM_PPLIB_POWERPLAYTABLE3 pplib3; |
Line -... | Line 1904... | ||
- | 1904 | }; |
|
- | 1905 | ||
- | 1906 | union pplib_clock_info { |
|
- | 1907 | struct _ATOM_PPLIB_R600_CLOCK_INFO r600; |
|
- | 1908 | struct _ATOM_PPLIB_RS780_CLOCK_INFO rs780; |
|
- | 1909 | struct _ATOM_PPLIB_EVERGREEN_CLOCK_INFO evergreen; |
|
- | 1910 | struct _ATOM_PPLIB_SUMO_CLOCK_INFO sumo; |
|
- | 1911 | }; |
|
- | 1912 | ||
- | 1913 | union pplib_power_state { |
|
- | 1914 | struct _ATOM_PPLIB_STATE v1; |
|
- | 1915 | struct _ATOM_PPLIB_STATE_V2 v2; |
|
- | 1916 | }; |
|
- | 1917 | ||
- | 1918 | static void radeon_atombios_parse_misc_flags_1_3(struct radeon_device *rdev, |
|
- | 1919 | int state_index, |
|
- | 1920 | u32 misc, u32 misc2) |
|
- | 1921 | { |
|
- | 1922 | rdev->pm.power_state[state_index].misc = misc; |
|
- | 1923 | rdev->pm.power_state[state_index].misc2 = misc2; |
|
- | 1924 | /* order matters! */ |
|
- | 1925 | if (misc & ATOM_PM_MISCINFO_POWER_SAVING_MODE) |
|
- | 1926 | rdev->pm.power_state[state_index].type = |
|
- | 1927 | POWER_STATE_TYPE_POWERSAVE; |
|
- | 1928 | if (misc & ATOM_PM_MISCINFO_DEFAULT_DC_STATE_ENTRY_TRUE) |
|
- | 1929 | rdev->pm.power_state[state_index].type = |
|
- | 1930 | POWER_STATE_TYPE_BATTERY; |
|
- | 1931 | if (misc & ATOM_PM_MISCINFO_DEFAULT_LOW_DC_STATE_ENTRY_TRUE) |
|
- | 1932 | rdev->pm.power_state[state_index].type = |
|
- | 1933 | POWER_STATE_TYPE_BATTERY; |
|
- | 1934 | if (misc & ATOM_PM_MISCINFO_LOAD_BALANCE_EN) |
|
- | 1935 | rdev->pm.power_state[state_index].type = |
|
- | 1936 | POWER_STATE_TYPE_BALANCED; |
|
- | 1937 | if (misc & ATOM_PM_MISCINFO_3D_ACCELERATION_EN) { |
|
- | 1938 | rdev->pm.power_state[state_index].type = |
|
- | 1939 | POWER_STATE_TYPE_PERFORMANCE; |
|
- | 1940 | rdev->pm.power_state[state_index].flags &= |
|
- | 1941 | ~RADEON_PM_STATE_SINGLE_DISPLAY_ONLY; |
|
- | 1942 | } |
|
- | 1943 | if (misc2 & ATOM_PM_MISCINFO2_SYSTEM_AC_LITE_MODE) |
|
- | 1944 | rdev->pm.power_state[state_index].type = |
|
- | 1945 | POWER_STATE_TYPE_BALANCED; |
|
- | 1946 | if (misc & ATOM_PM_MISCINFO_DRIVER_DEFAULT_MODE) { |
|
- | 1947 | rdev->pm.power_state[state_index].type = |
|
- | 1948 | POWER_STATE_TYPE_DEFAULT; |
|
- | 1949 | rdev->pm.default_power_state_index = state_index; |
|
- | 1950 | rdev->pm.power_state[state_index].default_clock_mode = |
|
- | 1951 | &rdev->pm.power_state[state_index].clock_info[0]; |
|
- | 1952 | } else if (state_index == 0) { |
|
- | 1953 | rdev->pm.power_state[state_index].clock_info[0].flags |= |
|
- | 1954 | RADEON_PM_MODE_NO_DISPLAY; |
|
- | 1955 | } |
|
1455 | }; |
1956 | } |
1456 | 1957 | ||
1457 | void radeon_atombios_get_power_modes(struct radeon_device *rdev) |
1958 | static int radeon_atombios_parse_power_table_1_3(struct radeon_device *rdev) |
- | 1959 | { |
|
- | 1960 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
|
- | 1961 | u32 misc, misc2 = 0; |
|
- | 1962 | int num_modes = 0, i; |
|
- | 1963 | int state_index = 0; |
|
1458 | { |
1964 | struct radeon_i2c_bus_rec i2c_bus; |
1459 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
1965 | union power_info *power_info; |
1460 | int index = GetIndexIntoMasterTable(DATA, PowerPlayInfo); |
1966 | int index = GetIndexIntoMasterTable(DATA, PowerPlayInfo); |
1461 | u16 data_offset; |
- | |
1462 | u8 frev, crev; |
- | |
1463 | u32 misc, misc2 = 0, sclk, mclk; |
- | |
1464 | union power_info *power_info; |
- | |
1465 | struct _ATOM_PPLIB_NONCLOCK_INFO *non_clock_info; |
- | |
1466 | struct _ATOM_PPLIB_STATE *power_state; |
- | |
1467 | int num_modes = 0, i, j; |
- | |
1468 | int state_index = 0, mode_index = 0; |
- | |
Line -... | Line 1967... | ||
- | 1967 | u16 data_offset; |
|
- | 1968 | u8 frev, crev; |
|
- | 1969 | ||
1469 | 1970 | if (!atom_parse_data_header(mode_info->atom_context, index, NULL, |
|
Line 1470... | Line 1971... | ||
1470 | atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, &crev, &data_offset); |
1971 | &frev, &crev, &data_offset)) |
1471 | - | ||
1472 | power_info = (union power_info *)(mode_info->atom_context->bios + data_offset); |
1972 | return state_index; |
- | 1973 | power_info = (union power_info *)(mode_info->atom_context->bios + data_offset); |
|
- | 1974 | ||
- | 1975 | /* add the i2c bus for thermal/fan chip */ |
|
- | 1976 | if (power_info->info.ucOverdriveThermalController > 0) { |
|
- | 1977 | DRM_INFO("Possible %s thermal controller at 0x%02x\n", |
|
1473 | 1978 | thermal_controller_names[power_info->info.ucOverdriveThermalController], |
|
- | 1979 | power_info->info.ucOverdriveControllerAddress >> 1); |
|
- | 1980 | i2c_bus = radeon_lookup_i2c_gpio(rdev, power_info->info.ucOverdriveI2cLine); |
|
- | 1981 | rdev->pm.i2c_bus = radeon_i2c_lookup(rdev, &i2c_bus); |
|
- | 1982 | if (rdev->pm.i2c_bus) { |
|
- | 1983 | struct i2c_board_info info = { }; |
|
- | 1984 | const char *name = thermal_controller_names[power_info->info. |
|
- | 1985 | ucOverdriveThermalController]; |
|
- | 1986 | info.addr = power_info->info.ucOverdriveControllerAddress >> 1; |
|
1474 | rdev->pm.default_power_state = NULL; |
1987 | strlcpy(info.type, name, sizeof(info.type)); |
1475 | 1988 | i2c_new_device(&rdev->pm.i2c_bus->adapter, &info); |
|
1476 | if (power_info) { |
1989 | } |
- | 1990 | } |
|
- | 1991 | num_modes = power_info->info.ucNumOfPowerModeEntries; |
|
- | 1992 | if (num_modes > ATOM_MAX_NUMBEROF_POWER_BLOCK) |
|
- | 1993 | num_modes = ATOM_MAX_NUMBEROF_POWER_BLOCK; |
|
1477 | if (frev < 4) { |
1994 | rdev->pm.power_state = kzalloc(sizeof(struct radeon_power_state) * num_modes, GFP_KERNEL); |
1478 | num_modes = power_info->info.ucNumOfPowerModeEntries; |
1995 | if (!rdev->pm.power_state) |
1479 | if (num_modes > ATOM_MAX_NUMBEROF_POWER_BLOCK) |
1996 | return state_index; |
1480 | num_modes = ATOM_MAX_NUMBEROF_POWER_BLOCK; |
1997 | /* last mode is usually default, array is low to high */ |
1481 | for (i = 0; i < num_modes; i++) { |
1998 | for (i = 0; i < num_modes; i++) { |
Line 1489... | Line 2006... | ||
1489 | le16_to_cpu(power_info->info.asPowerPlayInfo[i].usEngineClock); |
2006 | le16_to_cpu(power_info->info.asPowerPlayInfo[i].usEngineClock); |
1490 | /* skip invalid modes */ |
2007 | /* skip invalid modes */ |
1491 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk == 0) || |
2008 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk == 0) || |
1492 | (rdev->pm.power_state[state_index].clock_info[0].sclk == 0)) |
2009 | (rdev->pm.power_state[state_index].clock_info[0].sclk == 0)) |
1493 | continue; |
2010 | continue; |
1494 | /* skip overclock modes for now */ |
- | |
1495 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk > |
- | |
1496 | rdev->clock.default_mclk + RADEON_MODE_OVERCLOCK_MARGIN) || |
- | |
1497 | (rdev->pm.power_state[state_index].clock_info[0].sclk > |
- | |
1498 | rdev->clock.default_sclk + RADEON_MODE_OVERCLOCK_MARGIN)) |
- | |
1499 | continue; |
- | |
1500 | rdev->pm.power_state[state_index].non_clock_info.pcie_lanes = |
2011 | rdev->pm.power_state[state_index].pcie_lanes = |
1501 | power_info->info.asPowerPlayInfo[i].ucNumPciELanes; |
2012 | power_info->info.asPowerPlayInfo[i].ucNumPciELanes; |
1502 | misc = le32_to_cpu(power_info->info.asPowerPlayInfo[i].ulMiscInfo); |
2013 | misc = le32_to_cpu(power_info->info.asPowerPlayInfo[i].ulMiscInfo); |
1503 | if (misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_SUPPORT) { |
2014 | if ((misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_SUPPORT) || |
- | 2015 | (misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_ACTIVE_HIGH)) { |
|
1504 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
2016 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
1505 | VOLTAGE_GPIO; |
2017 | VOLTAGE_GPIO; |
1506 | rdev->pm.power_state[state_index].clock_info[0].voltage.gpio = |
2018 | rdev->pm.power_state[state_index].clock_info[0].voltage.gpio = |
1507 | radeon_lookup_gpio(rdev, |
2019 | radeon_lookup_gpio(rdev, |
1508 | power_info->info.asPowerPlayInfo[i].ucVoltageDropIndex); |
2020 | power_info->info.asPowerPlayInfo[i].ucVoltageDropIndex); |
Line 1516... | Line 2028... | ||
1516 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
2028 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
1517 | VOLTAGE_VDDC; |
2029 | VOLTAGE_VDDC; |
1518 | rdev->pm.power_state[state_index].clock_info[0].voltage.vddc_id = |
2030 | rdev->pm.power_state[state_index].clock_info[0].voltage.vddc_id = |
1519 | power_info->info.asPowerPlayInfo[i].ucVoltageDropIndex; |
2031 | power_info->info.asPowerPlayInfo[i].ucVoltageDropIndex; |
1520 | } |
2032 | } |
1521 | /* order matters! */ |
- | |
1522 | if (misc & ATOM_PM_MISCINFO_POWER_SAVING_MODE) |
- | |
1523 | rdev->pm.power_state[state_index].type = |
- | |
1524 | POWER_STATE_TYPE_POWERSAVE; |
- | |
1525 | if (misc & ATOM_PM_MISCINFO_DEFAULT_DC_STATE_ENTRY_TRUE) |
- | |
1526 | rdev->pm.power_state[state_index].type = |
- | |
1527 | POWER_STATE_TYPE_BATTERY; |
- | |
1528 | if (misc & ATOM_PM_MISCINFO_DEFAULT_LOW_DC_STATE_ENTRY_TRUE) |
- | |
1529 | rdev->pm.power_state[state_index].type = |
- | |
1530 | POWER_STATE_TYPE_BATTERY; |
- | |
1531 | if (misc & ATOM_PM_MISCINFO_LOAD_BALANCE_EN) |
- | |
1532 | rdev->pm.power_state[state_index].type = |
- | |
1533 | POWER_STATE_TYPE_BALANCED; |
- | |
1534 | if (misc & ATOM_PM_MISCINFO_3D_ACCELERATION_EN) |
- | |
1535 | rdev->pm.power_state[state_index].type = |
- | |
1536 | POWER_STATE_TYPE_PERFORMANCE; |
- | |
1537 | if (misc & ATOM_PM_MISCINFO_DRIVER_DEFAULT_MODE) { |
- | |
1538 | rdev->pm.power_state[state_index].type = |
- | |
1539 | POWER_STATE_TYPE_DEFAULT; |
- | |
1540 | rdev->pm.default_power_state = &rdev->pm.power_state[state_index]; |
- | |
1541 | rdev->pm.power_state[state_index].default_clock_mode = |
2033 | rdev->pm.power_state[state_index].flags = RADEON_PM_STATE_SINGLE_DISPLAY_ONLY; |
1542 | &rdev->pm.power_state[state_index].clock_info[0]; |
2034 | radeon_atombios_parse_misc_flags_1_3(rdev, state_index, misc, 0); |
1543 | } |
- | |
1544 | state_index++; |
2035 | state_index++; |
1545 | break; |
2036 | break; |
1546 | case 2: |
2037 | case 2: |
1547 | rdev->pm.power_state[state_index].num_clock_modes = 1; |
2038 | rdev->pm.power_state[state_index].num_clock_modes = 1; |
1548 | rdev->pm.power_state[state_index].clock_info[0].mclk = |
2039 | rdev->pm.power_state[state_index].clock_info[0].mclk = |
Line 1551... | Line 2042... | ||
1551 | le32_to_cpu(power_info->info_2.asPowerPlayInfo[i].ulEngineClock); |
2042 | le32_to_cpu(power_info->info_2.asPowerPlayInfo[i].ulEngineClock); |
1552 | /* skip invalid modes */ |
2043 | /* skip invalid modes */ |
1553 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk == 0) || |
2044 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk == 0) || |
1554 | (rdev->pm.power_state[state_index].clock_info[0].sclk == 0)) |
2045 | (rdev->pm.power_state[state_index].clock_info[0].sclk == 0)) |
1555 | continue; |
2046 | continue; |
1556 | /* skip overclock modes for now */ |
- | |
1557 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk > |
- | |
1558 | rdev->clock.default_mclk + RADEON_MODE_OVERCLOCK_MARGIN) || |
- | |
1559 | (rdev->pm.power_state[state_index].clock_info[0].sclk > |
- | |
1560 | rdev->clock.default_sclk + RADEON_MODE_OVERCLOCK_MARGIN)) |
- | |
1561 | continue; |
- | |
1562 | rdev->pm.power_state[state_index].non_clock_info.pcie_lanes = |
2047 | rdev->pm.power_state[state_index].pcie_lanes = |
1563 | power_info->info_2.asPowerPlayInfo[i].ucNumPciELanes; |
2048 | power_info->info_2.asPowerPlayInfo[i].ucNumPciELanes; |
1564 | misc = le32_to_cpu(power_info->info_2.asPowerPlayInfo[i].ulMiscInfo); |
2049 | misc = le32_to_cpu(power_info->info_2.asPowerPlayInfo[i].ulMiscInfo); |
1565 | misc2 = le32_to_cpu(power_info->info_2.asPowerPlayInfo[i].ulMiscInfo2); |
2050 | misc2 = le32_to_cpu(power_info->info_2.asPowerPlayInfo[i].ulMiscInfo2); |
1566 | if (misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_SUPPORT) { |
2051 | if ((misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_SUPPORT) || |
- | 2052 | (misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_ACTIVE_HIGH)) { |
|
1567 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
2053 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
1568 | VOLTAGE_GPIO; |
2054 | VOLTAGE_GPIO; |
1569 | rdev->pm.power_state[state_index].clock_info[0].voltage.gpio = |
2055 | rdev->pm.power_state[state_index].clock_info[0].voltage.gpio = |
1570 | radeon_lookup_gpio(rdev, |
2056 | radeon_lookup_gpio(rdev, |
1571 | power_info->info_2.asPowerPlayInfo[i].ucVoltageDropIndex); |
2057 | power_info->info_2.asPowerPlayInfo[i].ucVoltageDropIndex); |
Line 1579... | Line 2065... | ||
1579 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
2065 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
1580 | VOLTAGE_VDDC; |
2066 | VOLTAGE_VDDC; |
1581 | rdev->pm.power_state[state_index].clock_info[0].voltage.vddc_id = |
2067 | rdev->pm.power_state[state_index].clock_info[0].voltage.vddc_id = |
1582 | power_info->info_2.asPowerPlayInfo[i].ucVoltageDropIndex; |
2068 | power_info->info_2.asPowerPlayInfo[i].ucVoltageDropIndex; |
1583 | } |
2069 | } |
1584 | /* order matters! */ |
- | |
1585 | if (misc & ATOM_PM_MISCINFO_POWER_SAVING_MODE) |
- | |
1586 | rdev->pm.power_state[state_index].type = |
- | |
1587 | POWER_STATE_TYPE_POWERSAVE; |
- | |
1588 | if (misc & ATOM_PM_MISCINFO_DEFAULT_DC_STATE_ENTRY_TRUE) |
- | |
1589 | rdev->pm.power_state[state_index].type = |
- | |
1590 | POWER_STATE_TYPE_BATTERY; |
- | |
1591 | if (misc & ATOM_PM_MISCINFO_DEFAULT_LOW_DC_STATE_ENTRY_TRUE) |
- | |
1592 | rdev->pm.power_state[state_index].type = |
- | |
1593 | POWER_STATE_TYPE_BATTERY; |
- | |
1594 | if (misc & ATOM_PM_MISCINFO_LOAD_BALANCE_EN) |
- | |
1595 | rdev->pm.power_state[state_index].type = |
- | |
1596 | POWER_STATE_TYPE_BALANCED; |
- | |
1597 | if (misc & ATOM_PM_MISCINFO_3D_ACCELERATION_EN) |
- | |
1598 | rdev->pm.power_state[state_index].type = |
- | |
1599 | POWER_STATE_TYPE_PERFORMANCE; |
- | |
1600 | if (misc2 & ATOM_PM_MISCINFO2_SYSTEM_AC_LITE_MODE) |
- | |
1601 | rdev->pm.power_state[state_index].type = |
- | |
1602 | POWER_STATE_TYPE_BALANCED; |
- | |
1603 | if (misc & ATOM_PM_MISCINFO_DRIVER_DEFAULT_MODE) { |
- | |
1604 | rdev->pm.power_state[state_index].type = |
- | |
1605 | POWER_STATE_TYPE_DEFAULT; |
- | |
1606 | rdev->pm.default_power_state = &rdev->pm.power_state[state_index]; |
- | |
1607 | rdev->pm.power_state[state_index].default_clock_mode = |
2070 | rdev->pm.power_state[state_index].flags = RADEON_PM_STATE_SINGLE_DISPLAY_ONLY; |
1608 | &rdev->pm.power_state[state_index].clock_info[0]; |
2071 | radeon_atombios_parse_misc_flags_1_3(rdev, state_index, misc, misc2); |
1609 | } |
- | |
1610 | state_index++; |
2072 | state_index++; |
1611 | break; |
2073 | break; |
1612 | case 3: |
2074 | case 3: |
1613 | rdev->pm.power_state[state_index].num_clock_modes = 1; |
2075 | rdev->pm.power_state[state_index].num_clock_modes = 1; |
1614 | rdev->pm.power_state[state_index].clock_info[0].mclk = |
2076 | rdev->pm.power_state[state_index].clock_info[0].mclk = |
Line 1617... | Line 2079... | ||
1617 | le32_to_cpu(power_info->info_3.asPowerPlayInfo[i].ulEngineClock); |
2079 | le32_to_cpu(power_info->info_3.asPowerPlayInfo[i].ulEngineClock); |
1618 | /* skip invalid modes */ |
2080 | /* skip invalid modes */ |
1619 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk == 0) || |
2081 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk == 0) || |
1620 | (rdev->pm.power_state[state_index].clock_info[0].sclk == 0)) |
2082 | (rdev->pm.power_state[state_index].clock_info[0].sclk == 0)) |
1621 | continue; |
2083 | continue; |
1622 | /* skip overclock modes for now */ |
- | |
1623 | if ((rdev->pm.power_state[state_index].clock_info[0].mclk > |
- | |
1624 | rdev->clock.default_mclk + RADEON_MODE_OVERCLOCK_MARGIN) || |
- | |
1625 | (rdev->pm.power_state[state_index].clock_info[0].sclk > |
- | |
1626 | rdev->clock.default_sclk + RADEON_MODE_OVERCLOCK_MARGIN)) |
- | |
1627 | continue; |
- | |
1628 | rdev->pm.power_state[state_index].non_clock_info.pcie_lanes = |
2084 | rdev->pm.power_state[state_index].pcie_lanes = |
1629 | power_info->info_3.asPowerPlayInfo[i].ucNumPciELanes; |
2085 | power_info->info_3.asPowerPlayInfo[i].ucNumPciELanes; |
1630 | misc = le32_to_cpu(power_info->info_3.asPowerPlayInfo[i].ulMiscInfo); |
2086 | misc = le32_to_cpu(power_info->info_3.asPowerPlayInfo[i].ulMiscInfo); |
1631 | misc2 = le32_to_cpu(power_info->info_3.asPowerPlayInfo[i].ulMiscInfo2); |
2087 | misc2 = le32_to_cpu(power_info->info_3.asPowerPlayInfo[i].ulMiscInfo2); |
1632 | if (misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_SUPPORT) { |
2088 | if ((misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_SUPPORT) || |
- | 2089 | (misc & ATOM_PM_MISCINFO_VOLTAGE_DROP_ACTIVE_HIGH)) { |
|
1633 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
2090 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = |
1634 | VOLTAGE_GPIO; |
2091 | VOLTAGE_GPIO; |
1635 | rdev->pm.power_state[state_index].clock_info[0].voltage.gpio = |
2092 | rdev->pm.power_state[state_index].clock_info[0].voltage.gpio = |
1636 | radeon_lookup_gpio(rdev, |
2093 | radeon_lookup_gpio(rdev, |
1637 | power_info->info_3.asPowerPlayInfo[i].ucVoltageDropIndex); |
2094 | power_info->info_3.asPowerPlayInfo[i].ucVoltageDropIndex); |
Line 1651... | Line 2108... | ||
1651 | true; |
2108 | true; |
1652 | rdev->pm.power_state[state_index].clock_info[0].voltage.vddci_id = |
2109 | rdev->pm.power_state[state_index].clock_info[0].voltage.vddci_id = |
1653 | power_info->info_3.asPowerPlayInfo[i].ucVDDCI_VoltageDropIndex; |
2110 | power_info->info_3.asPowerPlayInfo[i].ucVDDCI_VoltageDropIndex; |
1654 | } |
2111 | } |
1655 | } |
2112 | } |
- | 2113 | rdev->pm.power_state[state_index].flags = RADEON_PM_STATE_SINGLE_DISPLAY_ONLY; |
|
- | 2114 | radeon_atombios_parse_misc_flags_1_3(rdev, state_index, misc, misc2); |
|
1656 | /* order matters! */ |
2115 | state_index++; |
- | 2116 | break; |
|
- | 2117 | } |
|
- | 2118 | } |
|
- | 2119 | /* last mode is usually default */ |
|
1657 | if (misc & ATOM_PM_MISCINFO_POWER_SAVING_MODE) |
2120 | if (rdev->pm.default_power_state_index == -1) { |
1658 | rdev->pm.power_state[state_index].type = |
2121 | rdev->pm.power_state[state_index - 1].type = |
1659 | POWER_STATE_TYPE_POWERSAVE; |
2122 | POWER_STATE_TYPE_DEFAULT; |
- | 2123 | rdev->pm.default_power_state_index = state_index - 1; |
|
- | 2124 | rdev->pm.power_state[state_index - 1].default_clock_mode = |
|
1660 | if (misc & ATOM_PM_MISCINFO_DEFAULT_DC_STATE_ENTRY_TRUE) |
2125 | &rdev->pm.power_state[state_index - 1].clock_info[0]; |
1661 | rdev->pm.power_state[state_index].type = |
2126 | rdev->pm.power_state[state_index].flags &= |
1662 | POWER_STATE_TYPE_BATTERY; |
2127 | ~RADEON_PM_STATE_SINGLE_DISPLAY_ONLY; |
- | 2128 | rdev->pm.power_state[state_index].misc = 0; |
|
- | 2129 | rdev->pm.power_state[state_index].misc2 = 0; |
|
- | 2130 | } |
|
- | 2131 | return state_index; |
|
- | 2132 | } |
|
- | 2133 | ||
- | 2134 | static void radeon_atombios_add_pplib_thermal_controller(struct radeon_device *rdev, |
|
- | 2135 | ATOM_PPLIB_THERMALCONTROLLER *controller) |
|
- | 2136 | { |
|
- | 2137 | struct radeon_i2c_bus_rec i2c_bus; |
|
- | 2138 | ||
- | 2139 | /* add the i2c bus for thermal/fan chip */ |
|
- | 2140 | if (controller->ucType > 0) { |
|
- | 2141 | if (controller->ucType == ATOM_PP_THERMALCONTROLLER_RV6xx) { |
|
- | 2142 | DRM_INFO("Internal thermal controller %s fan control\n", |
|
- | 2143 | (controller->ucFanParameters & |
|
- | 2144 | ATOM_PP_FANPARAMETERS_NOFAN) ? "without" : "with"); |
|
- | 2145 | rdev->pm.int_thermal_type = THERMAL_TYPE_RV6XX; |
|
- | 2146 | } else if (controller->ucType == ATOM_PP_THERMALCONTROLLER_RV770) { |
|
- | 2147 | DRM_INFO("Internal thermal controller %s fan control\n", |
|
- | 2148 | (controller->ucFanParameters & |
|
- | 2149 | ATOM_PP_FANPARAMETERS_NOFAN) ? "without" : "with"); |
|
- | 2150 | rdev->pm.int_thermal_type = THERMAL_TYPE_RV770; |
|
- | 2151 | } else if (controller->ucType == ATOM_PP_THERMALCONTROLLER_EVERGREEN) { |
|
- | 2152 | DRM_INFO("Internal thermal controller %s fan control\n", |
|
- | 2153 | (controller->ucFanParameters & |
|
- | 2154 | ATOM_PP_FANPARAMETERS_NOFAN) ? "without" : "with"); |
|
- | 2155 | rdev->pm.int_thermal_type = THERMAL_TYPE_EVERGREEN; |
|
- | 2156 | } else if (controller->ucType == ATOM_PP_THERMALCONTROLLER_SUMO) { |
|
- | 2157 | DRM_INFO("Internal thermal controller %s fan control\n", |
|
- | 2158 | (controller->ucFanParameters & |
|
- | 2159 | ATOM_PP_FANPARAMETERS_NOFAN) ? "without" : "with"); |
|
- | 2160 | rdev->pm.int_thermal_type = THERMAL_TYPE_SUMO; |
|
- | 2161 | } else if (controller->ucType == ATOM_PP_THERMALCONTROLLER_NISLANDS) { |
|
- | 2162 | DRM_INFO("Internal thermal controller %s fan control\n", |
|
- | 2163 | (controller->ucFanParameters & |
|
- | 2164 | ATOM_PP_FANPARAMETERS_NOFAN) ? "without" : "with"); |
|
- | 2165 | rdev->pm.int_thermal_type = THERMAL_TYPE_NI; |
|
- | 2166 | } else if ((controller->ucType == |
|
- | 2167 | ATOM_PP_THERMALCONTROLLER_EXTERNAL_GPIO) || |
|
- | 2168 | (controller->ucType == |
|
- | 2169 | ATOM_PP_THERMALCONTROLLER_ADT7473_WITH_INTERNAL) || |
|
- | 2170 | (controller->ucType == |
|
- | 2171 | ATOM_PP_THERMALCONTROLLER_EMC2103_WITH_INTERNAL)) { |
|
- | 2172 | DRM_INFO("Special thermal controller config\n"); |
|
- | 2173 | } else { |
|
- | 2174 | DRM_INFO("Possible %s thermal controller at 0x%02x %s fan control\n", |
|
- | 2175 | pp_lib_thermal_controller_names[controller->ucType], |
|
- | 2176 | controller->ucI2cAddress >> 1, |
|
- | 2177 | (controller->ucFanParameters & |
|
- | 2178 | ATOM_PP_FANPARAMETERS_NOFAN) ? "without" : "with"); |
|
- | 2179 | i2c_bus = radeon_lookup_i2c_gpio(rdev, controller->ucI2cLine); |
|
- | 2180 | rdev->pm.i2c_bus = radeon_i2c_lookup(rdev, &i2c_bus); |
|
- | 2181 | if (rdev->pm.i2c_bus) { |
|
- | 2182 | struct i2c_board_info info = { }; |
|
- | 2183 | const char *name = pp_lib_thermal_controller_names[controller->ucType]; |
|
- | 2184 | info.addr = controller->ucI2cAddress >> 1; |
|
- | 2185 | strlcpy(info.type, name, sizeof(info.type)); |
|
- | 2186 | i2c_new_device(&rdev->pm.i2c_bus->adapter, &info); |
|
- | 2187 | } |
|
- | 2188 | } |
|
- | 2189 | } |
|
- | 2190 | } |
|
- | 2191 | ||
- | 2192 | static void radeon_atombios_get_default_voltages(struct radeon_device *rdev, |
|
- | 2193 | u16 *vddc, u16 *vddci) |
|
- | 2194 | { |
|
- | 2195 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
|
- | 2196 | int index = GetIndexIntoMasterTable(DATA, FirmwareInfo); |
|
- | 2197 | u8 frev, crev; |
|
- | 2198 | u16 data_offset; |
|
- | 2199 | union firmware_info *firmware_info; |
|
- | 2200 | ||
- | 2201 | *vddc = 0; |
|
- | 2202 | *vddci = 0; |
|
- | 2203 | ||
- | 2204 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
|
- | 2205 | &frev, &crev, &data_offset)) { |
|
- | 2206 | firmware_info = |
|
- | 2207 | (union firmware_info *)(mode_info->atom_context->bios + |
|
- | 2208 | data_offset); |
|
- | 2209 | *vddc = le16_to_cpu(firmware_info->info_14.usBootUpVDDCVoltage); |
|
- | 2210 | if ((frev == 2) && (crev >= 2)) |
|
- | 2211 | *vddci = le16_to_cpu(firmware_info->info_22.usBootUpVDDCIVoltage); |
|
- | 2212 | } |
|
- | 2213 | } |
|
- | 2214 | ||
- | 2215 | static void radeon_atombios_parse_pplib_non_clock_info(struct radeon_device *rdev, |
|
- | 2216 | int state_index, int mode_index, |
|
- | 2217 | struct _ATOM_PPLIB_NONCLOCK_INFO *non_clock_info) |
|
- | 2218 | { |
|
- | 2219 | int j; |
|
- | 2220 | u32 misc = le32_to_cpu(non_clock_info->ulCapsAndSettings); |
|
- | 2221 | u32 misc2 = le16_to_cpu(non_clock_info->usClassification); |
|
- | 2222 | u16 vddc, vddci; |
|
- | 2223 | ||
- | 2224 | radeon_atombios_get_default_voltages(rdev, &vddc, &vddci); |
|
- | 2225 | ||
- | 2226 | rdev->pm.power_state[state_index].misc = misc; |
|
- | 2227 | rdev->pm.power_state[state_index].misc2 = misc2; |
|
- | 2228 | rdev->pm.power_state[state_index].pcie_lanes = |
|
1663 | if (misc & ATOM_PM_MISCINFO_DEFAULT_LOW_DC_STATE_ENTRY_TRUE) |
2229 | ((misc & ATOM_PPLIB_PCIE_LINK_WIDTH_MASK) >> |
- | 2230 | ATOM_PPLIB_PCIE_LINK_WIDTH_SHIFT) + 1; |
|
- | 2231 | switch (misc2 & ATOM_PPLIB_CLASSIFICATION_UI_MASK) { |
|
- | 2232 | case ATOM_PPLIB_CLASSIFICATION_UI_BATTERY: |
|
1664 | rdev->pm.power_state[state_index].type = |
2233 | rdev->pm.power_state[state_index].type = |
1665 | POWER_STATE_TYPE_BATTERY; |
2234 | POWER_STATE_TYPE_BATTERY; |
- | 2235 | break; |
|
1666 | if (misc & ATOM_PM_MISCINFO_LOAD_BALANCE_EN) |
2236 | case ATOM_PPLIB_CLASSIFICATION_UI_BALANCED: |
1667 | rdev->pm.power_state[state_index].type = |
2237 | rdev->pm.power_state[state_index].type = |
1668 | POWER_STATE_TYPE_BALANCED; |
2238 | POWER_STATE_TYPE_BALANCED; |
- | 2239 | break; |
|
1669 | if (misc & ATOM_PM_MISCINFO_3D_ACCELERATION_EN) |
2240 | case ATOM_PPLIB_CLASSIFICATION_UI_PERFORMANCE: |
1670 | rdev->pm.power_state[state_index].type = |
2241 | rdev->pm.power_state[state_index].type = |
1671 | POWER_STATE_TYPE_PERFORMANCE; |
2242 | POWER_STATE_TYPE_PERFORMANCE; |
- | 2243 | break; |
|
- | 2244 | case ATOM_PPLIB_CLASSIFICATION_UI_NONE: |
|
1672 | if (misc2 & ATOM_PM_MISCINFO2_SYSTEM_AC_LITE_MODE) |
2245 | if (misc2 & ATOM_PPLIB_CLASSIFICATION_3DPERFORMANCE) |
1673 | rdev->pm.power_state[state_index].type = |
2246 | rdev->pm.power_state[state_index].type = |
1674 | POWER_STATE_TYPE_BALANCED; |
2247 | POWER_STATE_TYPE_PERFORMANCE; |
- | 2248 | break; |
|
- | 2249 | } |
|
- | 2250 | rdev->pm.power_state[state_index].flags = 0; |
|
1675 | if (misc & ATOM_PM_MISCINFO_DRIVER_DEFAULT_MODE) { |
2251 | if (misc & ATOM_PPLIB_SINGLE_DISPLAY_ONLY) |
- | 2252 | rdev->pm.power_state[state_index].flags |= |
|
- | 2253 | RADEON_PM_STATE_SINGLE_DISPLAY_ONLY; |
|
- | 2254 | if (misc2 & ATOM_PPLIB_CLASSIFICATION_BOOT) { |
|
1676 | rdev->pm.power_state[state_index].type = |
2255 | rdev->pm.power_state[state_index].type = |
1677 | POWER_STATE_TYPE_DEFAULT; |
2256 | POWER_STATE_TYPE_DEFAULT; |
1678 | rdev->pm.default_power_state = &rdev->pm.power_state[state_index]; |
2257 | rdev->pm.default_power_state_index = state_index; |
1679 | rdev->pm.power_state[state_index].default_clock_mode = |
2258 | rdev->pm.power_state[state_index].default_clock_mode = |
- | 2259 | &rdev->pm.power_state[state_index].clock_info[mode_index - 1]; |
|
- | 2260 | if (ASIC_IS_DCE5(rdev)) { |
|
- | 2261 | /* NI chips post without MC ucode, so default clocks are strobe mode only */ |
|
- | 2262 | rdev->pm.default_sclk = rdev->pm.power_state[state_index].clock_info[0].sclk; |
|
- | 2263 | rdev->pm.default_mclk = rdev->pm.power_state[state_index].clock_info[0].mclk; |
|
- | 2264 | rdev->pm.default_vddc = rdev->pm.power_state[state_index].clock_info[0].voltage.voltage; |
|
- | 2265 | rdev->pm.default_vddci = rdev->pm.power_state[state_index].clock_info[0].voltage.vddci; |
|
- | 2266 | } else { |
|
- | 2267 | /* patch the table values with the default slck/mclk from firmware info */ |
|
- | 2268 | for (j = 0; j < mode_index; j++) { |
|
- | 2269 | rdev->pm.power_state[state_index].clock_info[j].mclk = |
|
- | 2270 | rdev->clock.default_mclk; |
|
1680 | &rdev->pm.power_state[state_index].clock_info[0]; |
2271 | rdev->pm.power_state[state_index].clock_info[j].sclk = |
- | 2272 | rdev->clock.default_sclk; |
|
- | 2273 | if (vddc) |
|
- | 2274 | rdev->pm.power_state[state_index].clock_info[j].voltage.voltage = |
|
- | 2275 | vddc; |
|
1681 | } |
2276 | } |
1682 | state_index++; |
- | |
1683 | break; |
- | |
1684 | } |
2277 | } |
1685 | } |
2278 | } |
1686 | } else if (frev == 4) { |
- | |
- | 2279 | } |
|
- | 2280 | ||
1687 | for (i = 0; i < power_info->info_4.ucNumStates; i++) { |
2281 | static bool radeon_atombios_parse_pplib_clock_info(struct radeon_device *rdev, |
1688 | mode_index = 0; |
- | |
1689 | power_state = (struct _ATOM_PPLIB_STATE *) |
- | |
1690 | (mode_info->atom_context->bios + |
2282 | int state_index, int mode_index, |
1691 | data_offset + |
- | |
1692 | le16_to_cpu(power_info->info_4.usStateArrayOffset) + |
- | |
1693 | i * power_info->info_4.ucStateEntrySize); |
2283 | union pplib_clock_info *clock_info) |
1694 | non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *) |
- | |
1695 | (mode_info->atom_context->bios + |
- | |
- | 2284 | { |
|
1696 | data_offset + |
2285 | u32 sclk, mclk; |
1697 | le16_to_cpu(power_info->info_4.usNonClockInfoArrayOffset) + |
- | |
1698 | (power_state->ucNonClockStateIndex * |
- | |
1699 | power_info->info_4.ucNonClockSize)); |
- | |
1700 | for (j = 0; j < (power_info->info_4.ucStateEntrySize - 1); j++) { |
- | |
- | 2286 | ||
1701 | if (rdev->flags & RADEON_IS_IGP) { |
2287 | if (rdev->flags & RADEON_IS_IGP) { |
1702 | struct _ATOM_PPLIB_RS780_CLOCK_INFO *clock_info = |
2288 | if (rdev->family >= CHIP_PALM) { |
1703 | (struct _ATOM_PPLIB_RS780_CLOCK_INFO *) |
2289 | sclk = le16_to_cpu(clock_info->sumo.usEngineClockLow); |
1704 | (mode_info->atom_context->bios + |
2290 | sclk |= clock_info->sumo.ucEngineClockHigh << 16; |
- | 2291 | rdev->pm.power_state[state_index].clock_info[mode_index].sclk = sclk; |
|
1705 | data_offset + |
2292 | } else { |
1706 | le16_to_cpu(power_info->info_4.usClockInfoArrayOffset) + |
2293 | sclk = le16_to_cpu(clock_info->rs780.usLowEngineClockLow); |
- | 2294 | sclk |= clock_info->rs780.ucLowEngineClockHigh << 16; |
|
1707 | (power_state->ucClockStateIndices[j] * |
2295 | rdev->pm.power_state[state_index].clock_info[mode_index].sclk = sclk; |
- | 2296 | } |
|
- | 2297 | } else if (ASIC_IS_DCE4(rdev)) { |
|
- | 2298 | sclk = le16_to_cpu(clock_info->evergreen.usEngineClockLow); |
|
1708 | power_info->info_4.ucClockInfoSize)); |
2299 | sclk |= clock_info->evergreen.ucEngineClockHigh << 16; |
1709 | sclk = le16_to_cpu(clock_info->usLowEngineClockLow); |
2300 | mclk = le16_to_cpu(clock_info->evergreen.usMemoryClockLow); |
1710 | sclk |= clock_info->ucLowEngineClockHigh << 16; |
2301 | mclk |= clock_info->evergreen.ucMemoryClockHigh << 16; |
- | 2302 | rdev->pm.power_state[state_index].clock_info[mode_index].mclk = mclk; |
|
1711 | rdev->pm.power_state[state_index].clock_info[mode_index].sclk = sclk; |
2303 | rdev->pm.power_state[state_index].clock_info[mode_index].sclk = sclk; |
1712 | /* skip invalid modes */ |
- | |
1713 | if (rdev->pm.power_state[state_index].clock_info[mode_index].sclk == 0) |
- | |
1714 | continue; |
- | |
1715 | /* skip overclock modes for now */ |
- | |
1716 | if (rdev->pm.power_state[state_index].clock_info[mode_index].sclk > |
- | |
1717 | rdev->clock.default_sclk + RADEON_MODE_OVERCLOCK_MARGIN) |
- | |
1718 | continue; |
- | |
1719 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.type = |
2304 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.type = |
1720 | VOLTAGE_SW; |
2305 | VOLTAGE_SW; |
1721 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.voltage = |
2306 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.voltage = |
1722 | clock_info->usVDDC; |
2307 | le16_to_cpu(clock_info->evergreen.usVDDC); |
1723 | mode_index++; |
- | |
1724 | } else { |
- | |
1725 | struct _ATOM_PPLIB_R600_CLOCK_INFO *clock_info = |
2308 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.vddci = |
1726 | (struct _ATOM_PPLIB_R600_CLOCK_INFO *) |
- | |
1727 | (mode_info->atom_context->bios + |
2309 | le16_to_cpu(clock_info->evergreen.usVDDCI); |
1728 | data_offset + |
2310 | } else { |
1729 | le16_to_cpu(power_info->info_4.usClockInfoArrayOffset) + |
- | |
1730 | (power_state->ucClockStateIndices[j] * |
- | |
1731 | power_info->info_4.ucClockInfoSize)); |
- | |
1732 | sclk = le16_to_cpu(clock_info->usEngineClockLow); |
2311 | sclk = le16_to_cpu(clock_info->r600.usEngineClockLow); |
1733 | sclk |= clock_info->ucEngineClockHigh << 16; |
2312 | sclk |= clock_info->r600.ucEngineClockHigh << 16; |
1734 | mclk = le16_to_cpu(clock_info->usMemoryClockLow); |
2313 | mclk = le16_to_cpu(clock_info->r600.usMemoryClockLow); |
1735 | mclk |= clock_info->ucMemoryClockHigh << 16; |
2314 | mclk |= clock_info->r600.ucMemoryClockHigh << 16; |
1736 | rdev->pm.power_state[state_index].clock_info[mode_index].mclk = mclk; |
2315 | rdev->pm.power_state[state_index].clock_info[mode_index].mclk = mclk; |
1737 | rdev->pm.power_state[state_index].clock_info[mode_index].sclk = sclk; |
2316 | rdev->pm.power_state[state_index].clock_info[mode_index].sclk = sclk; |
1738 | /* skip invalid modes */ |
- | |
1739 | if ((rdev->pm.power_state[state_index].clock_info[mode_index].mclk == 0) || |
- | |
1740 | (rdev->pm.power_state[state_index].clock_info[mode_index].sclk == 0)) |
- | |
1741 | continue; |
- | |
1742 | /* skip overclock modes for now */ |
- | |
1743 | if ((rdev->pm.power_state[state_index].clock_info[mode_index].mclk > |
- | |
1744 | rdev->clock.default_mclk + RADEON_MODE_OVERCLOCK_MARGIN) || |
- | |
1745 | (rdev->pm.power_state[state_index].clock_info[mode_index].sclk > |
- | |
1746 | rdev->clock.default_sclk + RADEON_MODE_OVERCLOCK_MARGIN)) |
- | |
1747 | continue; |
- | |
1748 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.type = |
2317 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.type = |
1749 | VOLTAGE_SW; |
2318 | VOLTAGE_SW; |
1750 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.voltage = |
2319 | rdev->pm.power_state[state_index].clock_info[mode_index].voltage.voltage = |
1751 | clock_info->usVDDC; |
2320 | le16_to_cpu(clock_info->r600.usVDDC); |
1752 | mode_index++; |
- | |
1753 | } |
2321 | } |
- | 2322 | ||
- | 2323 | if (rdev->flags & RADEON_IS_IGP) { |
|
- | 2324 | /* skip invalid modes */ |
|
- | 2325 | if (rdev->pm.power_state[state_index].clock_info[mode_index].sclk == 0) |
|
- | 2326 | return false; |
|
- | 2327 | } else { |
|
- | 2328 | /* skip invalid modes */ |
|
- | 2329 | if ((rdev->pm.power_state[state_index].clock_info[mode_index].mclk == 0) || |
|
- | 2330 | (rdev->pm.power_state[state_index].clock_info[mode_index].sclk == 0)) |
|
- | 2331 | return false; |
|
- | 2332 | } |
|
- | 2333 | return true; |
|
- | 2334 | } |
|
- | 2335 | ||
- | 2336 | static int radeon_atombios_parse_power_table_4_5(struct radeon_device *rdev) |
|
- | 2337 | { |
|
- | 2338 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
|
- | 2339 | struct _ATOM_PPLIB_NONCLOCK_INFO *non_clock_info; |
|
- | 2340 | union pplib_power_state *power_state; |
|
- | 2341 | int i, j; |
|
- | 2342 | int state_index = 0, mode_index = 0; |
|
- | 2343 | union pplib_clock_info *clock_info; |
|
- | 2344 | bool valid; |
|
- | 2345 | union power_info *power_info; |
|
- | 2346 | int index = GetIndexIntoMasterTable(DATA, PowerPlayInfo); |
|
- | 2347 | u16 data_offset; |
|
- | 2348 | u8 frev, crev; |
|
- | 2349 | ||
- | 2350 | if (!atom_parse_data_header(mode_info->atom_context, index, NULL, |
|
- | 2351 | &frev, &crev, &data_offset)) |
|
- | 2352 | return state_index; |
|
- | 2353 | power_info = (union power_info *)(mode_info->atom_context->bios + data_offset); |
|
- | 2354 | ||
- | 2355 | radeon_atombios_add_pplib_thermal_controller(rdev, &power_info->pplib.sThermalController); |
|
- | 2356 | rdev->pm.power_state = kzalloc(sizeof(struct radeon_power_state) * |
|
- | 2357 | power_info->pplib.ucNumStates, GFP_KERNEL); |
|
- | 2358 | if (!rdev->pm.power_state) |
|
- | 2359 | return state_index; |
|
- | 2360 | /* first mode is usually default, followed by low to high */ |
|
- | 2361 | for (i = 0; i < power_info->pplib.ucNumStates; i++) { |
|
- | 2362 | mode_index = 0; |
|
- | 2363 | power_state = (union pplib_power_state *) |
|
- | 2364 | (mode_info->atom_context->bios + data_offset + |
|
- | 2365 | le16_to_cpu(power_info->pplib.usStateArrayOffset) + |
|
- | 2366 | i * power_info->pplib.ucStateEntrySize); |
|
- | 2367 | non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *) |
|
- | 2368 | (mode_info->atom_context->bios + data_offset + |
|
- | 2369 | le16_to_cpu(power_info->pplib.usNonClockInfoArrayOffset) + |
|
- | 2370 | (power_state->v1.ucNonClockStateIndex * |
|
- | 2371 | power_info->pplib.ucNonClockSize)); |
|
- | 2372 | for (j = 0; j < (power_info->pplib.ucStateEntrySize - 1); j++) { |
|
- | 2373 | clock_info = (union pplib_clock_info *) |
|
- | 2374 | (mode_info->atom_context->bios + data_offset + |
|
- | 2375 | le16_to_cpu(power_info->pplib.usClockInfoArrayOffset) + |
|
- | 2376 | (power_state->v1.ucClockStateIndices[j] * |
|
- | 2377 | power_info->pplib.ucClockInfoSize)); |
|
- | 2378 | valid = radeon_atombios_parse_pplib_clock_info(rdev, |
|
- | 2379 | state_index, mode_index, |
|
- | 2380 | clock_info); |
|
- | 2381 | if (valid) |
|
- | 2382 | mode_index++; |
|
1754 | } |
2383 | } |
1755 | rdev->pm.power_state[state_index].num_clock_modes = mode_index; |
2384 | rdev->pm.power_state[state_index].num_clock_modes = mode_index; |
1756 | if (mode_index) { |
2385 | if (mode_index) { |
1757 | misc = le32_to_cpu(non_clock_info->ulCapsAndSettings); |
2386 | radeon_atombios_parse_pplib_non_clock_info(rdev, state_index, mode_index, |
1758 | misc2 = le16_to_cpu(non_clock_info->usClassification); |
- | |
1759 | rdev->pm.power_state[state_index].non_clock_info.pcie_lanes = |
- | |
1760 | ((misc & ATOM_PPLIB_PCIE_LINK_WIDTH_MASK) >> |
- | |
1761 | ATOM_PPLIB_PCIE_LINK_WIDTH_SHIFT) + 1; |
- | |
1762 | switch (misc2 & ATOM_PPLIB_CLASSIFICATION_UI_MASK) { |
- | |
1763 | case ATOM_PPLIB_CLASSIFICATION_UI_BATTERY: |
- | |
1764 | rdev->pm.power_state[state_index].type = |
- | |
1765 | POWER_STATE_TYPE_BATTERY; |
2387 | non_clock_info); |
1766 | break; |
- | |
1767 | case ATOM_PPLIB_CLASSIFICATION_UI_BALANCED: |
- | |
1768 | rdev->pm.power_state[state_index].type = |
- | |
1769 | POWER_STATE_TYPE_BALANCED; |
- | |
1770 | break; |
- | |
1771 | case ATOM_PPLIB_CLASSIFICATION_UI_PERFORMANCE: |
- | |
1772 | rdev->pm.power_state[state_index].type = |
- | |
1773 | POWER_STATE_TYPE_PERFORMANCE; |
- | |
1774 | break; |
2388 | state_index++; |
1775 | } |
2389 | } |
- | 2390 | } |
|
- | 2391 | /* if multiple clock modes, mark the lowest as no display */ |
|
- | 2392 | for (i = 0; i < state_index; i++) { |
|
- | 2393 | if (rdev->pm.power_state[i].num_clock_modes > 1) |
|
- | 2394 | rdev->pm.power_state[i].clock_info[0].flags |= |
|
- | 2395 | RADEON_PM_MODE_NO_DISPLAY; |
|
- | 2396 | } |
|
- | 2397 | /* first mode is usually default */ |
|
1776 | if (misc2 & ATOM_PPLIB_CLASSIFICATION_BOOT) { |
2398 | if (rdev->pm.default_power_state_index == -1) { |
1777 | rdev->pm.power_state[state_index].type = |
2399 | rdev->pm.power_state[0].type = |
1778 | POWER_STATE_TYPE_DEFAULT; |
2400 | POWER_STATE_TYPE_DEFAULT; |
1779 | rdev->pm.default_power_state = &rdev->pm.power_state[state_index]; |
2401 | rdev->pm.default_power_state_index = 0; |
1780 | rdev->pm.power_state[state_index].default_clock_mode = |
2402 | rdev->pm.power_state[0].default_clock_mode = |
1781 | &rdev->pm.power_state[state_index].clock_info[mode_index - 1]; |
2403 | &rdev->pm.power_state[0].clock_info[0]; |
- | 2404 | } |
|
- | 2405 | return state_index; |
|
1782 | } |
2406 | } |
- | 2407 | ||
- | 2408 | static int radeon_atombios_parse_power_table_6(struct radeon_device *rdev) |
|
- | 2409 | { |
|
- | 2410 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
|
- | 2411 | struct _ATOM_PPLIB_NONCLOCK_INFO *non_clock_info; |
|
- | 2412 | union pplib_power_state *power_state; |
|
- | 2413 | int i, j, non_clock_array_index, clock_array_index; |
|
- | 2414 | int state_index = 0, mode_index = 0; |
|
- | 2415 | union pplib_clock_info *clock_info; |
|
- | 2416 | struct StateArray *state_array; |
|
- | 2417 | struct ClockInfoArray *clock_info_array; |
|
- | 2418 | struct NonClockInfoArray *non_clock_info_array; |
|
- | 2419 | bool valid; |
|
- | 2420 | union power_info *power_info; |
|
- | 2421 | int index = GetIndexIntoMasterTable(DATA, PowerPlayInfo); |
|
- | 2422 | u16 data_offset; |
|
- | 2423 | u8 frev, crev; |
|
- | 2424 | ||
- | 2425 | if (!atom_parse_data_header(mode_info->atom_context, index, NULL, |
|
- | 2426 | &frev, &crev, &data_offset)) |
|
- | 2427 | return state_index; |
|
- | 2428 | power_info = (union power_info *)(mode_info->atom_context->bios + data_offset); |
|
- | 2429 | ||
- | 2430 | radeon_atombios_add_pplib_thermal_controller(rdev, &power_info->pplib.sThermalController); |
|
- | 2431 | state_array = (struct StateArray *) |
|
- | 2432 | (mode_info->atom_context->bios + data_offset + |
|
- | 2433 | le16_to_cpu(power_info->pplib.usStateArrayOffset)); |
|
- | 2434 | clock_info_array = (struct ClockInfoArray *) |
|
- | 2435 | (mode_info->atom_context->bios + data_offset + |
|
- | 2436 | le16_to_cpu(power_info->pplib.usClockInfoArrayOffset)); |
|
- | 2437 | non_clock_info_array = (struct NonClockInfoArray *) |
|
- | 2438 | (mode_info->atom_context->bios + data_offset + |
|
- | 2439 | le16_to_cpu(power_info->pplib.usNonClockInfoArrayOffset)); |
|
- | 2440 | rdev->pm.power_state = kzalloc(sizeof(struct radeon_power_state) * |
|
- | 2441 | state_array->ucNumEntries, GFP_KERNEL); |
|
- | 2442 | if (!rdev->pm.power_state) |
|
- | 2443 | return state_index; |
|
- | 2444 | for (i = 0; i < state_array->ucNumEntries; i++) { |
|
- | 2445 | mode_index = 0; |
|
- | 2446 | power_state = (union pplib_power_state *)&state_array->states[i]; |
|
- | 2447 | /* XXX this might be an inagua bug... */ |
|
- | 2448 | non_clock_array_index = i; /* power_state->v2.nonClockInfoIndex */ |
|
- | 2449 | non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *) |
|
- | 2450 | &non_clock_info_array->nonClockInfo[non_clock_array_index]; |
|
- | 2451 | for (j = 0; j < power_state->v2.ucNumDPMLevels; j++) { |
|
- | 2452 | clock_array_index = power_state->v2.clockInfoIndex[j]; |
|
- | 2453 | /* XXX this might be an inagua bug... */ |
|
- | 2454 | if (clock_array_index >= clock_info_array->ucNumEntries) |
|
- | 2455 | continue; |
|
- | 2456 | clock_info = (union pplib_clock_info *) |
|
- | 2457 | &clock_info_array->clockInfo[clock_array_index]; |
|
- | 2458 | valid = radeon_atombios_parse_pplib_clock_info(rdev, |
|
- | 2459 | state_index, mode_index, |
|
- | 2460 | clock_info); |
|
- | 2461 | if (valid) |
|
- | 2462 | mode_index++; |
|
- | 2463 | } |
|
- | 2464 | rdev->pm.power_state[state_index].num_clock_modes = mode_index; |
|
- | 2465 | if (mode_index) { |
|
- | 2466 | radeon_atombios_parse_pplib_non_clock_info(rdev, state_index, mode_index, |
|
- | 2467 | non_clock_info); |
|
1783 | state_index++; |
2468 | state_index++; |
1784 | } |
2469 | } |
1785 | } |
2470 | } |
- | 2471 | /* if multiple clock modes, mark the lowest as no display */ |
|
- | 2472 | for (i = 0; i < state_index; i++) { |
|
- | 2473 | if (rdev->pm.power_state[i].num_clock_modes > 1) |
|
- | 2474 | rdev->pm.power_state[i].clock_info[0].flags |= |
|
- | 2475 | RADEON_PM_MODE_NO_DISPLAY; |
|
- | 2476 | } |
|
- | 2477 | /* first mode is usually default */ |
|
- | 2478 | if (rdev->pm.default_power_state_index == -1) { |
|
- | 2479 | rdev->pm.power_state[0].type = |
|
- | 2480 | POWER_STATE_TYPE_DEFAULT; |
|
- | 2481 | rdev->pm.default_power_state_index = 0; |
|
- | 2482 | rdev->pm.power_state[0].default_clock_mode = |
|
- | 2483 | &rdev->pm.power_state[0].clock_info[0]; |
|
1786 | } |
2484 | } |
1787 | } else { |
2485 | return state_index; |
1788 | /* XXX figure out some good default low power mode for cards w/out power tables */ |
- | |
1789 | } |
2486 | } |
Line -... | Line 2487... | ||
- | 2487 | ||
- | 2488 | void radeon_atombios_get_power_modes(struct radeon_device *rdev) |
|
- | 2489 | { |
|
- | 2490 | struct radeon_mode_info *mode_info = &rdev->mode_info; |
|
- | 2491 | int index = GetIndexIntoMasterTable(DATA, PowerPlayInfo); |
|
- | 2492 | u16 data_offset; |
|
- | 2493 | u8 frev, crev; |
|
- | 2494 | int state_index = 0; |
|
1790 | 2495 | ||
- | 2496 | rdev->pm.default_power_state_index = -1; |
|
- | 2497 | ||
- | 2498 | if (atom_parse_data_header(mode_info->atom_context, index, NULL, |
|
- | 2499 | &frev, &crev, &data_offset)) { |
|
- | 2500 | switch (frev) { |
|
- | 2501 | case 1: |
|
- | 2502 | case 2: |
|
- | 2503 | case 3: |
|
- | 2504 | state_index = radeon_atombios_parse_power_table_1_3(rdev); |
|
- | 2505 | break; |
|
- | 2506 | case 4: |
|
- | 2507 | case 5: |
|
- | 2508 | state_index = radeon_atombios_parse_power_table_4_5(rdev); |
|
- | 2509 | break; |
|
- | 2510 | case 6: |
|
- | 2511 | state_index = radeon_atombios_parse_power_table_6(rdev); |
|
- | 2512 | break; |
|
- | 2513 | default: |
|
- | 2514 | break; |
|
- | 2515 | } |
|
- | 2516 | } else { |
|
- | 2517 | rdev->pm.power_state = kzalloc(sizeof(struct radeon_power_state), GFP_KERNEL); |
|
1791 | if (rdev->pm.default_power_state == NULL) { |
2518 | if (rdev->pm.power_state) { |
1792 | /* add the default mode */ |
2519 | /* add the default mode */ |
1793 | rdev->pm.power_state[state_index].type = |
2520 | rdev->pm.power_state[state_index].type = |
1794 | POWER_STATE_TYPE_DEFAULT; |
2521 | POWER_STATE_TYPE_DEFAULT; |
1795 | rdev->pm.power_state[state_index].num_clock_modes = 1; |
2522 | rdev->pm.power_state[state_index].num_clock_modes = 1; |
1796 | rdev->pm.power_state[state_index].clock_info[0].mclk = rdev->clock.default_mclk; |
2523 | rdev->pm.power_state[state_index].clock_info[0].mclk = rdev->clock.default_mclk; |
1797 | rdev->pm.power_state[state_index].clock_info[0].sclk = rdev->clock.default_sclk; |
2524 | rdev->pm.power_state[state_index].clock_info[0].sclk = rdev->clock.default_sclk; |
1798 | rdev->pm.power_state[state_index].default_clock_mode = |
2525 | rdev->pm.power_state[state_index].default_clock_mode = |
1799 | &rdev->pm.power_state[state_index].clock_info[0]; |
2526 | &rdev->pm.power_state[state_index].clock_info[0]; |
1800 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = VOLTAGE_NONE; |
- | |
1801 | if (rdev->asic->get_pcie_lanes) |
2527 | rdev->pm.power_state[state_index].clock_info[0].voltage.type = VOLTAGE_NONE; |
1802 | rdev->pm.power_state[state_index].non_clock_info.pcie_lanes = radeon_get_pcie_lanes(rdev); |
- | |
1803 | else |
2528 | rdev->pm.power_state[state_index].pcie_lanes = 16; |
1804 | rdev->pm.power_state[state_index].non_clock_info.pcie_lanes = 16; |
2529 | rdev->pm.default_power_state_index = state_index; |
1805 | rdev->pm.default_power_state = &rdev->pm.power_state[state_index]; |
2530 | rdev->pm.power_state[state_index].flags = 0; |
1806 | state_index++; |
2531 | state_index++; |
- | 2532 | } |
|
- | 2533 | } |
|
1807 | } |
2534 | |
Line 1808... | Line 2535... | ||
1808 | rdev->pm.num_power_states = state_index; |
2535 | rdev->pm.num_power_states = state_index; |
1809 | 2536 | ||
1810 | rdev->pm.current_power_state = rdev->pm.default_power_state; |
2537 | rdev->pm.current_power_state_index = rdev->pm.default_power_state_index; |
1811 | rdev->pm.current_clock_mode = |
2538 | rdev->pm.current_clock_mode_index = 0; |
Line 1812... | Line 2539... | ||
1812 | rdev->pm.default_power_state->default_clock_mode; |
2539 | rdev->pm.current_vddc = rdev->pm.power_state[rdev->pm.default_power_state_index].clock_info[0].voltage.voltage; |
1813 | } |
2540 | } |
1814 | 2541 | ||
Line 1826... | Line 2553... | ||
1826 | { |
2553 | { |
1827 | GET_ENGINE_CLOCK_PS_ALLOCATION args; |
2554 | GET_ENGINE_CLOCK_PS_ALLOCATION args; |
1828 | int index = GetIndexIntoMasterTable(COMMAND, GetEngineClock); |
2555 | int index = GetIndexIntoMasterTable(COMMAND, GetEngineClock); |
Line 1829... | Line 2556... | ||
1829 | 2556 | ||
1830 | atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
2557 | atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
1831 | return args.ulReturnEngineClock; |
2558 | return le32_to_cpu(args.ulReturnEngineClock); |
Line 1832... | Line 2559... | ||
1832 | } |
2559 | } |
1833 | 2560 | ||
1834 | uint32_t radeon_atom_get_memory_clock(struct radeon_device *rdev) |
2561 | uint32_t radeon_atom_get_memory_clock(struct radeon_device *rdev) |
1835 | { |
2562 | { |
Line 1836... | Line 2563... | ||
1836 | GET_MEMORY_CLOCK_PS_ALLOCATION args; |
2563 | GET_MEMORY_CLOCK_PS_ALLOCATION args; |
1837 | int index = GetIndexIntoMasterTable(COMMAND, GetMemoryClock); |
2564 | int index = GetIndexIntoMasterTable(COMMAND, GetMemoryClock); |
1838 | 2565 | ||
Line 1839... | Line 2566... | ||
1839 | atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
2566 | atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
1840 | return args.ulReturnMemoryClock; |
2567 | return le32_to_cpu(args.ulReturnMemoryClock); |
1841 | } |
2568 | } |
1842 | 2569 | ||
1843 | void radeon_atom_set_engine_clock(struct radeon_device *rdev, |
2570 | void radeon_atom_set_engine_clock(struct radeon_device *rdev, |
Line 1844... | Line 2571... | ||
1844 | uint32_t eng_clock) |
2571 | uint32_t eng_clock) |
Line 1845... | Line 2572... | ||
1845 | { |
2572 | { |
1846 | SET_ENGINE_CLOCK_PS_ALLOCATION args; |
2573 | SET_ENGINE_CLOCK_PS_ALLOCATION args; |
Line 1847... | Line 2574... | ||
1847 | int index = GetIndexIntoMasterTable(COMMAND, SetEngineClock); |
2574 | int index = GetIndexIntoMasterTable(COMMAND, SetEngineClock); |
Line 1858... | Line 2585... | ||
1858 | int index = GetIndexIntoMasterTable(COMMAND, SetMemoryClock); |
2585 | int index = GetIndexIntoMasterTable(COMMAND, SetMemoryClock); |
Line 1859... | Line 2586... | ||
1859 | 2586 | ||
1860 | if (rdev->flags & RADEON_IS_IGP) |
2587 | if (rdev->flags & RADEON_IS_IGP) |
Line 1861... | Line 2588... | ||
1861 | return; |
2588 | return; |
- | 2589 | ||
- | 2590 | args.ulTargetMemoryClock = cpu_to_le32(mem_clock); /* 10 khz */ |
|
- | 2591 | ||
- | 2592 | atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
|
- | 2593 | } |
|
- | 2594 | ||
- | 2595 | union set_voltage { |
|
- | 2596 | struct _SET_VOLTAGE_PS_ALLOCATION alloc; |
|
- | 2597 | struct _SET_VOLTAGE_PARAMETERS v1; |
|
- | 2598 | struct _SET_VOLTAGE_PARAMETERS_V2 v2; |
|
- | 2599 | }; |
|
- | 2600 | ||
- | 2601 | void radeon_atom_set_voltage(struct radeon_device *rdev, u16 voltage_level, u8 voltage_type) |
|
- | 2602 | { |
|
- | 2603 | union set_voltage args; |
|
- | 2604 | int index = GetIndexIntoMasterTable(COMMAND, SetVoltage); |
|
- | 2605 | u8 frev, crev, volt_index = voltage_level; |
|
- | 2606 | ||
- | 2607 | if (!atom_parse_cmd_header(rdev->mode_info.atom_context, index, &frev, &crev)) |
|
- | 2608 | return; |
|
- | 2609 | ||
- | 2610 | switch (crev) { |
|
- | 2611 | case 1: |
|
- | 2612 | args.v1.ucVoltageType = voltage_type; |
|
- | 2613 | args.v1.ucVoltageMode = SET_ASIC_VOLTAGE_MODE_ALL_SOURCE; |
|
- | 2614 | args.v1.ucVoltageIndex = volt_index; |
|
- | 2615 | break; |
|
- | 2616 | case 2: |
|
- | 2617 | args.v2.ucVoltageType = voltage_type; |
|
- | 2618 | args.v2.ucVoltageMode = SET_ASIC_VOLTAGE_MODE_SET_VOLTAGE; |
|
- | 2619 | args.v2.usVoltageLevel = cpu_to_le16(voltage_level); |
|
- | 2620 | break; |
|
- | 2621 | default: |
|
- | 2622 | DRM_ERROR("Unknown table version %d, %d\n", frev, crev); |
|
Line 1862... | Line 2623... | ||
1862 | 2623 | return; |
|
1863 | args.ulTargetMemoryClock = mem_clock; /* 10 khz */ |
2624 | } |
Line -... | Line 2625... | ||
- | 2625 | ||
- | 2626 | atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
|
1864 | 2627 | } |
|
1865 | atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
2628 | |
1866 | } |
2629 | |
1867 | 2630 | ||
Line 1880... | Line 2643... | ||
1880 | 2643 | ||
1881 | /* let the bios control the backlight */ |
2644 | /* let the bios control the backlight */ |
Line 1882... | Line 2645... | ||
1882 | bios_2_scratch &= ~ATOM_S2_VRI_BRIGHT_ENABLE; |
2645 | bios_2_scratch &= ~ATOM_S2_VRI_BRIGHT_ENABLE; |
1883 | 2646 | ||
Line 1884... | Line 2647... | ||
1884 | /* tell the bios not to handle mode switching */ |
2647 | /* tell the bios not to handle mode switching */ |
1885 | bios_6_scratch |= (ATOM_S6_ACC_BLOCK_DISPLAY_SWITCH | ATOM_S6_ACC_MODE); |
2648 | bios_6_scratch |= ATOM_S6_ACC_BLOCK_DISPLAY_SWITCH; |
1886 | 2649 | ||
1887 | if (rdev->family >= CHIP_R600) { |
2650 | if (rdev->family >= CHIP_R600) { |
Line 1931... | Line 2694... | ||
1931 | if (rdev->family >= CHIP_R600) |
2694 | if (rdev->family >= CHIP_R600) |
1932 | bios_6_scratch = RREG32(R600_BIOS_6_SCRATCH); |
2695 | bios_6_scratch = RREG32(R600_BIOS_6_SCRATCH); |
1933 | else |
2696 | else |
1934 | bios_6_scratch = RREG32(RADEON_BIOS_6_SCRATCH); |
2697 | bios_6_scratch = RREG32(RADEON_BIOS_6_SCRATCH); |
Line 1935... | Line 2698... | ||
1935 | 2698 | ||
1936 | if (lock) |
2699 | if (lock) { |
- | 2700 | bios_6_scratch |= ATOM_S6_CRITICAL_STATE; |
|
1937 | bios_6_scratch |= ATOM_S6_CRITICAL_STATE; |
2701 | bios_6_scratch &= ~ATOM_S6_ACC_MODE; |
1938 | else |
2702 | } else { |
- | 2703 | bios_6_scratch &= ~ATOM_S6_CRITICAL_STATE; |
|
- | 2704 | bios_6_scratch |= ATOM_S6_ACC_MODE; |
|
Line 1939... | Line 2705... | ||
1939 | bios_6_scratch &= ~ATOM_S6_CRITICAL_STATE; |
2705 | } |
1940 | 2706 | ||
1941 | if (rdev->family >= CHIP_R600) |
2707 | if (rdev->family >= CHIP_R600) |
1942 | WREG32(R600_BIOS_6_SCRATCH, bios_6_scratch); |
2708 | WREG32(R600_BIOS_6_SCRATCH, bios_6_scratch); |
Line 1968... | Line 2734... | ||
1968 | } |
2734 | } |
Line 1969... | Line 2735... | ||
1969 | 2735 | ||
1970 | if ((radeon_encoder->devices & ATOM_DEVICE_TV1_SUPPORT) && |
2736 | if ((radeon_encoder->devices & ATOM_DEVICE_TV1_SUPPORT) && |
1971 | (radeon_connector->devices & ATOM_DEVICE_TV1_SUPPORT)) { |
2737 | (radeon_connector->devices & ATOM_DEVICE_TV1_SUPPORT)) { |
1972 | if (connected) { |
2738 | if (connected) { |
1973 | DRM_DEBUG("TV1 connected\n"); |
2739 | DRM_DEBUG_KMS("TV1 connected\n"); |
1974 | bios_3_scratch |= ATOM_S3_TV1_ACTIVE; |
2740 | bios_3_scratch |= ATOM_S3_TV1_ACTIVE; |
1975 | bios_6_scratch |= ATOM_S6_ACC_REQ_TV1; |
2741 | bios_6_scratch |= ATOM_S6_ACC_REQ_TV1; |
1976 | } else { |
2742 | } else { |
1977 | DRM_DEBUG("TV1 disconnected\n"); |
2743 | DRM_DEBUG_KMS("TV1 disconnected\n"); |
1978 | bios_0_scratch &= ~ATOM_S0_TV1_MASK; |
2744 | bios_0_scratch &= ~ATOM_S0_TV1_MASK; |
1979 | bios_3_scratch &= ~ATOM_S3_TV1_ACTIVE; |
2745 | bios_3_scratch &= ~ATOM_S3_TV1_ACTIVE; |
1980 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_TV1; |
2746 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_TV1; |
1981 | } |
2747 | } |
1982 | } |
2748 | } |
1983 | if ((radeon_encoder->devices & ATOM_DEVICE_CV_SUPPORT) && |
2749 | if ((radeon_encoder->devices & ATOM_DEVICE_CV_SUPPORT) && |
1984 | (radeon_connector->devices & ATOM_DEVICE_CV_SUPPORT)) { |
2750 | (radeon_connector->devices & ATOM_DEVICE_CV_SUPPORT)) { |
1985 | if (connected) { |
2751 | if (connected) { |
1986 | DRM_DEBUG("CV connected\n"); |
2752 | DRM_DEBUG_KMS("CV connected\n"); |
1987 | bios_3_scratch |= ATOM_S3_CV_ACTIVE; |
2753 | bios_3_scratch |= ATOM_S3_CV_ACTIVE; |
1988 | bios_6_scratch |= ATOM_S6_ACC_REQ_CV; |
2754 | bios_6_scratch |= ATOM_S6_ACC_REQ_CV; |
1989 | } else { |
2755 | } else { |
1990 | DRM_DEBUG("CV disconnected\n"); |
2756 | DRM_DEBUG_KMS("CV disconnected\n"); |
1991 | bios_0_scratch &= ~ATOM_S0_CV_MASK; |
2757 | bios_0_scratch &= ~ATOM_S0_CV_MASK; |
1992 | bios_3_scratch &= ~ATOM_S3_CV_ACTIVE; |
2758 | bios_3_scratch &= ~ATOM_S3_CV_ACTIVE; |
1993 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_CV; |
2759 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_CV; |
1994 | } |
2760 | } |
1995 | } |
2761 | } |
1996 | if ((radeon_encoder->devices & ATOM_DEVICE_LCD1_SUPPORT) && |
2762 | if ((radeon_encoder->devices & ATOM_DEVICE_LCD1_SUPPORT) && |
1997 | (radeon_connector->devices & ATOM_DEVICE_LCD1_SUPPORT)) { |
2763 | (radeon_connector->devices & ATOM_DEVICE_LCD1_SUPPORT)) { |
1998 | if (connected) { |
2764 | if (connected) { |
1999 | DRM_DEBUG("LCD1 connected\n"); |
2765 | DRM_DEBUG_KMS("LCD1 connected\n"); |
2000 | bios_0_scratch |= ATOM_S0_LCD1; |
2766 | bios_0_scratch |= ATOM_S0_LCD1; |
2001 | bios_3_scratch |= ATOM_S3_LCD1_ACTIVE; |
2767 | bios_3_scratch |= ATOM_S3_LCD1_ACTIVE; |
2002 | bios_6_scratch |= ATOM_S6_ACC_REQ_LCD1; |
2768 | bios_6_scratch |= ATOM_S6_ACC_REQ_LCD1; |
2003 | } else { |
2769 | } else { |
2004 | DRM_DEBUG("LCD1 disconnected\n"); |
2770 | DRM_DEBUG_KMS("LCD1 disconnected\n"); |
2005 | bios_0_scratch &= ~ATOM_S0_LCD1; |
2771 | bios_0_scratch &= ~ATOM_S0_LCD1; |
2006 | bios_3_scratch &= ~ATOM_S3_LCD1_ACTIVE; |
2772 | bios_3_scratch &= ~ATOM_S3_LCD1_ACTIVE; |
2007 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_LCD1; |
2773 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_LCD1; |
2008 | } |
2774 | } |
2009 | } |
2775 | } |
2010 | if ((radeon_encoder->devices & ATOM_DEVICE_CRT1_SUPPORT) && |
2776 | if ((radeon_encoder->devices & ATOM_DEVICE_CRT1_SUPPORT) && |
2011 | (radeon_connector->devices & ATOM_DEVICE_CRT1_SUPPORT)) { |
2777 | (radeon_connector->devices & ATOM_DEVICE_CRT1_SUPPORT)) { |
2012 | if (connected) { |
2778 | if (connected) { |
2013 | DRM_DEBUG("CRT1 connected\n"); |
2779 | DRM_DEBUG_KMS("CRT1 connected\n"); |
2014 | bios_0_scratch |= ATOM_S0_CRT1_COLOR; |
2780 | bios_0_scratch |= ATOM_S0_CRT1_COLOR; |
2015 | bios_3_scratch |= ATOM_S3_CRT1_ACTIVE; |
2781 | bios_3_scratch |= ATOM_S3_CRT1_ACTIVE; |
2016 | bios_6_scratch |= ATOM_S6_ACC_REQ_CRT1; |
2782 | bios_6_scratch |= ATOM_S6_ACC_REQ_CRT1; |
2017 | } else { |
2783 | } else { |
2018 | DRM_DEBUG("CRT1 disconnected\n"); |
2784 | DRM_DEBUG_KMS("CRT1 disconnected\n"); |
2019 | bios_0_scratch &= ~ATOM_S0_CRT1_MASK; |
2785 | bios_0_scratch &= ~ATOM_S0_CRT1_MASK; |
2020 | bios_3_scratch &= ~ATOM_S3_CRT1_ACTIVE; |
2786 | bios_3_scratch &= ~ATOM_S3_CRT1_ACTIVE; |
2021 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_CRT1; |
2787 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_CRT1; |
2022 | } |
2788 | } |
2023 | } |
2789 | } |
2024 | if ((radeon_encoder->devices & ATOM_DEVICE_CRT2_SUPPORT) && |
2790 | if ((radeon_encoder->devices & ATOM_DEVICE_CRT2_SUPPORT) && |
2025 | (radeon_connector->devices & ATOM_DEVICE_CRT2_SUPPORT)) { |
2791 | (radeon_connector->devices & ATOM_DEVICE_CRT2_SUPPORT)) { |
2026 | if (connected) { |
2792 | if (connected) { |
2027 | DRM_DEBUG("CRT2 connected\n"); |
2793 | DRM_DEBUG_KMS("CRT2 connected\n"); |
2028 | bios_0_scratch |= ATOM_S0_CRT2_COLOR; |
2794 | bios_0_scratch |= ATOM_S0_CRT2_COLOR; |
2029 | bios_3_scratch |= ATOM_S3_CRT2_ACTIVE; |
2795 | bios_3_scratch |= ATOM_S3_CRT2_ACTIVE; |
2030 | bios_6_scratch |= ATOM_S6_ACC_REQ_CRT2; |
2796 | bios_6_scratch |= ATOM_S6_ACC_REQ_CRT2; |
2031 | } else { |
2797 | } else { |
2032 | DRM_DEBUG("CRT2 disconnected\n"); |
2798 | DRM_DEBUG_KMS("CRT2 disconnected\n"); |
2033 | bios_0_scratch &= ~ATOM_S0_CRT2_MASK; |
2799 | bios_0_scratch &= ~ATOM_S0_CRT2_MASK; |
2034 | bios_3_scratch &= ~ATOM_S3_CRT2_ACTIVE; |
2800 | bios_3_scratch &= ~ATOM_S3_CRT2_ACTIVE; |
2035 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_CRT2; |
2801 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_CRT2; |
2036 | } |
2802 | } |
2037 | } |
2803 | } |
2038 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP1_SUPPORT) && |
2804 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP1_SUPPORT) && |
2039 | (radeon_connector->devices & ATOM_DEVICE_DFP1_SUPPORT)) { |
2805 | (radeon_connector->devices & ATOM_DEVICE_DFP1_SUPPORT)) { |
2040 | if (connected) { |
2806 | if (connected) { |
2041 | DRM_DEBUG("DFP1 connected\n"); |
2807 | DRM_DEBUG_KMS("DFP1 connected\n"); |
2042 | bios_0_scratch |= ATOM_S0_DFP1; |
2808 | bios_0_scratch |= ATOM_S0_DFP1; |
2043 | bios_3_scratch |= ATOM_S3_DFP1_ACTIVE; |
2809 | bios_3_scratch |= ATOM_S3_DFP1_ACTIVE; |
2044 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP1; |
2810 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP1; |
2045 | } else { |
2811 | } else { |
2046 | DRM_DEBUG("DFP1 disconnected\n"); |
2812 | DRM_DEBUG_KMS("DFP1 disconnected\n"); |
2047 | bios_0_scratch &= ~ATOM_S0_DFP1; |
2813 | bios_0_scratch &= ~ATOM_S0_DFP1; |
2048 | bios_3_scratch &= ~ATOM_S3_DFP1_ACTIVE; |
2814 | bios_3_scratch &= ~ATOM_S3_DFP1_ACTIVE; |
2049 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP1; |
2815 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP1; |
2050 | } |
2816 | } |
2051 | } |
2817 | } |
2052 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP2_SUPPORT) && |
2818 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP2_SUPPORT) && |
2053 | (radeon_connector->devices & ATOM_DEVICE_DFP2_SUPPORT)) { |
2819 | (radeon_connector->devices & ATOM_DEVICE_DFP2_SUPPORT)) { |
2054 | if (connected) { |
2820 | if (connected) { |
2055 | DRM_DEBUG("DFP2 connected\n"); |
2821 | DRM_DEBUG_KMS("DFP2 connected\n"); |
2056 | bios_0_scratch |= ATOM_S0_DFP2; |
2822 | bios_0_scratch |= ATOM_S0_DFP2; |
2057 | bios_3_scratch |= ATOM_S3_DFP2_ACTIVE; |
2823 | bios_3_scratch |= ATOM_S3_DFP2_ACTIVE; |
2058 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP2; |
2824 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP2; |
2059 | } else { |
2825 | } else { |
2060 | DRM_DEBUG("DFP2 disconnected\n"); |
2826 | DRM_DEBUG_KMS("DFP2 disconnected\n"); |
2061 | bios_0_scratch &= ~ATOM_S0_DFP2; |
2827 | bios_0_scratch &= ~ATOM_S0_DFP2; |
2062 | bios_3_scratch &= ~ATOM_S3_DFP2_ACTIVE; |
2828 | bios_3_scratch &= ~ATOM_S3_DFP2_ACTIVE; |
2063 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP2; |
2829 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP2; |
2064 | } |
2830 | } |
2065 | } |
2831 | } |
2066 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP3_SUPPORT) && |
2832 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP3_SUPPORT) && |
2067 | (radeon_connector->devices & ATOM_DEVICE_DFP3_SUPPORT)) { |
2833 | (radeon_connector->devices & ATOM_DEVICE_DFP3_SUPPORT)) { |
2068 | if (connected) { |
2834 | if (connected) { |
2069 | DRM_DEBUG("DFP3 connected\n"); |
2835 | DRM_DEBUG_KMS("DFP3 connected\n"); |
2070 | bios_0_scratch |= ATOM_S0_DFP3; |
2836 | bios_0_scratch |= ATOM_S0_DFP3; |
2071 | bios_3_scratch |= ATOM_S3_DFP3_ACTIVE; |
2837 | bios_3_scratch |= ATOM_S3_DFP3_ACTIVE; |
2072 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP3; |
2838 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP3; |
2073 | } else { |
2839 | } else { |
2074 | DRM_DEBUG("DFP3 disconnected\n"); |
2840 | DRM_DEBUG_KMS("DFP3 disconnected\n"); |
2075 | bios_0_scratch &= ~ATOM_S0_DFP3; |
2841 | bios_0_scratch &= ~ATOM_S0_DFP3; |
2076 | bios_3_scratch &= ~ATOM_S3_DFP3_ACTIVE; |
2842 | bios_3_scratch &= ~ATOM_S3_DFP3_ACTIVE; |
2077 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP3; |
2843 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP3; |
2078 | } |
2844 | } |
2079 | } |
2845 | } |
2080 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP4_SUPPORT) && |
2846 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP4_SUPPORT) && |
2081 | (radeon_connector->devices & ATOM_DEVICE_DFP4_SUPPORT)) { |
2847 | (radeon_connector->devices & ATOM_DEVICE_DFP4_SUPPORT)) { |
2082 | if (connected) { |
2848 | if (connected) { |
2083 | DRM_DEBUG("DFP4 connected\n"); |
2849 | DRM_DEBUG_KMS("DFP4 connected\n"); |
2084 | bios_0_scratch |= ATOM_S0_DFP4; |
2850 | bios_0_scratch |= ATOM_S0_DFP4; |
2085 | bios_3_scratch |= ATOM_S3_DFP4_ACTIVE; |
2851 | bios_3_scratch |= ATOM_S3_DFP4_ACTIVE; |
2086 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP4; |
2852 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP4; |
2087 | } else { |
2853 | } else { |
2088 | DRM_DEBUG("DFP4 disconnected\n"); |
2854 | DRM_DEBUG_KMS("DFP4 disconnected\n"); |
2089 | bios_0_scratch &= ~ATOM_S0_DFP4; |
2855 | bios_0_scratch &= ~ATOM_S0_DFP4; |
2090 | bios_3_scratch &= ~ATOM_S3_DFP4_ACTIVE; |
2856 | bios_3_scratch &= ~ATOM_S3_DFP4_ACTIVE; |
2091 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP4; |
2857 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP4; |
2092 | } |
2858 | } |
2093 | } |
2859 | } |
2094 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP5_SUPPORT) && |
2860 | if ((radeon_encoder->devices & ATOM_DEVICE_DFP5_SUPPORT) && |
2095 | (radeon_connector->devices & ATOM_DEVICE_DFP5_SUPPORT)) { |
2861 | (radeon_connector->devices & ATOM_DEVICE_DFP5_SUPPORT)) { |
2096 | if (connected) { |
2862 | if (connected) { |
2097 | DRM_DEBUG("DFP5 connected\n"); |
2863 | DRM_DEBUG_KMS("DFP5 connected\n"); |
2098 | bios_0_scratch |= ATOM_S0_DFP5; |
2864 | bios_0_scratch |= ATOM_S0_DFP5; |
2099 | bios_3_scratch |= ATOM_S3_DFP5_ACTIVE; |
2865 | bios_3_scratch |= ATOM_S3_DFP5_ACTIVE; |
2100 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP5; |
2866 | bios_6_scratch |= ATOM_S6_ACC_REQ_DFP5; |
2101 | } else { |
2867 | } else { |
2102 | DRM_DEBUG("DFP5 disconnected\n"); |
2868 | DRM_DEBUG_KMS("DFP5 disconnected\n"); |
2103 | bios_0_scratch &= ~ATOM_S0_DFP5; |
2869 | bios_0_scratch &= ~ATOM_S0_DFP5; |
2104 | bios_3_scratch &= ~ATOM_S3_DFP5_ACTIVE; |
2870 | bios_3_scratch &= ~ATOM_S3_DFP5_ACTIVE; |
2105 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP5; |
2871 | bios_6_scratch &= ~ATOM_S6_ACC_REQ_DFP5; |
2106 | } |
2872 | } |