aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/radeon/radeon_atombios.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu/drm/radeon/radeon_atombios.c')
-rw-r--r--drivers/gpu/drm/radeon/radeon_atombios.c43
1 files changed, 26 insertions, 17 deletions
diff --git a/drivers/gpu/drm/radeon/radeon_atombios.c b/drivers/gpu/drm/radeon/radeon_atombios.c
index 02d5c415f499..f5d12fb103fa 100644
--- a/drivers/gpu/drm/radeon/radeon_atombios.c
+++ b/drivers/gpu/drm/radeon/radeon_atombios.c
@@ -675,7 +675,8 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev)
675 ATOM_ENCODER_CAP_RECORD *cap_record; 675 ATOM_ENCODER_CAP_RECORD *cap_record;
676 u16 caps = 0; 676 u16 caps = 0;
677 677
678 while (record->ucRecordType > 0 && 678 while (record->ucRecordSize > 0 &&
679 record->ucRecordType > 0 &&
679 record->ucRecordType <= ATOM_MAX_OBJECT_RECORD_NUMBER) { 680 record->ucRecordType <= ATOM_MAX_OBJECT_RECORD_NUMBER) {
680 switch (record->ucRecordType) { 681 switch (record->ucRecordType) {
681 case ATOM_ENCODER_CAP_RECORD_TYPE: 682 case ATOM_ENCODER_CAP_RECORD_TYPE:
@@ -720,7 +721,8 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev)
720 break; 721 break;
721 } 722 }
722 723
723 while (record->ucRecordType > 0 && 724 while (record->ucRecordSize > 0 &&
725 record->ucRecordType > 0 &&
724 record->ucRecordType <= ATOM_MAX_OBJECT_RECORD_NUMBER) { 726 record->ucRecordType <= ATOM_MAX_OBJECT_RECORD_NUMBER) {
725 switch (record->ucRecordType) { 727 switch (record->ucRecordType) {
726 case ATOM_I2C_RECORD_TYPE: 728 case ATOM_I2C_RECORD_TYPE:
@@ -782,10 +784,9 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev)
782 ATOM_HPD_INT_RECORD *hpd_record; 784 ATOM_HPD_INT_RECORD *hpd_record;
783 ATOM_I2C_ID_CONFIG_ACCESS *i2c_config; 785 ATOM_I2C_ID_CONFIG_ACCESS *i2c_config;
784 786
785 while (record->ucRecordType > 0 787 while (record->ucRecordSize > 0 &&
786 && record-> 788 record->ucRecordType > 0 &&
787 ucRecordType <= 789 record->ucRecordType <= ATOM_MAX_OBJECT_RECORD_NUMBER) {
788 ATOM_MAX_OBJECT_RECORD_NUMBER) {
789 switch (record->ucRecordType) { 790 switch (record->ucRecordType) {
790 case ATOM_I2C_RECORD_TYPE: 791 case ATOM_I2C_RECORD_TYPE:
791 i2c_record = 792 i2c_record =
@@ -2175,24 +2176,27 @@ static void radeon_atombios_add_pplib_thermal_controller(struct radeon_device *r
2175 } 2176 }
2176} 2177}
2177 2178
2178static u16 radeon_atombios_get_default_vddc(struct radeon_device *rdev) 2179static void radeon_atombios_get_default_voltages(struct radeon_device *rdev,
2180 u16 *vddc, u16 *vddci)
2179{ 2181{
2180 struct radeon_mode_info *mode_info = &rdev->mode_info; 2182 struct radeon_mode_info *mode_info = &rdev->mode_info;
2181 int index = GetIndexIntoMasterTable(DATA, FirmwareInfo); 2183 int index = GetIndexIntoMasterTable(DATA, FirmwareInfo);
2182 u8 frev, crev; 2184 u8 frev, crev;
2183 u16 data_offset; 2185 u16 data_offset;
2184 union firmware_info *firmware_info; 2186 union firmware_info *firmware_info;
2185 u16 vddc = 0; 2187
2188 *vddc = 0;
2189 *vddci = 0;
2186 2190
2187 if (atom_parse_data_header(mode_info->atom_context, index, NULL, 2191 if (atom_parse_data_header(mode_info->atom_context, index, NULL,
2188 &frev, &crev, &data_offset)) { 2192 &frev, &crev, &data_offset)) {
2189 firmware_info = 2193 firmware_info =
2190 (union firmware_info *)(mode_info->atom_context->bios + 2194 (union firmware_info *)(mode_info->atom_context->bios +
2191 data_offset); 2195 data_offset);
2192 vddc = le16_to_cpu(firmware_info->info_14.usBootUpVDDCVoltage); 2196 *vddc = le16_to_cpu(firmware_info->info_14.usBootUpVDDCVoltage);
2197 if ((frev == 2) && (crev >= 2))
2198 *vddci = le16_to_cpu(firmware_info->info_22.usBootUpVDDCIVoltage);
2193 } 2199 }
2194
2195 return vddc;
2196} 2200}
2197 2201
2198static void radeon_atombios_parse_pplib_non_clock_info(struct radeon_device *rdev, 2202static void radeon_atombios_parse_pplib_non_clock_info(struct radeon_device *rdev,
@@ -2202,7 +2206,9 @@ static void radeon_atombios_parse_pplib_non_clock_info(struct radeon_device *rde
2202 int j; 2206 int j;
2203 u32 misc = le32_to_cpu(non_clock_info->ulCapsAndSettings); 2207 u32 misc = le32_to_cpu(non_clock_info->ulCapsAndSettings);
2204 u32 misc2 = le16_to_cpu(non_clock_info->usClassification); 2208 u32 misc2 = le16_to_cpu(non_clock_info->usClassification);
2205 u16 vddc = radeon_atombios_get_default_vddc(rdev); 2209 u16 vddc, vddci;
2210
2211 radeon_atombios_get_default_voltages(rdev, &vddc, &vddci);
2206 2212
2207 rdev->pm.power_state[state_index].misc = misc; 2213 rdev->pm.power_state[state_index].misc = misc;
2208 rdev->pm.power_state[state_index].misc2 = misc2; 2214 rdev->pm.power_state[state_index].misc2 = misc2;
@@ -2243,6 +2249,7 @@ static void radeon_atombios_parse_pplib_non_clock_info(struct radeon_device *rde
2243 rdev->pm.default_sclk = rdev->pm.power_state[state_index].clock_info[0].sclk; 2249 rdev->pm.default_sclk = rdev->pm.power_state[state_index].clock_info[0].sclk;
2244 rdev->pm.default_mclk = rdev->pm.power_state[state_index].clock_info[0].mclk; 2250 rdev->pm.default_mclk = rdev->pm.power_state[state_index].clock_info[0].mclk;
2245 rdev->pm.default_vddc = rdev->pm.power_state[state_index].clock_info[0].voltage.voltage; 2251 rdev->pm.default_vddc = rdev->pm.power_state[state_index].clock_info[0].voltage.voltage;
2252 rdev->pm.default_vddci = rdev->pm.power_state[state_index].clock_info[0].voltage.vddci;
2246 } else { 2253 } else {
2247 /* patch the table values with the default slck/mclk from firmware info */ 2254 /* patch the table values with the default slck/mclk from firmware info */
2248 for (j = 0; j < mode_index; j++) { 2255 for (j = 0; j < mode_index; j++) {
@@ -2285,6 +2292,8 @@ static bool radeon_atombios_parse_pplib_clock_info(struct radeon_device *rdev,
2285 VOLTAGE_SW; 2292 VOLTAGE_SW;
2286 rdev->pm.power_state[state_index].clock_info[mode_index].voltage.voltage = 2293 rdev->pm.power_state[state_index].clock_info[mode_index].voltage.voltage =
2287 le16_to_cpu(clock_info->evergreen.usVDDC); 2294 le16_to_cpu(clock_info->evergreen.usVDDC);
2295 rdev->pm.power_state[state_index].clock_info[mode_index].voltage.vddci =
2296 le16_to_cpu(clock_info->evergreen.usVDDCI);
2288 } else { 2297 } else {
2289 sclk = le16_to_cpu(clock_info->r600.usEngineClockLow); 2298 sclk = le16_to_cpu(clock_info->r600.usEngineClockLow);
2290 sclk |= clock_info->r600.ucEngineClockHigh << 16; 2299 sclk |= clock_info->r600.ucEngineClockHigh << 16;
@@ -2576,25 +2585,25 @@ union set_voltage {
2576 struct _SET_VOLTAGE_PARAMETERS_V2 v2; 2585 struct _SET_VOLTAGE_PARAMETERS_V2 v2;
2577}; 2586};
2578 2587
2579void radeon_atom_set_voltage(struct radeon_device *rdev, u16 level) 2588void radeon_atom_set_voltage(struct radeon_device *rdev, u16 voltage_level, u8 voltage_type)
2580{ 2589{
2581 union set_voltage args; 2590 union set_voltage args;
2582 int index = GetIndexIntoMasterTable(COMMAND, SetVoltage); 2591 int index = GetIndexIntoMasterTable(COMMAND, SetVoltage);
2583 u8 frev, crev, volt_index = level; 2592 u8 frev, crev, volt_index = voltage_level;
2584 2593
2585 if (!atom_parse_cmd_header(rdev->mode_info.atom_context, index, &frev, &crev)) 2594 if (!atom_parse_cmd_header(rdev->mode_info.atom_context, index, &frev, &crev))
2586 return; 2595 return;
2587 2596
2588 switch (crev) { 2597 switch (crev) {
2589 case 1: 2598 case 1:
2590 args.v1.ucVoltageType = SET_VOLTAGE_TYPE_ASIC_VDDC; 2599 args.v1.ucVoltageType = voltage_type;
2591 args.v1.ucVoltageMode = SET_ASIC_VOLTAGE_MODE_ALL_SOURCE; 2600 args.v1.ucVoltageMode = SET_ASIC_VOLTAGE_MODE_ALL_SOURCE;
2592 args.v1.ucVoltageIndex = volt_index; 2601 args.v1.ucVoltageIndex = volt_index;
2593 break; 2602 break;
2594 case 2: 2603 case 2:
2595 args.v2.ucVoltageType = SET_VOLTAGE_TYPE_ASIC_VDDC; 2604 args.v2.ucVoltageType = voltage_type;
2596 args.v2.ucVoltageMode = SET_ASIC_VOLTAGE_MODE_SET_VOLTAGE; 2605 args.v2.ucVoltageMode = SET_ASIC_VOLTAGE_MODE_SET_VOLTAGE;
2597 args.v2.usVoltageLevel = cpu_to_le16(level); 2606 args.v2.usVoltageLevel = cpu_to_le16(voltage_level);
2598 break; 2607 break;
2599 default: 2608 default:
2600 DRM_ERROR("Unknown table version %d, %d\n", frev, crev); 2609 DRM_ERROR("Unknown table version %d, %d\n", frev, crev);