radeon_hd: Drop dp config array from dp_info

* Caching these values could result in missed
  state changes.
* We may want to re-implement later.
* Highlights that all DP AUX communication is broken
  during my testing.
This commit is contained in:
Alexander von Gluck IV
2017-09-29 11:10:56 -05:00
parent 8856b51897
commit 2da9ebb7f3
4 changed files with 30 additions and 73 deletions
+1 -5
View File
@@ -19,10 +19,9 @@ typedef struct {
// Required configuration // Required configuration
bool valid; // Is valid DP information bool valid; // Is valid DP information
uint32 auxPin; // Normally GPIO pin on GPU uint32 auxPin; // Normally GPIO pin on GPU
uint8 revision; // DP Revision from DPCD
uint8 config[DP_DPCD_SIZE]; // DP Configuration Data
int laneCount; int laneCount;
uint32 linkRate; // DP Link Speed 162000, 270000, 540000 uint32 linkRate; // DP Link Speed 162000, 270000, 540000
// Internal State information // Internal State information
@@ -45,9 +44,6 @@ typedef struct {
uint32 dp_encode_link_rate(uint32 linkRate); uint32 dp_encode_link_rate(uint32 linkRate);
uint32 dp_decode_link_rate(uint32 rawLinkRate); uint32 dp_decode_link_rate(uint32 rawLinkRate);
uint32 dp_get_lane_count_max(dp_info* dpInfo);
uint32 dp_get_link_rate_max(dp_info* dpInfo);
uint32 dp_get_pixel_clock_max(int linkRate, int laneCount, int bpp); uint32 dp_get_pixel_clock_max(int linkRate, int laneCount, int bpp);
+1
View File
@@ -42,6 +42,7 @@
#define DP_DPCD_REV_MAJOR_MASK (15 << 4) // Int #define DP_DPCD_REV_MAJOR_MASK (15 << 4) // Int
#define DP_DPCD_REV_10 0x0010 // Value #define DP_DPCD_REV_10 0x0010 // Value
#define DP_DPCD_REV_11 0x0011 // Value #define DP_DPCD_REV_11 0x0011 // Value
#define DP_DPCD_REV_12 0x0012 // Value
// DP Maximum Link Rate (0x1) // DP Maximum Link Rate (0x1)
#define DP_MAX_LINK_RATE 0x0001 // Reg #define DP_MAX_LINK_RATE 0x0001 // Reg
// Use DP_LINK_RATE_* for speed. // Use DP_LINK_RATE_* for speed.
-14
View File
@@ -64,17 +64,3 @@ dp_get_pixel_clock_max(int linkRate, int laneCount, int bpp)
{ {
return (linkRate * laneCount * 8) / bpp; return (linkRate * laneCount * 8) / bpp;
} }
uint32
dp_get_link_rate_max(dp_info* dpInfo)
{
return dp_decode_link_rate(dpInfo->config[DP_MAX_LINK_RATE]);
}
uint32
dp_get_lane_count_max(dp_info* dpInfo)
{
return dpInfo->config[DP_MAX_LANE_COUNT] & DP_MAX_LANE_COUNT_MASK;
}
@@ -353,9 +353,6 @@ dp_get_encoder_config(uint32 connectorIndex)
uint32 uint32
dp_get_lane_count(uint32 connectorIndex, display_mode* mode) dp_get_lane_count(uint32 connectorIndex, display_mode* mode)
{ {
// Radeon specific
dp_info* dpInfo = &gConnector[connectorIndex]->dpInfo;
size_t pixelChunk; size_t pixelChunk;
size_t pixelsPerChunk; size_t pixelsPerChunk;
status_t result = dp_get_pixel_size_for((color_space)mode->space, status_t result = dp_get_pixel_size_for((color_space)mode->space,
@@ -368,8 +365,10 @@ dp_get_lane_count(uint32 connectorIndex, display_mode* mode)
uint32 bitsPerPixel = (pixelChunk / pixelsPerChunk) * 8; uint32 bitsPerPixel = (pixelChunk / pixelsPerChunk) * 8;
uint32 dpMaxLinkRate = dp_get_link_rate_max(dpInfo); uint32 dpMaxLinkRate
uint32 dpMaxLaneCount = dp_get_lane_count_max(dpInfo); = dp_decode_link_rate(dpcd_reg_read(connectorIndex, DP_MAX_LINK_RATE));
uint32 dpMaxLaneCount = dpcd_reg_read(connectorIndex,
DP_MAX_LANE_COUNT) & DP_MAX_LANE_COUNT_MASK;
uint32 lane; uint32 lane;
// don't go below 2 lanes or display is jittery // don't go below 2 lanes or display is jittery
@@ -393,9 +392,6 @@ dp_get_link_rate(uint32 connectorIndex, display_mode* mode)
if (encoderID == ENCODER_OBJECT_ID_NUTMEG) if (encoderID == ENCODER_OBJECT_ID_NUTMEG)
return 270000; return 270000;
dp_info* dpInfo = &gConnector[connectorIndex]->dpInfo;
uint32 laneCount = dp_get_lane_count(connectorIndex, mode);
size_t pixelChunk; size_t pixelChunk;
size_t pixelsPerChunk; size_t pixelsPerChunk;
status_t result = dp_get_pixel_size_for((color_space)mode->space, status_t result = dp_get_pixel_size_for((color_space)mode->space,
@@ -407,6 +403,7 @@ dp_get_link_rate(uint32 connectorIndex, display_mode* mode)
} }
uint32 bitsPerPixel = (pixelChunk / pixelsPerChunk) * 8; uint32 bitsPerPixel = (pixelChunk / pixelsPerChunk) * 8;
uint32 laneCount = dp_get_lane_count(connectorIndex, mode);
uint32 maxPixelClock uint32 maxPixelClock
= dp_get_pixel_clock_max(162000, laneCount, bitsPerPixel); = dp_get_pixel_clock_max(162000, laneCount, bitsPerPixel);
@@ -426,7 +423,7 @@ dp_get_link_rate(uint32 connectorIndex, display_mode* mode)
} }
#endif #endif
return dp_get_link_rate_max(dpInfo); return dp_decode_link_rate(dpcd_reg_read(connectorIndex, DP_MAX_LINK_RATE));
} }
@@ -464,46 +461,18 @@ dp_setup_connectors()
for (uint32 index = 0; index < ATOM_MAX_SUPPORTED_DEVICE; index++) { for (uint32 index = 0; index < ATOM_MAX_SUPPORTED_DEVICE; index++) {
dp_info* dpInfo = &gConnector[index]->dpInfo; dp_info* dpInfo = &gConnector[index]->dpInfo;
dpInfo->valid = false; // Validate connector is actually display port
if (gConnector[index]->valid == false if (gConnector[index]->valid == false
|| connector_is_dp(index) == false) { || connector_is_dp(index) == false) {
dpInfo->config[0] = 0; dpInfo->valid = false;
continue; continue;
} }
TRACE("%s: found dp connector on index %" B_PRIu32 "\n", // Configure communication pins.
__func__, index);
uint32 i2cPinIndex = gConnector[index]->i2cPinIndex; uint32 i2cPinIndex = gConnector[index]->i2cPinIndex;
uint32 auxPin = gGPIOInfo[i2cPinIndex]->hwPin; uint32 auxPin = gGPIOInfo[i2cPinIndex]->hwPin;
dpInfo->auxPin = auxPin; dpInfo->auxPin = auxPin;
dpInfo->valid = true;
dp_aux_msg message;
memset(&message, 0, sizeof(message));
message.address = DP_DPCD_REV;
message.request = DP_AUX_NATIVE_READ;
// TODO: validate
message.size = DP_DPCD_SIZE;
message.buffer = dpInfo->config;
status_t result = dp_aux_transaction(index, &message);
if (result == B_OK) {
dpInfo->valid = true;
TRACE("%s: connector(%" B_PRIu32 "): successful read of DPCD\n",
__func__, index);
} else {
TRACE("%s: connector(%" B_PRIu32 "): failed read of DPCD\n",
__func__, index);
}
/*
TRACE("%s: DPCD is ", __func__);
uint32 position;
for (position = 0; position < message.size; position++)
_sPrintf("%02x ", message.buffer + position);
_sPrintf("\n");
*/
} }
} }
@@ -858,6 +827,7 @@ dp_link_train(uint8 crtcID)
return B_ERROR; return B_ERROR;
} }
dp->revision = dpcd_reg_read(connectorIndex, DP_DPCD_REV);
dp->trainingReadInterval dp->trainingReadInterval
= dpcd_reg_read(connectorIndex, DP_TRAINING_AUX_RD_INTERVAL); = dpcd_reg_read(connectorIndex, DP_TRAINING_AUX_RD_INTERVAL);
@@ -871,11 +841,11 @@ dp_link_train(uint8 crtcID)
// *** DisplayPort link training initialization // *** DisplayPort link training initialization
// Power up the DP sink // Power up the DP sink
if (dp->config[0] >= DP_DPCD_REV_11) if (dp->revision >= DP_DPCD_REV_11)
dpcd_reg_write(connectorIndex, DP_SET_POWER, DP_SET_POWER_D0); dpcd_reg_write(connectorIndex, DP_SET_POWER, DP_SET_POWER_D0);
// Possibly enable downspread on the sink // Possibly enable downspread on the sink
if ((dp->config[3] & 0x1) != 0) { if ((dpcd_reg_read(connectorIndex, DP_MAX_DOWNSPREAD) & 0x1) != 0) {
dpcd_reg_write(connectorIndex, DP_DOWNSPREAD_CTRL, dpcd_reg_write(connectorIndex, DP_DOWNSPREAD_CTRL,
DP_DOWNSPREAD_CTRL_AMP_EN); DP_DOWNSPREAD_CTRL_AMP_EN);
} else } else
@@ -884,11 +854,13 @@ dp_link_train(uint8 crtcID)
encoder_dig_setup(connectorIndex, mode->timing.pixel_clock, encoder_dig_setup(connectorIndex, mode->timing.pixel_clock,
ATOM_ENCODER_CMD_SETUP_PANEL_MODE); ATOM_ENCODER_CMD_SETUP_PANEL_MODE);
// TODO: Doesn't this overwrite important dpcd info? // Enable enhanced frame if supported
sandbox = dp->laneCount; sandbox = dpcd_reg_read(connectorIndex, DP_LANE_COUNT);
if ((dp->config[0] >= DP_DPCD_REV_11) if (dp->revision >= DP_DPCD_REV_11
&& (dp->config[2] & DP_ENHANCED_FRAME_CAP_EN)) && (dpcd_reg_read(connectorIndex, DP_MAX_LANE_COUNT)
& DP_ENHANCED_FRAME_CAP_EN)) {
sandbox |= DP_ENHANCED_FRAME_EN; sandbox |= DP_ENHANCED_FRAME_EN;
}
dpcd_reg_write(connectorIndex, DP_LANE_COUNT, sandbox); dpcd_reg_write(connectorIndex, DP_LANE_COUNT, sandbox);
// Set the link rate on the DP sink // Set the link rate on the DP sink
@@ -1012,6 +984,8 @@ dp_is_dp12_capable(uint32 connectorIndex)
uint32 capabilities = gConnector[connectorIndex]->encoder.capabilities; uint32 capabilities = gConnector[connectorIndex]->encoder.capabilities;
// DP_DPCD_REV_12 as well?
if (info.dceMajor >= 5 if (info.dceMajor >= 5
&& gInfo->dpExternalClock >= 539000 && gInfo->dpExternalClock >= 539000
&& (capabilities & ATOM_ENCODER_CAP_RECORD_HBR2) != 0) { && (capabilities & ATOM_ENCODER_CAP_RECORD_HBR2) != 0) {
@@ -1036,17 +1010,17 @@ debug_dp_info()
continue; continue;
ERROR(" + DP Config Data\n"); ERROR(" + DP Config Data\n");
ERROR(" - max lane count: %d\n", ERROR(" - max lane count: %d\n",
dp->config[DP_MAX_LANE_COUNT] & DP_MAX_LANE_COUNT_MASK); dpcd_reg_read(id, DP_MAX_LANE_COUNT) & DP_MAX_LANE_COUNT_MASK);
ERROR(" - max link rate: %d\n", ERROR(" - max link rate: %d\n",
dp->config[DP_MAX_LINK_RATE]); dpcd_reg_read(id, DP_MAX_LINK_RATE));
ERROR(" - receiver port count: %d\n", ERROR(" - receiver port count: %d\n",
dp->config[DP_NORP] & DP_NORP_MASK); dpcd_reg_read(id, DP_NORP) & DP_NORP_MASK);
ERROR(" - downstream port present: %s\n", ERROR(" - downstream port present: %s\n",
(dp->config[DP_DOWNSTREAMPORT] & DP_DOWNSTREAMPORT_EN) dpcd_reg_read(id, DP_DOWNSTREAMPORT) & DP_DOWNSTREAMPORT_EN
? "yes" : "no"); ? "yes" : "no");
ERROR(" - downstream port count: %d\n", ERROR(" - downstream port count: %d\n",
dp->config[DP_DOWNSTREAMPORT_COUNT] dpcd_reg_read(id, DP_DOWNSTREAMPORT_COUNT)
& DP_DOWNSTREAMPORT_COUNT_MASK); & DP_DOWNSTREAMPORT_COUNT_MASK);
ERROR(" + Training\n"); ERROR(" + Training\n");
ERROR(" - attempts: %" B_PRIu8 "\n", ERROR(" - attempts: %" B_PRIu8 "\n",
dp->trainingAttempts); dp->trainingAttempts);