Begin work powering up the DisplayPort connector
* Add new struct to store DP connector information * DisplayPort Configuration Data is populated by setup function
This commit is contained in:
parent
18500e1cd6
commit
f2c3cbf779
@ -23,6 +23,7 @@
|
|||||||
#include "bios.h"
|
#include "bios.h"
|
||||||
#include "connector.h"
|
#include "connector.h"
|
||||||
#include "display.h"
|
#include "display.h"
|
||||||
|
#include "displayport.h"
|
||||||
#include "gpu.h"
|
#include "gpu.h"
|
||||||
#include "pll.h"
|
#include "pll.h"
|
||||||
#include "utility.h"
|
#include "utility.h"
|
||||||
@ -42,6 +43,7 @@ struct accelerant_info* gInfo;
|
|||||||
display_info* gDisplay[MAX_DISPLAY];
|
display_info* gDisplay[MAX_DISPLAY];
|
||||||
connector_info* gConnector[ATOM_MAX_SUPPORTED_DEVICE];
|
connector_info* gConnector[ATOM_MAX_SUPPORTED_DEVICE];
|
||||||
gpio_info* gGPIOInfo[ATOM_MAX_SUPPORTED_DEVICE];
|
gpio_info* gGPIOInfo[ATOM_MAX_SUPPORTED_DEVICE];
|
||||||
|
dp_info* gDPInfo[ATOM_MAX_SUPPORTED_DEVICE];
|
||||||
|
|
||||||
|
|
||||||
class AreaCloner {
|
class AreaCloner {
|
||||||
@ -140,6 +142,16 @@ init_common(int device, bool isClone)
|
|||||||
memset(gGPIOInfo[id], 0, sizeof(gpio_info));
|
memset(gGPIOInfo[id], 0, sizeof(gpio_info));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// malloc for card DP information
|
||||||
|
for (uint32 id = 0; id < ATOM_MAX_SUPPORTED_DEVICE; id++) {
|
||||||
|
gDPInfo[id] = (dp_info*)malloc(sizeof(dp_info));
|
||||||
|
|
||||||
|
if (gDPInfo[id] == NULL)
|
||||||
|
return B_NO_MEMORY;
|
||||||
|
memset(gDPInfo[id], 0, sizeof(dp_info));
|
||||||
|
gDPInfo[id]->valid = false;
|
||||||
|
}
|
||||||
|
|
||||||
gInfo->is_clone = isClone;
|
gInfo->is_clone = isClone;
|
||||||
gInfo->device = device;
|
gInfo->device = device;
|
||||||
|
|
||||||
@ -269,6 +281,9 @@ radeon_init_accelerant(int device)
|
|||||||
// print found connectors
|
// print found connectors
|
||||||
debug_connectors();
|
debug_connectors();
|
||||||
|
|
||||||
|
// setup link on any DisplayPort connectors
|
||||||
|
dp_setup_connectors();
|
||||||
|
|
||||||
// detect attached displays
|
// detect attached displays
|
||||||
status = detect_displays();
|
status = detect_displays();
|
||||||
//if (status != B_OK)
|
//if (status != B_OK)
|
||||||
|
@ -127,6 +127,17 @@ typedef struct {
|
|||||||
} gpio_info;
|
} gpio_info;
|
||||||
|
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
bool valid;
|
||||||
|
|
||||||
|
uint8 dpConfig[8]; // DP configuration data
|
||||||
|
uint8 dpSinkType;
|
||||||
|
uint8 dpClock;
|
||||||
|
int dpLaneCount;
|
||||||
|
bool eDPOn;
|
||||||
|
} dp_info;
|
||||||
|
|
||||||
|
|
||||||
struct encoder_info {
|
struct encoder_info {
|
||||||
bool valid;
|
bool valid;
|
||||||
uint16 objectID;
|
uint16 objectID;
|
||||||
@ -178,6 +189,7 @@ extern atom_context* gAtomContext;
|
|||||||
extern display_info* gDisplay[MAX_DISPLAY];
|
extern display_info* gDisplay[MAX_DISPLAY];
|
||||||
extern connector_info* gConnector[ATOM_MAX_SUPPORTED_DEVICE];
|
extern connector_info* gConnector[ATOM_MAX_SUPPORTED_DEVICE];
|
||||||
extern gpio_info* gGPIOInfo[ATOM_MAX_SUPPORTED_DEVICE];
|
extern gpio_info* gGPIOInfo[ATOM_MAX_SUPPORTED_DEVICE];
|
||||||
|
extern dp_info* gDPInfo[ATOM_MAX_SUPPORTED_DEVICE];
|
||||||
|
|
||||||
|
|
||||||
// register access
|
// register access
|
||||||
|
@ -160,6 +160,23 @@ dp_aux_read(uint32 hwPin, uint16 address,
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void
|
||||||
|
dpcd_reg_write(uint32 hwPin, uint16 address, uint8 value)
|
||||||
|
{
|
||||||
|
dp_aux_write(hwPin, address, &value, 1, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static uint8
|
||||||
|
dpcd_reg_read(uint32 hwPin, uint16 address)
|
||||||
|
{
|
||||||
|
uint8 value = 0;
|
||||||
|
dp_aux_read(hwPin, address, &value, 1, 0);
|
||||||
|
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
dp_aux_get_i2c_byte(uint32 hwPin, uint16 address, uint8* data, bool end)
|
dp_aux_get_i2c_byte(uint32 hwPin, uint16 address, uint8* data, bool end)
|
||||||
{
|
{
|
||||||
@ -316,24 +333,104 @@ dp_get_link_clock(uint32 connectorIndex)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
void
|
||||||
dp_link_train(uint32 connectorIndex)
|
dp_setup_connectors()
|
||||||
{
|
{
|
||||||
TRACE("%s\n", __func__);
|
TRACE("%s\n", __func__);
|
||||||
|
|
||||||
|
for (uint32 index = 0; index < ATOM_MAX_SUPPORTED_DEVICE; index++) {
|
||||||
|
gDPInfo[index]->valid = false;
|
||||||
|
if (gConnector[index]->valid == false) {
|
||||||
|
gDPInfo[index]->dpConfig[0] = 0;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (gConnector[index]->type != VIDEO_CONNECTOR_DP
|
||||||
|
&& gConnector[index]->type != VIDEO_CONNECTOR_EDP
|
||||||
|
&& gConnector[index]->encoder.isDPBridge == false) {
|
||||||
|
gDPInfo[index]->dpConfig[0] = 0;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint32 gpioID = gConnector[index]->gpioID;
|
||||||
|
uint32 hwPin = gGPIOInfo[gpioID]->hwPin;
|
||||||
|
|
||||||
|
uint8 auxMessage[25];
|
||||||
|
int result;
|
||||||
|
int i;
|
||||||
|
|
||||||
|
result = dp_aux_read(hwPin, DP_DPCD_REV, auxMessage, 8, 0);
|
||||||
|
if (result > 0) {
|
||||||
|
memcpy(gDPInfo[index]->dpConfig, auxMessage, 8);
|
||||||
|
TRACE("%s: connector #%" B_PRIu32 " DP Config:\n", __func__, index);
|
||||||
|
for (i = 0; i < 8; i++)
|
||||||
|
TRACE("%s: %02x\n", __func__, auxMessage[i]);
|
||||||
|
|
||||||
|
gDPInfo[index]->valid = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
dp_link_train(uint8 crtcID)
|
||||||
|
{
|
||||||
|
TRACE("%s\n", __func__);
|
||||||
|
|
||||||
|
uint32 connectorIndex = gDisplay[crtcID]->connectorIndex;
|
||||||
|
if (gDPInfo[connectorIndex]->valid != true) {
|
||||||
|
ERROR("%s: started on non-DisplayPort connector #%" B_PRIu32 "\n",
|
||||||
|
__func__, connectorIndex);
|
||||||
|
return B_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
int index = GetIndexIntoMasterTable(COMMAND, DPEncoderService);
|
int index = GetIndexIntoMasterTable(COMMAND, DPEncoderService);
|
||||||
// Table version
|
// Table version
|
||||||
uint8 tableMajor;
|
uint8 tableMajor;
|
||||||
uint8 tableMinor;
|
uint8 tableMinor;
|
||||||
|
|
||||||
bool useDpencoder = true; // ??
|
bool dpUseEncoder = true;
|
||||||
if (atom_parse_cmd_header(gAtomContext, index, &tableMajor, &tableMinor)
|
if (atom_parse_cmd_header(gAtomContext, index, &tableMajor, &tableMinor)
|
||||||
== B_OK) {
|
== B_OK) {
|
||||||
if (tableMinor > 1) {
|
if (tableMinor > 1) {
|
||||||
useDpencoder = false;
|
// The AtomBIOS DPEncoderService greater then 1.1 can't program the
|
||||||
|
// training pattern properly.
|
||||||
|
dpUseEncoder = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: perform displayport training
|
uint32 linkEnumeration
|
||||||
return B_ERROR;
|
= gConnector[connectorIndex]->encoder.linkEnumeration;
|
||||||
|
uint32 gpioID = gConnector[connectorIndex]->gpioID;
|
||||||
|
uint32 hwPin = gGPIOInfo[gpioID]->hwPin;
|
||||||
|
|
||||||
|
uint32 dpEncoderID = 0;
|
||||||
|
if (encoder_pick_dig(crtcID) > 0)
|
||||||
|
dpEncoderID |= ATOM_DP_CONFIG_DIG2_ENCODER;
|
||||||
|
else
|
||||||
|
dpEncoderID |= ATOM_DP_CONFIG_DIG1_ENCODER;
|
||||||
|
if (linkEnumeration == GRAPH_OBJECT_ENUM_ID2)
|
||||||
|
dpEncoderID |= ATOM_DP_CONFIG_LINK_B;
|
||||||
|
else
|
||||||
|
dpEncoderID |= ATOM_DP_CONFIG_LINK_A;
|
||||||
|
|
||||||
|
//uint8 dpReadInterval = dpcd_reg_read(hwPin, DP_TRAINING_AUX_RD_INTERVAL);
|
||||||
|
uint8 dpMaxLanes = dpcd_reg_read(hwPin, DP_MAX_LANE_COUNT);
|
||||||
|
|
||||||
|
radeon_shared_info &info = *gInfo->shared_info;
|
||||||
|
bool dpTPS3Supported = false;
|
||||||
|
if (info.dceMajor >= 5 && (dpMaxLanes & DP_TPS3_SUPPORTED) != 0)
|
||||||
|
dpTPS3Supported = true;
|
||||||
|
|
||||||
|
// power up the DP sink
|
||||||
|
if (gDPInfo[connectorIndex]->dpConfig[0] >= 0x11)
|
||||||
|
dpcd_reg_write(hwPin, DP_SET_POWER, DP_SET_POWER_D0);
|
||||||
|
|
||||||
|
// possibly enable downspread on the sink
|
||||||
|
if (gDPInfo[connectorIndex]->dpConfig[3] & 0x1)
|
||||||
|
dpcd_reg_write(hwPin, DP_DOWNSPREAD_CTRL, DP_SPREAD_AMP_0_5);
|
||||||
|
else
|
||||||
|
dpcd_reg_write(hwPin, DP_DOWNSPREAD_CTRL, 0);
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
@ -23,6 +23,7 @@ status_t dp_aux_get_i2c_byte(uint32 hwPin, uint16 address,
|
|||||||
uint8* data, bool end);
|
uint8* data, bool end);
|
||||||
|
|
||||||
uint32 dp_get_link_clock(uint32 connectorIndex);
|
uint32 dp_get_link_clock(uint32 connectorIndex);
|
||||||
|
void dp_setup_connectors();
|
||||||
status_t dp_link_train(uint32 connectorIndex);
|
status_t dp_link_train(uint32 connectorIndex);
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user