mirror of
https://github.com/torvalds/linux.git
synced 2026-03-09 18:16:36 +01:00
drm/amd/display: Add concept of analog encoders (v2)
Add a num_analog_stream_encoders field to indicate how many analog stream encoders are present. When analog stream encoders are present, create them. Additionally, add an analog_engine field to link encoders and search for supported analog encoders in the BIOS for each link. When connecting an RGB signal, search for analog stream encoders. The actual DCE analog link and stream encoder is going to be added in a subsequent commit. v2: Add check to see if an analog engine is really supported. Signed-off-by: Timur Kristóf <timur.kristof@gmail.com> Reviewed-by: Harry Wentland <harry.wentland@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
This commit is contained in:
parent
c2192872d9
commit
5834c33fd3
5 changed files with 51 additions and 3 deletions
|
|
@ -446,6 +446,14 @@ bool resource_construct(
|
|||
DC_ERR("DC: failed to create stream_encoder!\n");
|
||||
pool->stream_enc_count++;
|
||||
}
|
||||
|
||||
for (i = 0; i < caps->num_analog_stream_encoder; i++) {
|
||||
pool->stream_enc[caps->num_stream_encoder + i] =
|
||||
create_funcs->create_stream_encoder(ENGINE_ID_DACA + i, ctx);
|
||||
if (pool->stream_enc[caps->num_stream_encoder + i] == NULL)
|
||||
DC_ERR("DC: failed to create analog stream_encoder %d!\n", i);
|
||||
pool->stream_enc_count++;
|
||||
}
|
||||
}
|
||||
|
||||
pool->hpo_dp_stream_enc_count = 0;
|
||||
|
|
|
|||
|
|
@ -47,6 +47,7 @@ struct encoder_init_data {
|
|||
enum hpd_source_id hpd_source;
|
||||
/* TODO: in DAL2, here was pointer to EventManagerInterface */
|
||||
struct graphics_object_id encoder;
|
||||
enum engine_id analog_engine;
|
||||
struct dc_context *ctx;
|
||||
enum transmitter transmitter;
|
||||
};
|
||||
|
|
@ -83,6 +84,7 @@ struct link_encoder {
|
|||
struct graphics_object_id connector;
|
||||
uint32_t output_signals;
|
||||
enum engine_id preferred_engine;
|
||||
enum engine_id analog_engine;
|
||||
struct encoder_feature_support features;
|
||||
enum transmitter transmitter;
|
||||
enum hpd_source_id hpd_source;
|
||||
|
|
|
|||
|
|
@ -49,6 +49,7 @@ struct resource_caps {
|
|||
int num_video_plane;
|
||||
int num_audio;
|
||||
int num_stream_encoder;
|
||||
int num_analog_stream_encoder;
|
||||
int num_pll;
|
||||
int num_dwb;
|
||||
int num_ddc;
|
||||
|
|
|
|||
|
|
@ -451,6 +451,32 @@ static enum channel_id get_ddc_line(struct dc_link *link)
|
|||
return channel;
|
||||
}
|
||||
|
||||
static enum engine_id find_analog_engine(struct dc_link *link)
|
||||
{
|
||||
struct dc_bios *bp = link->ctx->dc_bios;
|
||||
struct graphics_object_id encoder = {0};
|
||||
enum bp_result bp_result = BP_RESULT_OK;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < 3; i++) {
|
||||
bp_result = bp->funcs->get_src_obj(bp, link->link_id, i, &encoder);
|
||||
|
||||
if (bp_result != BP_RESULT_OK)
|
||||
return ENGINE_ID_UNKNOWN;
|
||||
|
||||
switch (encoder.id) {
|
||||
case ENCODER_ID_INTERNAL_DAC1:
|
||||
case ENCODER_ID_INTERNAL_KLDSCP_DAC1:
|
||||
return ENGINE_ID_DACA;
|
||||
case ENCODER_ID_INTERNAL_DAC2:
|
||||
case ENCODER_ID_INTERNAL_KLDSCP_DAC2:
|
||||
return ENGINE_ID_DACB;
|
||||
}
|
||||
}
|
||||
|
||||
return ENGINE_ID_UNKNOWN;
|
||||
}
|
||||
|
||||
static bool transmitter_supported(const enum transmitter transmitter)
|
||||
{
|
||||
return transmitter != TRANSMITTER_UNKNOWN &&
|
||||
|
|
@ -459,6 +485,12 @@ static bool transmitter_supported(const enum transmitter transmitter)
|
|||
transmitter != TRANSMITTER_TRAVIS_LCD;
|
||||
}
|
||||
|
||||
static bool analog_engine_supported(const enum engine_id engine_id)
|
||||
{
|
||||
return engine_id == ENGINE_ID_DACA ||
|
||||
engine_id == ENGINE_ID_DACB;
|
||||
}
|
||||
|
||||
static bool construct_phy(struct dc_link *link,
|
||||
const struct link_init_data *init_params)
|
||||
{
|
||||
|
|
@ -495,8 +527,10 @@ static bool construct_phy(struct dc_link *link,
|
|||
*/
|
||||
bp_funcs->get_src_obj(bios, link->link_id, 0, &enc_init_data.encoder);
|
||||
enc_init_data.transmitter = translate_encoder_to_transmitter(enc_init_data.encoder);
|
||||
enc_init_data.analog_engine = find_analog_engine(link);
|
||||
|
||||
if (!transmitter_supported(enc_init_data.transmitter)) {
|
||||
if (!transmitter_supported(enc_init_data.transmitter) &&
|
||||
!analog_engine_supported(enc_init_data.analog_engine)) {
|
||||
DC_LOG_WARNING("link_id %d has unsupported encoder\n", link->link_id.id);
|
||||
return false;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -954,6 +954,10 @@ struct stream_encoder *dce100_find_first_free_match_stream_enc_for_link(
|
|||
int i;
|
||||
int j = -1;
|
||||
struct dc_link *link = stream->link;
|
||||
enum engine_id preferred_engine = link->link_enc->preferred_engine;
|
||||
|
||||
if (dc_is_rgb_signal(stream->signal))
|
||||
preferred_engine = link->link_enc->analog_engine;
|
||||
|
||||
for (i = 0; i < pool->stream_enc_count; i++) {
|
||||
if (!res_ctx->is_stream_enc_acquired[i] &&
|
||||
|
|
@ -962,8 +966,7 @@ struct stream_encoder *dce100_find_first_free_match_stream_enc_for_link(
|
|||
* in daisy chain use case
|
||||
*/
|
||||
j = i;
|
||||
if (pool->stream_enc[i]->id ==
|
||||
link->link_enc->preferred_engine)
|
||||
if (pool->stream_enc[i]->id == preferred_engine)
|
||||
return pool->stream_enc[i];
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue