diff options
author | Harry Wentland <harry.wentland@amd.com> | 2015-07-31 15:17:37 -0400 |
---|---|---|
committer | Alex Deucher <alexander.deucher@amd.com> | 2015-09-21 17:45:13 -0400 |
commit | 5d15c508cd657f036f8f44facd24532271fcb90b (patch) | |
tree | 5c42afc171c3f476653e0ab87df9dffa305fa2ed | |
parent | bcd3147acedf04dfcf2f2fa9a2f63d3406dd11e1 (diff) |
amd/dal: Adapter Service
Provides information about ASIC features and capabilities. Also provides
access to ASIC resources such as VBIOS, GPIO and I2cAux Manager
SW Layer
/===============================================================\
| Asic |
| Capability |
| |
| Adapter |
| Service |
| |
|---------------------------------------------------------------|
| GPIO |
| |
| |
| |
\===============================================================/
HW Layer
Signed-off-by: Harry Wentland <harry.wentland@amd.com>
17 files changed, 5695 insertions, 1 deletions
diff --git a/drivers/gpu/drm/amd/dal/Makefile b/drivers/gpu/drm/amd/dal/Makefile index 09f96a6422ca..8b38527ddda9 100644 --- a/drivers/gpu/drm/amd/dal/Makefile +++ b/drivers/gpu/drm/amd/dal/Makefile @@ -7,7 +7,7 @@ AMDDALPATH = $(RELATIVE_AMD_DAL_PATH) subdir-ccflags-y += -I$(AMDDALPATH)/ -I$(AMDDALPATH)/include -DDAL_CZ_BRINGUP -DAL_LIBS = amdgpu_dm asic_capability basics gpio +DAL_LIBS = amdgpu_dm adapter asic_capability basics gpio AMD_DAL = $(addsuffix /Makefile, $(addprefix $(FULL_AMD_DAL_PATH)/,$(DAL_LIBS))) diff --git a/drivers/gpu/drm/amd/dal/adapter/Makefile b/drivers/gpu/drm/amd/dal/adapter/Makefile new file mode 100644 index 000000000000..2be2f00a3409 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/Makefile @@ -0,0 +1,17 @@ +# +# Makefile for the 'adapter' sub-component of DAL. +# It provides the control and status of HW adapter. + +ADAPTER = adapter_service.o hw_ctx_adapter_service.o wireless_data_source.o + +AMD_DAL_ADAPTER = $(addprefix $(AMDDALPATH)/adapter/,$(ADAPTER)) + +AMD_DAL_FILES += $(AMD_DAL_ADAPTER) + +############################################################################### +# DCE 11x +############################################################################### + +ifdef CONFIG_DRM_AMD_DAL_DCE11_0 +AMD_DAL_FILES += $(AMDDALPATH)/adapter/dce110/hw_ctx_adapter_service_dce110.o +endif diff --git a/drivers/gpu/drm/amd/dal/adapter/adapter_service.c b/drivers/gpu/drm/amd/dal/adapter/adapter_service.c new file mode 100644 index 000000000000..54ac5b33d4c3 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/adapter_service.c @@ -0,0 +1,2032 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + + +#include "dal_services.h" + +#include "include/adapter_service_interface.h" +#include "include/i2caux_interface.h" +#include "include/asic_capability_types.h" +#include "include/bios_parser_interface.h" +#include "include/gpio_service_interface.h" +#include "include/asic_capability_interface.h" +#include "include/logger_interface.h" + +#include "adapter_service.h" +#include "hw_ctx_adapter_service.h" +#include "atom.h" +#include "wireless_data_source.h" + +#if defined(CONFIG_DRM_AMD_DAL_DCE11_0) +#include "dce110/hw_ctx_adapter_service_dce110.h" +#endif + +/* + * Adapter service feature entry table. + * + * This is an array of features that is used to generate feature set. Each + * entry consists three element: + * + * Feature name, default value, and if this feature is a boolean type. A + * feature can only be a boolean or int type. + * + * Example 1: a boolean type feature + * FEATURE_ENABLE_HW_EDID_POLLING, false, true + * + * First element is feature name: EATURE_ENABLE_HW_EDID_POLLING, it has a + * default value 0, and it is a boolean feature. + * + * Example 2: an int type feature + * FEATURE_DCP_PROGRAMMING_WA, 0x1FF7, false + * + * In this case, the default value is 0x1FF7 and not a boolean type, which + * makes it an int type. + */ + +static +#if !defined(DAL_CZ_BRINGUP) +const +#endif +struct feature_source_entry feature_entry_table[] = { + /* Feature name | default value | is boolean type */ + {FEATURE_ENABLE_HW_EDID_POLLING, false, true}, + {FEATURE_DP_SINK_DETECT_POLL_DATA_PIN, false, true}, + {FEATURE_UNDERFLOW_INTERRUPT, false, true}, + {FEATURE_ALLOW_WATERMARK_ADJUSTMENT, false, true}, + {FEATURE_LIGHT_SLEEP, false, true}, + {FEATURE_DCP_DITHER_FRAME_RANDOM_ENABLE, false, true}, + {FEATURE_DCP_DITHER_RGB_RANDOM_ENABLE, false, true}, + {FEATURE_DCP_DITHER_HIGH_PASS_RANDOM_ENABLE, false, true}, + {FEATURE_LINE_BUFFER_ENHANCED_PIXEL_DEPTH, false, true}, + {FEATURE_MAXIMIZE_URGENCY_WATERMARKS, false, true}, + {FEATURE_MAXIMIZE_STUTTER_MARKS, false, true}, + {FEATURE_MAXIMIZE_NBP_MARKS, false, true}, + /* + * We meet HW I2C issue when test S3 resume on KB. + * An EPR is created for debug the issue. + * Make Test has already been implemented + * with HW I2C. The work load for revert back to SW I2C in make test + * is big. Below is workaround for this issue. + * Driver uses SW I2C. + * Make Test uses HW I2C. + */ +#if defined(DAL_CZ_BRINGUP) + {FEATURE_RESTORE_USAGE_I2C_SW_ENGINE, true, true}, +#else + {FEATURE_RESTORE_USAGE_I2C_SW_ENGINE, false, true}, +#endif + {FEATURE_USE_MAX_DISPLAY_CLK, false, true}, + {FEATURE_ALLOW_EDP_RESOURCE_SHARING, false, true}, + {FEATURE_SUPPORT_DP_YUV, false, true}, + {FEATURE_SUPPORT_DP_Y_ONLY, false, true}, + {FEATURE_DISABLE_DP_GTC_SYNC, true, true}, + {FEATURE_MODIFY_TIMINGS_FOR_WIRELESS, false, true}, + {FEATURE_DCP_BIT_DEPTH_REDUCTION_MODE, 0, false}, + {FEATURE_DCP_DITHER_MODE, 0, false}, + {FEATURE_DCP_PROGRAMMING_WA, 0, false}, + {FEATURE_NO_HPD_LOW_POLLING_VCC_OFF, false, true}, + {FEATURE_ENABLE_DFS_BYPASS, false, true}, + {FEATURE_WIRELESS_FULL_TIMING_ADJUSTMENT, false, true}, + {FEATURE_MAX_COFUNC_NON_DP_DISPLAYS, 2, false}, + {FEATURE_WIRELESS_LIMIT_720P, false, true}, + {FEATURE_MODIFY_TIMINGS_FOR_WIRELESS, false, true}, + {FEATURE_SUPPORTED_HDMI_CONNECTION_NUM, 0, false}, + {FEATURE_DETECT_REQUIRE_HPD_HIGH, false, true}, + {FEATURE_NO_HPD_LOW_POLLING_VCC_OFF, false, true}, + {FEATURE_LB_HIGH_RESOLUTION, false, true}, + {FEATURE_MAX_CONTROLLER_NUM, 0, false}, + {FEATURE_DRR_SUPPORT, AS_DRR_SUPPORT_ENABLED, false}, + {FEATURE_STUTTER_MODE, 15, false}, + {FEATURE_DP_DISPLAY_FORCE_SS_ENABLE, false, true}, + {FEATURE_REPORT_CE_MODE_ONLY, false, true}, + {FEATURE_ALLOW_OPTIMIZED_MODE_AS_DEFAULT, false, true}, + {FEATURE_DDC_READ_FORCE_REPEATED_START, false, true}, + {FEATURE_FORCE_TIMING_RESYNC, false, true}, + {FEATURE_TMDS_DISABLE_DITHERING, false, true}, + {FEATURE_HDMI_DISABLE_DITHERING, false, true}, + {FEATURE_DP_DISABLE_DITHERING, false, true}, + {FEATURE_EMBEDDED_DISABLE_DITHERING, true, true}, + {FEATURE_ALLOW_SELF_REFRESH, false, true}, + {FEATURE_ALLOW_DYNAMIC_PIXEL_ENCODING_CHANGE, false, true}, + {FEATURE_ALLOW_HSYNC_VSYNC_ADJUSTMENT, false, true}, + {FEATURE_FORCE_PSR, false, true}, + {FEATURE_PSR_SETUP_TIME_TEST, 0, false}, + {FEATURE_POWER_GATING_PIPE_IN_TILE, true, true}, + {FEATURE_POWER_GATING_LB_PORTION, true, true}, + {FEATURE_PREFER_3D_TIMING, false, true}, + {FEATURE_VARI_BRIGHT_ENABLE, true, true}, + {FEATURE_PSR_ENABLE, false, true}, + {FEATURE_WIRELESS_ENABLE_COMPRESSED_AUDIO, false, true}, + {FEATURE_WIRELESS_INCLUDE_UNVERIFIED_TIMINGS, true, true}, + {FEATURE_EDID_STRESS_READ, false, true}, + {FEATURE_DP_FRAME_PACK_STEREO3D, false, true}, + {FEATURE_DISPLAY_PREFERRED_VIEW, 0, false}, + {FEATURE_ALLOW_HDMI_WITHOUT_AUDIO, false, true}, + {FEATURE_ABM_2_0, false, true}, + {FEATURE_SUPPORT_MIRABILIS, false, true}, + {FEATURE_OPTIMIZATION, 0xFFFF, false}, + {FEATURE_PERF_MEASURE, 0, false}, + {FEATURE_MIN_BACKLIGHT_LEVEL, 0, false}, + {FEATURE_MAX_BACKLIGHT_LEVEL, 255, false}, + {FEATURE_LOAD_DMCU_FIRMWARE, true, true}, + {FEATURE_DISABLE_AZ_CLOCK_GATING, false, true}, + {FEATURE_ENABLE_GPU_SCALING, false, true}, + {FEATURE_DONGLE_SINK_COUNT_CHECK, true, true}, + {FEATURE_INSTANT_UP_SCALE_DOWN_SCALE, false, true}, + {FEATURE_TILED_DISPLAY, false, true}, + {FEATURE_PREFERRED_ABM_CONFIG_SET, 0, false}, + {FEATURE_CHANGE_SW_I2C_SPEED, 50, false}, + {FEATURE_CHANGE_HW_I2C_SPEED, 50, false}, + {FEATURE_CHANGE_I2C_SPEED_CONTROL, false, true}, + {FEATURE_DEFAULT_PSR_LEVEL, 0, false}, + {FEATURE_MAX_CLOCK_SOURCE_NUM, 0, false}, + {FEATURE_REPORT_SINGLE_SELECTED_TIMING, false, true}, + {FEATURE_ALLOW_HDMI_HIGH_CLK_DP_DONGLE, true, true}, + {FEATURE_SUPPORT_EXTERNAL_PANEL_DRR, false, true}, + {FEATURE_LVDS_SAFE_PIXEL_CLOCK_RANGE, 0, false}, + {FEATURE_ABM_CONFIG, 0, false}, + {FEATURE_WIRELESS_ENABLE, false, true}, + {FEATURE_ALLOW_DIRECT_MEMORY_ACCESS_TRIG, false, true}, + {FEATURE_FORCE_STATIC_SCREEN_EVENT_TRIGGERS, 0, false}, + {FEATURE_USE_PPLIB, true, true}, + {FEATURE_DISABLE_LPT_SUPPORT, false, true}, + {FEATURE_DUMMY_FBC_BACKEND, false, true}, + {FEATURE_DPMS_AUDIO_ENDPOINT_CONTROL, true, true}, + {FEATURE_DISABLE_FBC_COMP_CLK_GATE, false, true}, + {FEATURE_PIXEL_PERFECT_OUTPUT, false, true}, + {FEATURE_8BPP_SUPPORTED, false, true} +}; + + +/* Stores entire ASIC features by sets */ +uint32_t adapter_feature_set[FEATURE_MAXIMUM/32]; + +enum { + LEGACY_MAX_NUM_OF_CONTROLLERS = 2, + DEFAULT_NUM_COFUNC_NON_DP_DISPLAYS = 2 +}; + +/* + * get_feature_entries_num + * + * Get number of feature entries + */ +static inline uint32_t get_feature_entries_num(void) +{ + return ARRAY_SIZE(feature_entry_table); +} + +static void get_platform_info_methods( + struct adapter_service *as) +{ + struct platform_info_params params; + uint32_t mask = 0; + + params.data = &mask; + params.method = PM_GET_AVAILABLE_METHODS; + + if (dal_get_platform_info(as->dal_context, ¶ms)) + as->platform_methods_mask = mask; + + +} + +static void initialize_backlight_caps( + struct adapter_service *as) +{ + struct firmware_info fw_info; + struct embedded_panel_info panel_info; + struct platform_info_ext_brightness_caps caps; + struct platform_info_params params; + bool custom_curve_present = false; + bool custom_min_max_present = false; + + if (!(PM_GET_EXTENDED_BRIGHNESS_CAPS & as->platform_methods_mask)) { + dal_logger_write(as->dal_context->logger, + LOG_MAJOR_BACKLIGHT, + LOG_MINOR_BACKLIGHT_BRIGHTESS_CAPS, + "This method is not support\n"); + return; + } + + if (dal_bios_parser_get_firmware_info + (as->bios_parser, &fw_info) != BP_RESULT_OK || + dal_bios_parser_get_embedded_panel_info + (as->bios_parser, &panel_info) != BP_RESULT_OK) + return; + + params.data = ∩︀ + params.method = PM_GET_EXTENDED_BRIGHNESS_CAPS; + + if (dal_get_platform_info(as->dal_context, ¶ms)) { + as->ac_level_percentage = caps.basic_caps.ac_level_percentage; + as->dc_level_percentage = caps.basic_caps.dc_level_percentage; + custom_curve_present = (caps.data_points_num > 0); + custom_min_max_present = true; + } else + return; + /* Choose minimum backlight level base on priority: + * extended caps,VBIOS,default */ + if (custom_min_max_present) + as->backlight_8bit_lut[0] = caps.min_input_signal; + + else if (fw_info.min_allowed_bl_level > 0) + as->backlight_8bit_lut[0] = fw_info.min_allowed_bl_level; + + else + as->backlight_8bit_lut[0] = DEFAULT_MIN_BACKLIGHT; + + /* Choose maximum backlight level base on priority: + * extended caps,default */ + if (custom_min_max_present) + as->backlight_8bit_lut[100] = caps.max_input_signal; + + else + as->backlight_8bit_lut[100] = DEFAULT_MAX_BACKLIGHT; + + if (as->backlight_8bit_lut[100] > ABSOLUTE_BACKLIGHT_MAX) + as->backlight_8bit_lut[100] = ABSOLUTE_BACKLIGHT_MAX; + + if (as->backlight_8bit_lut[0] > as->backlight_8bit_lut[100]) + as->backlight_8bit_lut[0] = as->backlight_8bit_lut[100]; + + if (custom_curve_present) { + uint16_t index = 1; + uint16_t i; + uint16_t num_of_data_points = (caps.data_points_num <= 99 ? + caps.data_points_num : 99); + /* Filling translation table from data points - + * between every two provided data points we + * lineary interpolate missing values + */ + for (i = 0 ; i < num_of_data_points; i++) { + uint16_t luminance = caps.data_points[i].luminance; + uint16_t signal_level = + caps.data_points[i].signal_level; + + if (signal_level < as->backlight_8bit_lut[0]) + signal_level = as->backlight_8bit_lut[0]; + + if (signal_level > as->backlight_8bit_lut[100]) + signal_level = as->backlight_8bit_lut[100]; + + /* Lineary interpolate missing values */ + if (index < luminance) { + uint16_t base_value = + as->backlight_8bit_lut[index-1]; + uint16_t delta_signal = + signal_level - base_value; + uint16_t delta_luma = luminance - index + 1; + uint16_t step = delta_signal; + + for (; index < luminance ; index++) { + as->backlight_8bit_lut[index] = + base_value + + (step / delta_luma); + step += delta_signal; + } + } + /* Now [index == luminance], so we can add + * data point to the translation table */ + as->backlight_8bit_lut[index++] = signal_level; + } + /* Complete the final segment of interpolation - + * between last datapoint and maximum value */ + if (index < 100) { + uint16_t base_value = as->backlight_8bit_lut[index-1]; + uint16_t delta_signal = + as->backlight_8bit_lut[100]-base_value; + uint16_t delta_luma = 100 - index + 1; + uint16_t step = delta_signal; + + for (; index < 100 ; index++) { + as->backlight_8bit_lut[index] = base_value + + (step / delta_luma); + step += delta_signal; + } + } + } + /* build backlight translation table based on default curve */ + else { + /* Default backlight curve can be defined by + * polinomial F(x) = A(x*x) + Bx + C. + * Backlight curve should always satisfy + * F(0) = min, F(100) = max, so polinomial coefficients are: + * A is 0.0255 - B/100 - min/10000 - + * (255-max)/10000 = (max - min)/10000 - B/100 + * B is adjustable factor to modify the curve. + * Bigger B results in less concave curve. + * B range is [0..(max-min)/100] + * C is backlight minimum + */ + uint16_t delta = as->backlight_8bit_lut[100] - + as->backlight_8bit_lut[0]; + uint16_t coeffc = as->backlight_8bit_lut[0]; + uint16_t coeffb = (BACKLIGHT_CURVE_COEFFB < delta ? + BACKLIGHT_CURVE_COEFFB : delta); + uint16_t coeffa = delta - coeffb; + uint16_t i; + uint32_t temp; + + for (i = 1; i < 100 ; i++) { + temp = (coeffa * i * i) / BACKLIGHT_CURVE_COEFFA_FACTOR; + as->backlight_8bit_lut[i] = temp + (coeffb * i) / + BACKLIGHT_CURVE_COEFFB_FACTOR + coeffc; + } + } + as->backlight_caps_initialized = true; +} + +static void log_overriden_features( + struct adapter_service *as, + const char *feature_name, + enum adapter_feature_id id, + bool bool_feature, + uint32_t value) +{ + if (bool_feature) + dal_logger_write(as->dal_context->logger, + LOG_MAJOR_FEATURE_OVERRIDE, + LOG_MINOR_FEATURE_OVERRIDE, + "Overridden %s is %s now\n", + feature_name, + (value == 0) ? "disabled" : "enabled"); + else + dal_logger_write(as->dal_context->logger, + LOG_MAJOR_FEATURE_OVERRIDE, + LOG_MINOR_FEATURE_OVERRIDE, + "Overridden %s new value: %d\n", + feature_name, + value); +} + +/************************************* + * Local static functions definition * + *************************************/ + +#define check_bool_feature(feature) \ +case FEATURE_ ## feature: \ + if (param->bool_param_enable_mask & \ + (1 << DAL_PARAM_ ## feature)) { \ + *data = param->bool_param_values & \ + (1 << DAL_PARAM_ ## feature); \ + ret = true; \ + feature_name = "FEATURE_" #feature; \ + } \ + break + +#define check_int_feature(feature) \ +case FEATURE_ ## feature: \ + if (param->int_param_values[DAL_PARAM_ ## feature] != \ + DAL_PARAM_INVALID_INT) { \ + *data = param->int_param_values[DAL_PARAM_ ## feature];\ + ret = true;\ + bool_feature = false;\ + feature_name = "FEATURE_" #feature;\ + } \ + break + +/* + * override_default_parameters + * + * Override features (from runtime parameter) + * corresponding to Adapter Service Feature ID + */ +static bool override_default_parameters( + struct adapter_service *as, + struct dal_override_parameters *param, + const uint32_t idx, + uint32_t *data) +{ + bool ret = false; + bool bool_feature = true; + char *feature_name; + + if (idx >= get_feature_entries_num()) { + ASSERT_CRITICAL(false); + return false; + } + + switch (feature_entry_table[idx].feature_id) { + check_int_feature(MAX_COFUNC_NON_DP_DISPLAYS); + check_int_feature(DRR_SUPPORT); + check_bool_feature(LIGHT_SLEEP); + check_bool_feature(MAXIMIZE_STUTTER_MARKS); + check_bool_feature(MAXIMIZE_URGENCY_WATERMARKS); + check_bool_feature(USE_MAX_DISPLAY_CLK); + check_bool_feature(ENABLE_DFS_BYPASS); + check_bool_feature(POWER_GATING_PIPE_IN_TILE); + check_bool_feature(POWER_GATING_LB_PORTION); + check_bool_feature(PSR_ENABLE); + check_bool_feature(VARI_BRIGHT_ENABLE); + check_bool_feature(USE_PPLIB); + check_bool_feature(DISABLE_LPT_SUPPORT); + check_bool_feature(DUMMY_FBC_BACKEND); + check_bool_feature(ENABLE_GPU_SCALING); + default: + return false; + } + if (ret) + log_overriden_features( + as, + feature_name, + feature_entry_table[idx].feature_id, + bool_feature, + *data); + + return ret; +} + +/* + * get_feature_value_from_data_sources + * + * For a given feature, determine its value from ASIC cap and wireless + * data source. + * idx : index of feature_entry_table for the feature id. + */ +static bool get_feature_value_from_data_sources( + const struct adapter_service *as, + const uint32_t idx, + uint32_t *data) +{ + if (idx >= get_feature_entries_num()) { + ASSERT_CRITICAL(false); + return false; + } + + switch (feature_entry_table[idx].feature_id) { + case FEATURE_MAX_COFUNC_NON_DP_DISPLAYS: + *data = as->asic_cap->data[ASIC_DATA_MAX_COFUNC_NONDP_DISPLAYS]; + break; + + case FEATURE_WIRELESS_LIMIT_720P: + *data = as->asic_cap->caps.WIRELESS_LIMIT_TO_720P; + break; + + case FEATURE_WIRELESS_FULL_TIMING_ADJUSTMENT: + *data = as->asic_cap->caps.WIRELESS_FULL_TIMING_ADJUSTMENT; + break; + + case FEATURE_MODIFY_TIMINGS_FOR_WIRELESS: + *data = as->asic_cap->caps.WIRELESS_TIMING_ADJUSTMENT; + break; + + case FEATURE_SUPPORTED_HDMI_CONNECTION_NUM: + *data = + as->asic_cap->data[ASIC_DATA_SUPPORTED_HDMI_CONNECTION_NUM]; + break; + + case FEATURE_DETECT_REQUIRE_HPD_HIGH: + *data = as->asic_cap->caps.HPD_CHECK_FOR_EDID; + break; + + case FEATURE_NO_HPD_LOW_POLLING_VCC_OFF: + *data = as->asic_cap->caps.NO_VCC_OFF_HPD_POLLING; + break; + + case FEATURE_STUTTER_MODE: + *data = as->asic_cap->data[ASIC_DATA_STUTTERMODE]; + break; + + case FEATURE_WIRELESS_ENABLE: + *data = as->wireless_data.wireless_enable; + break; + + case FEATURE_8BPP_SUPPORTED: + *data = as->asic_cap->caps.SUPPORT_8BPP; + break; + + default: + return false; + } + + return true; +} + +/* get_bool_value + * + * Get the boolean value of a given feature + */ +static bool get_bool_value( + const uint32_t set, + const uint32_t idx) +{ + if (idx >= 32) { + ASSERT_CRITICAL(false); + return false; + } + + return ((set & (1 << idx)) != 0); +} + +/* + * get_hpd_info + * + * Get HPD information from BIOS + */ +static bool get_hpd_info(struct adapter_service *as, + struct graphics_object_id id, + struct graphics_object_hpd_info *info) +{ + return BP_RESULT_OK == + dal_bios_parser_get_hpd_info(as->bios_parser, id, info); +} + +/* + * lookup_feature_entry + * + * Find the entry index of a given feature in feature table + */ +static uint32_t lookup_feature_entry( + enum adapter_feature_id feature_id) +{ + uint32_t entries_num = get_feature_entries_num(); + uint32_t i = 0; + + while (i != entries_num) { + if (feature_entry_table[i].feature_id == feature_id) + break; + + ++i; + } + + return i; +} + +/* + * set_bool_value + * + * Set the boolean value of a given feature + */ +static void set_bool_value( + uint32_t *set, + const uint32_t idx, + bool value) +{ + if (idx >= 32) { + ASSERT_CRITICAL(false); + return; + } + + if (value) + *set |= (1 << idx); + else + *set &= ~(1 << idx); +} + +/* + * generate_feature_set + * + * Generate the internal feature set from multiple data sources + */ +static bool generate_feature_set( + struct adapter_service *as, + struct dal_override_parameters *param) +{ + uint32_t i = 0; + uint32_t value = 0; + uint32_t set_idx = 0; + uint32_t internal_idx = 0; + uint32_t entry_num = 0; + const struct feature_source_entry *entry = NULL; + + dal_memset(adapter_feature_set, 0, sizeof(adapter_feature_set)); + entry_num = get_feature_entries_num(); + + + while (i != entry_num) { + entry = &feature_entry_table[i]; + + if (entry->feature_id <= FEATURE_UNKNOWN || + entry->feature_id >= FEATURE_MAXIMUM) { + ASSERT_CRITICAL(false); + return false; + } + + set_idx = (uint32_t)((entry->feature_id - 1) / 32); + internal_idx = (uint32_t)((entry->feature_id - 1) % 32); + + /* TODO: wireless, runtime parameter, vbios */ + if (!override_default_parameters(as, param, i, &value)) { + if (!get_feature_value_from_data_sources( + as, i, &value)) { + /* + * Can't find feature values from + * above data sources + * Assign default value + */ + value = entry->default_value; + } + } + + if (entry->is_boolean_type) + set_bool_value(&adapter_feature_set[set_idx], + internal_idx, + value != 0); + else + adapter_feature_set[set_idx] = value; + + i++; + } + + return true; +} + + +/* + * create_hw_ctx + * + * Create HW context for adapter service. This is DCE specific. + */ +static struct hw_ctx_adapter_service *create_hw_ctx( + enum dce_version dce_version, + struct dal_context *dal_context) +{ + switch (dce_version) { +#if defined(CONFIG_DRM_AMD_DAL_DCE11_0) + case DCE_VERSION_11_0: + return dal_adapter_service_create_hw_ctx_dce110(dal_context); +#endif + default: + ASSERT_CRITICAL(false); + return NULL; + } +} + +/* + * adapter_service_destruct + * + * Release memory of objects in adapter service + */ +static void adapter_service_destruct( + struct adapter_service *as) +{ + dal_adapter_service_destroy_hw_ctx(&as->hw_ctx); + dal_i2caux_destroy(&as->i2caux); + dal_bios_parser_destroy(&as->bios_parser); + dal_gpio_service_destroy(&as->gpio_service); + dal_asic_capability_destroy(&as->asic_cap); + dal_bios_parser_destroy_integrated_info(&as->integrated_info); +} + +/* + * adapter_service_construct + * + * Construct the derived type of adapter service + */ +static bool adapter_service_construct( + struct adapter_service *as, + struct as_init_data *init_data) +{ + if (!init_data) + return false; + + /* Create ASIC capability */ + as->dal_context = init_data->dal_context; + as->asic_cap = dal_asic_capability_create( + &init_data->hw_init_data, as->dal_context); + + if (!as->asic_cap) { + ASSERT_CRITICAL(false); + return false; + } + +#if defined(DAL_CZ_BRINGUP) + if (dal_adapter_service_get_dce_version(as) == DCE_VERSION_11_0) { + uint32_t i; + + for (i = 0; i < ARRAY_SIZE(feature_entry_table); i++) { + enum adapter_feature_id id = + feature_entry_table[i].feature_id; + if (id == FEATURE_MAXIMIZE_URGENCY_WATERMARKS || + id == FEATURE_MAXIMIZE_STUTTER_MARKS || + id == FEATURE_MAXIMIZE_NBP_MARKS) + feature_entry_table[i].default_value = true; + } + } +#endif + + /* Generate feature set table */ + if (!generate_feature_set(as, init_data->display_param)) { + ASSERT_CRITICAL(false); + goto failed_to_generate_features; + } + + /* Create BIOS parser */ + init_data->bp_init_data.dal_context = init_data->dal_context; + as->bios_parser = + dal_bios_parser_create(&init_data->bp_init_data, as); + + if (!as->bios_parser) { + ASSERT_CRITICAL(false); + goto failed_to_create_bios_parser; + } + + /* Create GPIO service */ + as->gpio_service = + dal_gpio_service_create( + dal_adapter_service_get_dce_version(as), + as->dal_context); + + if (!as->gpio_service) { + ASSERT_CRITICAL(false); + goto failed_to_create_gpio_service; + } + + /* Create I2C AUX */ + as->i2caux = dal_i2caux_create(as, as->dal_context); + + if (!as->i2caux) { + ASSERT_CRITICAL(false); + goto failed_to_create_i2caux; + } + + /* Create Adapter Service HW Context*/ + as->hw_ctx = create_hw_ctx( + dal_adapter_service_get_dce_version(as), + as->dal_context); + + if (!as->hw_ctx) { + ASSERT_CRITICAL(false); + goto failed_to_create_hw_ctx; + } + + /* Integrated info is not provided on discrete ASIC. NULL is allowed */ + as->integrated_info = dal_bios_parser_create_integrated_info( + as->bios_parser); + + dal_bios_parser_post_init(as->bios_parser); + + /* Generate backlight translation table and initializes + other brightness properties */ + as->backlight_caps_initialized = false; + + get_platform_info_methods(as); + + initialize_backlight_caps(as); + + return true; + +failed_to_generate_features: + dal_adapter_service_destroy_hw_ctx(&as->hw_ctx); + +failed_to_create_hw_ctx: + dal_i2caux_destroy(&as->i2caux); + +failed_to_create_i2caux: + dal_gpio_service_destroy(&as->gpio_service); + +failed_to_create_gpio_service: + dal_bios_parser_destroy(&as->bios_parser); + +failed_to_create_bios_parser: + dal_asic_capability_destroy(&as->asic_cap); + + return false; +} + +/* + * Global function definition + */ + +/* + * dal_adapter_service_create + * + * Create adapter service + */ +struct adapter_service *dal_adapter_service_create( + struct as_init_data *init_data) +{ + struct adapter_service *as; + + as = dal_alloc(sizeof(struct adapter_service)); + + if (!as) { + ASSERT_CRITICAL(false); + return NULL; + } + + if (adapter_service_construct(as, init_data)) + return as; + + ASSERT_CRITICAL(false); + + dal_free(as); + + return NULL; +} + +/* + * dal_adapter_service_destroy + * + * Destroy adapter service and objects it contains + */ +void dal_adapter_service_destroy( + struct adapter_service **as) +{ + if (!as) { + ASSERT_CRITICAL(false); + return; + } + + if (!*as) { + ASSERT_CRITICAL(false); + return; + } + + adapter_service_destruct(*as); + + dal_free(*as); + + *as = NULL; +} + +/* + * dal_adapter_service_get_dce_version + * + * Get the DCE version of current ASIC + */ +enum dce_version dal_adapter_service_get_dce_version( + const struct adapter_service *as) +{ + uint32_t version = as->asic_cap->data[ASIC_DATA_DCE_VERSION]; + + switch (version) { + case 0x110: + return DCE_VERSION_11_0; + default: + ASSERT_CRITICAL(false); + return DCE_VERSION_UNKNOWN; + } +} + +/* + * dal_adapter_service_get_controllers_num + * + * Get number of controllers + */ +uint8_t dal_adapter_service_get_controllers_num( + struct adapter_service *as) +{ + uint32_t result = as->asic_cap->data[ASIC_DATA_CONTROLLERS_NUM]; + + /* Check the "max num of controllers" feature, + * use it for debugging purposes only */ + /* TODO implement + * dal_adapter_service_get_feature_value(as, ) */ + + return result; +} + + +/** Get total number of connectors. + * + * \param as Adapter Service + * + * \return Total number of connectors. It is up-to-the caller to decide + * if the number is valid. + */ +uint8_t dal_adapter_service_get_connectors_num( + struct adapter_service *as) +{ + uint8_t vbios_connectors_num = 0; + uint8_t wireless_connectors_num = 0; + + vbios_connectors_num = dal_bios_parser_get_connectors_number( + as->bios_parser); + wireless_connectors_num = wireless_get_connectors_num(as); + + return vbios_connectors_num + wireless_connectors_num; +} + +static bool is_wireless_object(struct graphics_object_id id) +{ + if ((id.type == OBJECT_TYPE_ENCODER && + id.id == ENCODER_ID_INTERNAL_WIRELESS) || + (id.type == OBJECT_TYPE_CONNECTOR && id.id == + CONNECTOR_ID_WIRELESS) || + (id.type == OBJECT_TYPE_CONNECTOR && id.id == + CONNECTOR_ID_MIRACAST)) + return true; + return false; +} + +/** + * Get the number of source objects of an object + * + * \param [in] as: Adapter Service + * + * \param [in] id: The graphics object id + * + * \return + * The number of the source objects of an object + */ +uint32_t dal_adapter_service_get_src_num( + struct adapter_service *as, struct graphics_object_id id) +{ + if (is_wireless_object(id)) + return wireless_get_srcs_num(as, id); + else + return dal_bios_parser_get_src_number(as->bios_parser, id); +} + +/** + * Get the source objects of an object + * + * \param [in] id The graphics object id + * \param [in] index Enumerating index which starts at 0 + * + * \return If enumerating successfully, return the VALID source object id, + * otherwise, returns "zeroed out" object id. + * Client should call dal_graphics_object_id_is_valid() to check + * weather the id is valid. + */ +struct graphics_object_id dal_adapter_service_get_src_obj( + struct adapter_service *as, + struct graphics_object_id id, + uint32_t index) +{ + struct graphics_object_id src_object_id; + + if (is_wireless_object(id)) + src_object_id = wireless_get_src_obj_id(as, id, index); + else { + if (BP_RESULT_OK != + dal_bios_parser_get_src_obj( + as->bios_parser, id, index, &src_object_id)) + src_object_id = + dal_graphics_object_id_init( + 0, + ENUM_ID_UNKNOWN, + OBJECT_TYPE_UNKNOWN); + } + + return src_object_id; +} + +/** Get connector object id associated with a connector index. + * + * \param as Adapter Service + * + * \param connector_index Index of connector between zero and total number + * returned by dal_adapter_service_get_connectors_num() + * + * \return graphics object id corresponding to the connector_index. + */ +struct graphics_object_id dal_adapter_service_get_connector_obj_id( + struct adapter_service *as, + uint8_t connector_index) +{ + uint8_t bios_connectors_num = + dal_bios_parser_get_connectors_number(as->bios_parser); + + if (connector_index >= bios_connectors_num) + return wireless_get_connector_id( + as, + connector_index); + else + return dal_bios_parser_get_connector_id( + as->bios_parser, + connector_index); +} + +bool dal_adapter_service_get_device_tag( + struct adapter_service *as, + struct graphics_object_id connector_object_id, + uint32_t device_tag_index, + struct connector_device_tag_info *info) +{ + if (BP_RESULT_OK == dal_bios_parser_get_device_tag(as->bios_parser, + connector_object_id, device_tag_index, info)) + return true; + else + return false; +} + +/* Check if DeviceId is supported by ATOM_OBJECT_HEADER support info */ +bool dal_adapter_service_is_device_id_supported(struct adapter_service *as, + struct device_id id) +{ + return dal_bios_parser_is_device_id_supported(as->bios_parser, id); +} + +bool dal_adapter_service_is_meet_underscan_req(struct adapter_service *as) +{ + struct firmware_info fw_info; + enum bp_result bp_result = dal_adapter_service_get_firmware_info( + as, &fw_info); + uint32_t disp_clk_limit = + as->asic_cap->data[ASIC_DATA_MIN_DISPCLK_FOR_UNDERSCAN]; + if (BP_RESULT_OK == bp_result) { + dal_logger_write(as->dal_context->logger, + LOG_MAJOR_ERROR, + LOG_MINOR_COMPONENT_ADAPTER_SERVICE, + "Read firmware is NULL"); + return false; + } + if (fw_info.default_display_engine_pll_frequency < disp_clk_limit) + return false; + return true; +} + +bool dal_adapter_service_underscan_for_hdmi_only(struct adapter_service *as) +{ + return as->asic_cap->caps.UNDERSCAN_FOR_HDMI_ONLY; +} +/* + * dal_adapter_service_get_clock_sources_num + * + * Get number of clock sources + */ +uint8_t dal_adapter_service_get_clock_sources_num( + struct adapter_service *as) +{ + struct firmware_info fw_info; + uint32_t max_clk_src = 0; + uint32_t num = as->asic_cap->data[ASIC_DATA_CLOCKSOURCES_NUM]; + + /* + * Check is system supports the use of the External clock source + * as a clock source for DP + */ + enum bp_result bp_result = + dal_bios_parser_get_firmware_info(as->bios_parser, + &fw_info); + + if (BP_RESULT_OK == bp_result && + fw_info.external_clock_source_frequency_for_dp != 0) + ++num; + + /* + * Add clock source for wireless if supported + */ + num += (uint32_t)wireless_get_clocks_num(as); + + /* Check the "max number of clock sources" feature */ + if (dal_adapter_service_get_feature_value( + FEATURE_MAX_CLOCK_SOURCE_NUM, + &max_clk_src, + sizeof(uint32_t))) + if ((max_clk_src != 0) && (max_clk_src < num)) + num = max_clk_src; + + return num; +} + +/* + * dal_adapter_service_get_func_controllers_num + * + * Get number of controllers + */ +uint8_t dal_adapter_service_get_func_controllers_num( + struct adapter_service *as) +{ + uint32_t result = + as->asic_cap->data[ASIC_DATA_FUNCTIONAL_CONTROLLERS_NUM]; + + /* Check the "max num of controllers" feature, + * use it for debugging purposes only */ + + /* Limit number of controllers by OS */ + + struct asic_feature_flags flags; + + flags.raw = as->asic_cap->data[ASIC_DATA_FEATURE_FLAGS]; + + if (flags.bits.LEGACY_CLIENT && + (result > LEGACY_MAX_NUM_OF_CONTROLLERS)) + result = LEGACY_MAX_NUM_OF_CONTROLLERS; + + return result; +} + +/* + * dal_adapter_service_is_feature_supported + * + * Return if a given feature is supported by the ASIC. The feature has to be + * a boolean type. + */ +bool dal_adapter_service_is_feature_supported( + enum adapter_feature_id feature_id) +{ + bool data = 0; + + dal_adapter_service_get_feature_value(feature_id, &data, sizeof(bool)); + + return data; +} + +/** + * Reports maximum number of confunctional non-DP displays. + * Value can be overriden if FEATURE_REPORT_SINGLE_SELECTED_TIMING feature is + * enabled. + * + * \return + * Maximum number of confunctional non-DP displays + */ +uint32_t dal_adapter_service_get_max_cofunc_non_dp_displays(void) +{ + uint32_t non_dp_displays = DEFAULT_NUM_COFUNC_NON_DP_DISPLAYS; + + if (true == dal_adapter_service_get_feature_value( + FEATURE_MAX_COFUNC_NON_DP_DISPLAYS, + &non_dp_displays, + sizeof(non_dp_displays))) { + /* the cached value exist */ + /* TODO: add more logic as per-DAL2 */ + } + + return non_dp_displays; +} + +uint32_t dal_adapter_service_get_single_selected_timing_signals(void) +{ + uint32_t signals_bitmap = 0; + + if (dal_adapter_service_is_feature_supported( + FEATURE_REPORT_SINGLE_SELECTED_TIMING)) { + /* the cached value exist */ + /* TODO: add more logic as per-DAL2 */ + signals_bitmap = 0; + } + + return signals_bitmap; +} + +/* + * dal_adapter_service_get_i2c_info + * + * Get I2C information from BIOS + */ +bool dal_adapter_service_get_i2c_info( + struct adapter_service *as, + struct graphics_object_id id, + struct graphics_object_i2c_info *i2c_info) +{ + if (!i2c_info) { + ASSERT_CRITICAL(false); + return false; + } + + return BP_RESULT_OK == + dal_bios_parser_get_i2c_info(as->bios_parser, id, i2c_info); +} + +/* + * dal_adapter_service_obtain_ddc + * + * Obtain DDC + */ +struct ddc *dal_adapter_service_obtain_ddc( + struct adapter_service *as, + struct graphics_object_id id) +{ + struct graphics_object_i2c_info i2c_info; + struct gpio_ddc_hw_info hw_info; + + + if (!dal_adapter_service_get_i2c_info(as, id, &i2c_info)) + return NULL; + + hw_info.ddc_channel = i2c_info.i2c_line; + hw_info.hw_supported = i2c_info.i2c_hw_assist; + + return dal_gpio_service_create_ddc( + as->gpio_service, + i2c_info.gpio_info.clk_a_register_index, + 1 << i2c_info.gpio_info.clk_a_shift, + &hw_info); +} + +/* + * dal_adapter_service_release_ddc + * + * Release DDC + */ +void dal_adapter_service_release_ddc( + struct adapter_service *as, + struct ddc *ddc) +{ + dal_gpio_service_destroy_ddc(&ddc); +} + +/* + * dal_adapter_service_obtain_hpd_irq + * + * Obtain HPD interrupt request + */ +struct irq *dal_adapter_service_obtain_hpd_irq( + struct adapter_service *as, + struct graphics_object_id id) +{ + enum bp_result bp_result; + + struct graphics_object_hpd_info hpd_info; + struct gpio_pin_info pin_info; + + if (!get_hpd_info(as, id, &hpd_info)) + return NULL; + + bp_result = dal_bios_parser_get_gpio_pin_info(as->bios_parser, + hpd_info.hpd_int_gpio_uid, &pin_info); + + if (bp_result != BP_RESULT_OK) { + ASSERT(bp_result == BP_RESULT_NORECORD); + return NULL; + } + + return dal_gpio_service_create_irq( + as->gpio_service, + pin_info.offset, + pin_info.mask); +} + +/* + * dal_adapter_service_release_irq + * + * Release interrupt request + */ +void dal_adapter_service_release_irq( + struct adapter_service *as, + struct irq *irq) +{ + dal_gpio_service_destroy_irq(&irq); +} + +/* + * dal_adapter_service_get_ss_info_num + * + * Get number of spread spectrum entries from BIOS + */ +uint32_t dal_adapter_service_get_ss_info_num( + struct adapter_service *as, + enum as_signal_type signal) +{ + return dal_bios_parser_get_ss_entry_number(as->bios_parser, signal); +} + +/* + * dal_adapter_service_get_ss_info + * + * Get spread spectrum info from BIOS + */ +bool dal_adapter_service_get_ss_info( + struct adapter_service *as, + enum as_signal_type signal, + uint32_t idx, + struct spread_spectrum_info *info) +{ + enum bp_result bp_result = + dal_bios_parser_get_spread_spectrum_info( + as->bios_parser, signal, idx, info); + + return BP_RESULT_OK == bp_result; +} + +/* + * dal_adapter_service_get_integrated_info + * + * Get integrated information on BIOS + */ +bool dal_adapter_service_get_integrated_info( + struct adapter_service *as, + struct integrated_info *info) +{ + if (info == NULL || as->integrated_info == NULL) + return false; + + dal_memmove(info, as->integrated_info, sizeof(struct integrated_info)); + + return true; +} + +/* + * dal_adapter_service_is_dfs_bypass_enabled + * + * Check if DFS bypass is enabled + */ +bool dal_adapter_service_is_dfs_bypass_enabled( + struct adapter_service *as) +{ + if (as->integrated_info == NULL) + return false; + if ((as->integrated_info->gpu_cap_info & DFS_BYPASS_ENABLE) && + dal_adapter_service_is_feature_supported( + FEATURE_ENABLE_DFS_BYPASS)) + return true; + else + return false; +} + +/* + * dal_adapter_service_get_sw_i2c_speed + * + * Get SW I2C speed + */ +uint32_t dal_adapter_service_get_sw_i2c_speed( + struct adapter_service *as) +{ + /* TODO: only from ASIC caps. Feature key is not implemented*/ + return as->asic_cap->data[ASIC_DATA_DEFAULT_I2C_SPEED_IN_KHZ]; +} + +/* + * dal_adapter_service_get_hw_i2c_speed + * + * Get HW I2C speed + */ +uint32_t dal_adapter_service_get_hw_i2c_speed( + struct adapter_service *as) +{ + /* TODO: only from ASIC caps. Feature key is not implemented*/ + return as->asic_cap->data[ASIC_DATA_DEFAULT_I2C_SPEED_IN_KHZ]; +} + +/* + * dal_adapter_service_get_mc_latency + * + * Get memory controller latency + */ +uint32_t dal_adapter_service_get_mc_latency( + struct adapter_service *as) +{ + return as->asic_cap->data[ASIC_DATA_MC_LATENCY]; +} + +/* + * dal_adapter_service_get_asic_vram_bit_width + * + * Get the video RAM bit width set on the ASIC + */ +uint32_t dal_adapter_service_get_asic_vram_bit_width( + struct adapter_service *as) +{ + return as->asic_cap->data[ASIC_DATA_VRAM_BITWIDTH]; +} + +/* + * dal_adapter_service_get_asic_bugs + * + * Get the bug flags set on this ASIC + */ +struct asic_bugs dal_adapter_service_get_asic_bugs( + struct adapter_service *as) +{ + return as->asic_cap->bugs; +} + + +struct dal_asic_runtime_flags dal_adapter_service_get_asic_runtime_flags( + struct adapter_service *as) +{ + return as->asic_cap->runtime_flags; +} + +/* + * dal_adapter_service_get_line_buffer_size + * + * Get line buffer size + */ +uint32_t dal_adapter_service_get_line_buffer_size( + struct adapter_service *as) +{ + return as->asic_cap->data[ASIC_DATA_LINEBUFFER_SIZE]; +} + +/* + * dal_adapter_service_get_bandwidth_tuning_params + * + * Get parameters for bandwidth tuning + */ +bool dal_adapter_service_get_bandwidth_tuning_params( + struct adapter_service *as, + union bandwidth_tuning_params *params) +{ + /* TODO: add implementation */ + /* note: data comes from runtime parameters */ + return false; +} + +/* + * dal_adapter_service_get_feature_flags + * + * Get a copy of ASIC feature flags + */ +struct asic_feature_flags dal_adapter_service_get_feature_flags( + struct adapter_service *as) +{ + struct asic_feature_flags result = { { 0 } }; + + if (!as) { + ASSERT_CRITICAL(false); + return result; + } + + result.raw = as->asic_cap->data[ASIC_DATA_FEATURE_FLAGS]; + + return result; +} + +/* + * dal_adapter_service_get_dram_bandwidth_efficiency + * + * Get efficiency of DRAM + */ +uint32_t dal_adapter_service_get_dram_bandwidth_efficiency( + struct adapter_service *as) +{ + return as->asic_cap->data[ASIC_DATA_DRAM_BANDWIDTH_EFFICIENCY]; +} + +/* + * dal_adapter_service_obtain_gpio + * + * Obtain GPIO + */ +struct gpio *dal_adapter_service_obtain_gpio( + struct adapter_service *as, + enum gpio_id id, + uint32_t en) +{ + return dal_gpio_service_create_gpio_ex( + as->gpio_service, id, en, + GPIO_PIN_OUTPUT_STATE_DEFAULT); +} + +/* + * dal_adapter_service_obtain_stereo_gpio + * + * Obtain GPIO for stereo3D + */ +struct gpio *dal_adapter_service_obtain_stereo_gpio( + struct adapter_service *as) +{ + const bool have_param_stereo_gpio = false; + + struct asic_feature_flags result; + + result.raw = as->asic_cap->data[ASIC_DATA_FEATURE_FLAGS]; + + /* Case 1 : Workstation stereo */ + if (result.bits.WORKSTATION_STEREO) + /* "active low" <--> "default 3d right eye polarity" = false */ + return dal_gpio_service_create_gpio_ex( + as->gpio_service, GPIO_ID_GENERIC, GPIO_GENERIC_A, + GPIO_PIN_OUTPUT_STATE_ACTIVE_LOW); + /* Case 2 : runtime parameter override for sideband stereo */ + else if (have_param_stereo_gpio) { + /* TODO implement */ + return NULL; + /* Case 3 : VBIOS gives us GPIO for sideband stereo */ + } else { + const struct graphics_object_id id = + dal_graphics_object_id_init( + GENERIC_ID_STEREO, + ENUM_ID_1, + OBJECT_TYPE_GENERIC); + + struct bp_gpio_cntl_info cntl_info; + struct gpio_pin_info pin_info; + + /* Get GPIO record for this object. + * Stereo GPIO record should have exactly one entry + * where active state defines stereosync polarity */ + if (1 != dal_bios_parser_get_gpio_record( + as->bios_parser, id, &cntl_info, 1)) { + return NULL; + } else if (BP_RESULT_OK != dal_bios_parser_get_gpio_pin_info( + as->bios_parser, cntl_info.id, &pin_info)) { + /*ASSERT_CRITICAL(false);*/ + return NULL; + } else + return dal_gpio_service_create_gpio_ex( + as->gpio_service, + pin_info.offset, pin_info.mask, + cntl_info.state); + } +} + +/* + * dal_adapter_service_release_gpio + * + * Release GPIO + */ +void dal_adapter_service_release_gpio( + struct adapter_service *as, + struct gpio *gpio) +{ + dal_gpio_service_destroy_gpio(&gpio); +} + +/* + * dal_adapter_service_get_firmware_info + * + * Get firmware information from BIOS + */ +bool dal_adapter_service_get_firmware_info( + struct adapter_service *as, + struct firmware_info *info) +{ + return dal_bios_parser_get_firmware_info(as->bios_parser, info) == + BP_RESULT_OK; +} + +/* + * dal_adapter_service_get_audio_support + * + * Get information on audio support + */ +union audio_support dal_adapter_service_get_audio_support( + struct adapter_service *as) +{ + return dal_adapter_service_hw_ctx_get_audio_support(as->hw_ctx); +} + +/* + * dal_adapter_service_get_stream_engines_num + * + * Get number of stream engines + */ +uint8_t dal_adapter_service_get_stream_engines_num( + struct adapter_service *as) +{ + return as->asic_cap->data[ASIC_DATA_DIGFE_NUM]; +} + +/* + * dal_adapter_service_get_feature_value + * + * Get the cached value of a given feature. This value can be a boolean, int, + * or characters. + */ +bool dal_adapter_service_get_feature_value( + const enum adapter_feature_id feature_id, + void *data, + uint32_t size) +{ + uint32_t entry_idx = 0; + uint32_t set_idx = 0; + uint32_t set_internal_idx = 0; + + if (feature_id >= FEATURE_MAXIMUM || feature_id <= FEATURE_UNKNOWN) { + ASSERT_CRITICAL(false); + return false; + } + + if (data == NULL) { + ASSERT_CRITICAL(false); + return false; + } + + entry_idx = lookup_feature_entry(feature_id); + set_idx = (uint32_t)((feature_id - 1)/32); + set_internal_idx = (uint32_t)((feature_id - 1) % 32); + + if (entry_idx >= get_feature_entries_num()) { + /* Cannot find this entry */ + ASSERT_CRITICAL(false); + return false; + } + + if (feature_entry_table[entry_idx].is_boolean_type) { + if (size != sizeof(bool)) { + ASSERT_CRITICAL(false); + return false; + } + + *(bool *)data = get_bool_value(adapter_feature_set[set_idx], + set_internal_idx); + } else { + if (size != sizeof(uint32_t)) { + ASSERT_CRITICAL(false); + return false; + } + + *(uint32_t *)data = adapter_feature_set[set_idx]; + } + + return true; +} + +/* + * dal_adapter_service_get_memory_type_multiplier + * + * Get multiplier for the memory type + */ +uint32_t dal_adapter_service_get_memory_type_multiplier( + struct adapter_service *as) +{ + return as->asic_cap->data[ASIC_DATA_MEMORYTYPE_MULTIPLIER]; +} + +/* + * dal_adapter_service_get_bios_parser + * + * Get BIOS parser handler + */ +struct bios_parser *dal_adapter_service_get_bios_parser( + struct adapter_service *as) +{ + return as->bios_parser; +} + +/* + * dal_adapter_service_get_i2caux + * + * Get i2c aux handler + */ +struct i2caux *dal_adapter_service_get_i2caux( + struct adapter_service *as) +{ + return as->i2caux; +} + +bool dal_adapter_service_initialize_hw_data( + struct adapter_service *as) +{ + return as->hw_ctx->funcs->power_up(as->hw_ctx); +} + +struct graphics_object_id dal_adapter_service_enum_fake_path_resource( + struct adapter_service *as, + uint32_t index) +{ + return as->hw_ctx->funcs->enum_fake_path_resource(as->hw_ctx, index); +} + +struct graphics_object_id dal_adapter_service_enum_stereo_sync_object( + struct adapter_service *as, + uint32_t index) +{ + return as->hw_ctx->funcs->enum_stereo_sync_object(as->hw_ctx, index); +} + +struct graphics_object_id dal_adapter_service_enum_sync_output_object( + struct adapter_service *as, + uint32_t index) +{ + return as->hw_ctx->funcs->enum_sync_output_object(as->hw_ctx, index); +} + +struct graphics_object_id dal_adapter_service_enum_audio_object( + struct adapter_service *as, + uint32_t index) +{ + return as->hw_ctx->funcs->enum_audio_object(as->hw_ctx, index); +} + + +void dal_adapter_service_update_audio_connectivity( + struct adapter_service *as, + uint32_t number_of_audio_capable_display_path) +{ + as->hw_ctx->funcs->update_audio_connectivity( + as->hw_ctx, + number_of_audio_capable_display_path, + dal_adapter_service_get_controllers_num(as)); +} + +bool dal_adapter_service_has_embedded_display_connector( + struct adapter_service *as) +{ + uint8_t index; + uint8_t num_connectors = dal_adapter_service_get_connectors_num(as); + + if (num_connectors == 0 || num_connectors > ENUM_ID_COUNT) + return false; + + for (index = 0; index < num_connectors; index++) { + struct graphics_object_id obj_id = + dal_adapter_service_get_connector_obj_id(as, index); + enum connector_id connector_id = + dal_graphics_object_id_get_connector_id(obj_id); + + if ((connector_id == CONNECTOR_ID_LVDS) || + (connector_id == CONNECTOR_ID_EDP)) + return true; + } + + return false; +} + +bool dal_adapter_service_get_embedded_panel_info( + struct adapter_service *as, + struct embedded_panel_info *info) +{ + enum bp_result result; + + if (info == NULL) + /*TODO: add DALASSERT_MSG here*/ + return false; + + result = dal_bios_parser_get_embedded_panel_info( + as->bios_parser, info); + + return result == BP_RESULT_OK; +} + +bool dal_adapter_service_enum_embedded_panel_patch_mode( + struct adapter_service *as, + uint32_t index, + struct embedded_panel_patch_mode *mode) +{ + enum bp_result result; + + if (mode == NULL) + /*TODO: add DALASSERT_MSG here*/ + return false; + + result = dal_bios_parser_enum_embedded_panel_patch_mode( + as->bios_parser, index, mode); + + return result == BP_RESULT_OK; +} + +bool dal_adapter_service_get_faked_edid_len( + struct adapter_service *as, + uint32_t *len) +{ + enum bp_result result; + + result = dal_bios_parser_get_faked_edid_len( + as->bios_parser, + len); + return result == BP_RESULT_OK; +} + +bool dal_adapter_service_get_faked_edid_buf( + struct adapter_service *as, + uint8_t *buf, + uint32_t len) +{ + enum bp_result result; + + result = dal_bios_parser_get_faked_edid_buf( + as->bios_parser, + buf, + len); + return result == BP_RESULT_OK; + +} + +/* + * dal_adapter_service_is_fusion + * + * Is this Fusion ASIC + */ +bool dal_adapter_service_is_fusion(struct adapter_service *as) +{ + return as->asic_cap->caps.IS_FUSION; +} + +/* + * dal_adapter_service_is_dfsbyass_dynamic + * + * + **/ +bool dal_adapter_service_is_dfsbyass_dynamic(struct adapter_service *as) +{ + return as->asic_cap->caps.DFSBYPASS_DYNAMIC_SUPPORT; +} + +/* + * dal_adapter_service_should_optimize + * + * @brief Reports whether driver settings allow requested optimization + * + * @param + * as: adapter service handler + * feature: for which optimization is validated + * + * @return + * true if requested feature can be optimized + */ +bool dal_adapter_service_should_optimize( + struct adapter_service *as, enum optimization_feature feature) +{ + uint32_t supported_optimization = 0; + struct dal_asic_runtime_flags flags; + + if (!dal_adapter_service_get_feature_value(FEATURE_OPTIMIZATION, + &supported_optimization, sizeof(uint32_t))) + return false; + + /* Retrieve ASIC runtime flags */ + flags = dal_adapter_service_get_asic_runtime_flags(as); + + /* Check runtime flags against different optimization features */ + switch (feature) { + case OF_SKIP_HW_PROGRAMMING_ON_ENABLED_EMBEDDED_DISPLAY: + if (!flags.bits.OPTIMIZED_DISPLAY_PROGRAMMING_ON_BOOT) + return false; + break; + + case OF_SKIP_RESET_OF_ALL_HW_ON_S3RESUME: + if (as->integrated_info == NULL || + !flags.bits.SKIP_POWER_DOWN_ON_RESUME) + return false; + break; + case OF_SKIP_POWER_DOWN_INACTIVE_ENCODER: + if (!dal_adapter_service_get_asic_runtime_flags(as).bits. + SKIP_POWER_DOWN_ON_RESUME) + return false; + break; + default: + break; + } + + return (supported_optimization & feature) != 0; +} + +/* + * dal_adapter_service_is_in_accelerated_mode + * + * @brief Determine if driver is in accelerated mode + * + * @param + * as: Adapter Service handler + * + * @out + * True if driver is in accelerated mode, false otherwise. + */ +bool dal_adapter_service_is_in_accelerated_mode(struct adapter_service *as) +{ + return dal_bios_parser_is_accelerated_mode(as->bios_parser); +} + +struct ddc *dal_adapter_service_obtain_ddc_from_i2c_info( + struct adapter_service *as, + struct graphics_object_i2c_info *info) +{ + struct gpio_ddc_hw_info hw_info = { + info->i2c_hw_assist, + info->i2c_line }; + return dal_gpio_service_create_ddc(as->gpio_service, + info->gpio_info.clk_a_register_index, + (1 << info->gpio_info.clk_a_shift), &hw_info); +} + +struct bdf_info dal_adapter_service_get_adapter_info(struct adapter_service *as) +{ + return as->bdf_info; +} + +/* + * dal_adapter_service_should_psr_skip_wait_for_pll_lock + * + * @brief Determine if this ASIC needs to wait on PLL lock bit + * + * @param + * as: Adapter Service handle + * + * @out + * True if ASIC does not need to wait for PLL lock bit, i.e. skip the wait. + */ +bool dal_adapter_service_should_psr_skip_wait_for_pll_lock( + struct adapter_service *as) +{ + return as->asic_cap->caps.SKIP_PSR_WAIT_FOR_PLL_LOCK_BIT; +} + +bool dal_adapter_service_is_lid_open(struct adapter_service *as) +{ + bool is_lid_open = false; + struct platform_info_params params; + + params.data = &is_lid_open; + params.method = PM_GET_LID_STATE; + + if ((PM_GET_LID_STATE & as->platform_methods_mask) && + dal_get_platform_info(as->dal_context, ¶ms)) + return is_lid_open; + +#if defined(CONFIG_DRM_AMD_DAL_VBIOS_PRESENT) + return dal_bios_parser_is_lid_open(as->bios_parser); +#else + return false; +#endif +} + +bool dal_adapter_service_get_panel_backlight_default_levels( + struct adapter_service *as, + struct panel_backlight_levels *levels) +{ + if (!as->backlight_caps_initialized) + return false; + + levels->ac_level_percentage = as->ac_level_percentage; + levels->dc_level_percentage = as->dc_level_percentage; + return true; +} + +bool dal_adapter_service_get_panel_backlight_boundaries( + struct adapter_service *as, + struct panel_backlight_boundaries *boundaries) +{ + if (!as->backlight_caps_initialized) + return false; + if (boundaries != NULL) { + boundaries->min_signal_level = as->backlight_8bit_lut[0]; + boundaries->max_signal_level = + as->backlight_8bit_lut[SIZEOF_BACKLIGHT_LUT - 1]; + return true; + } + return false; +} + + +uint32_t dal_adapter_service_get_view_port_pixel_granularity( + struct adapter_service *as) +{ + return as->asic_cap->data[ASIC_DATA_VIEWPORT_PIXEL_GRANULARITY]; +} + +/** + * Get number of paths per DP 1.2 connector from the runtime parameter if it + * exists. + * A check to see if MST is supported for the generation of ASIC is done + * + * \return + * Number of paths per DP 1.2 connector is exists in runtime parameters + * or ASIC cap + */ +uint32_t dal_adapter_service_get_num_of_path_per_dp_mst_connector( + struct adapter_service *as) +{ + if (as->asic_cap->caps.DP_MST_SUPPORTED == 0) { + /* ASIC doesn't support DP MST at all */ + return 0; + } + + return as->asic_cap->data[ASIC_DATA_PATH_NUM_PER_DPMST_CONNECTOR]; +} + +uint32_t dal_adapter_service_get_num_of_underlays( + struct adapter_service *as) +{ + return as->asic_cap->data[ASIC_DATA_NUM_OF_VIDEO_PLANES]; +} + +bool dal_adapter_service_get_encoder_cap_info( + struct adapter_service *as, + struct graphics_object_id id, + struct graphics_object_encoder_cap_info *info) +{ + struct bp_encoder_cap_info bp_cap_info = {0}; + enum bp_result result; + + if (NULL == info) { + ASSERT_CRITICAL(false); + return false; + } + + /* + * Retrieve Encoder Capability Information from VBIOS and store the + * call result (success or fail) + * Info from VBIOS about HBR2 has two fields: + * + * - dpHbr2Cap: indicates supported/not supported by HW Encoder + * - dpHbr2En : indicates DP spec compliant/not compliant + */ + result = dal_bios_parser_get_encoder_cap_info( + as->bios_parser, + id, + &bp_cap_info); + + /* Set dp_hbr2_validated flag (it's equal to Enable) */ + info->dp_hbr2_validated = bp_cap_info.DP_HBR2_EN; + + if (result == BP_RESULT_OK) { + info->dp_hbr2_cap = bp_cap_info.DP_HBR2_CAP; + return true; + } + + return false; +} + +bool dal_adapter_service_is_mc_tuning_req(struct adapter_service *as) +{ + return as->asic_cap->caps.NEED_MC_TUNING ? true : false; +} diff --git a/drivers/gpu/drm/amd/dal/adapter/adapter_service.h b/drivers/gpu/drm/amd/dal/adapter/adapter_service.h new file mode 100644 index 000000000000..2ee93c7fca61 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/adapter_service.h @@ -0,0 +1,67 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_ADAPTER_SERVICE_H__ +#define __DAL_ADAPTER_SERVICE_H__ + +/* Include */ +#include "include/adapter_service_interface.h" +#include "wireless_data_source.h" + +/* + * Forward declaration + */ +struct gpio_service; +struct asic_cap; + +/* Adapter service */ +struct adapter_service { + struct dal_context *dal_context; + struct asic_capability *asic_cap; + struct bios_parser *bios_parser; + struct gpio_service *gpio_service; + struct i2caux *i2caux; + struct wireless_data wireless_data; + struct hw_ctx_adapter_service *hw_ctx; + struct integrated_info *integrated_info; + struct bdf_info bdf_info; + uint32_t platform_methods_mask; + uint32_t ac_level_percentage; + uint32_t dc_level_percentage; + uint32_t backlight_caps_initialized; + uint32_t backlight_8bit_lut[SIZEOF_BACKLIGHT_LUT]; +}; + +/* Type of feature with its runtime parameter and default value */ +struct feature_source_entry { + enum adapter_feature_id feature_id; + uint32_t default_value; + bool is_boolean_type; +}; + +/* Stores entire ASIC features by sets */ +extern uint32_t adapter_feature_set[]; + +#endif /* __DAL_ADAPTER_SERVICE_H__ */ diff --git a/drivers/gpu/drm/amd/dal/adapter/dce110/hw_ctx_adapter_service_dce110.c b/drivers/gpu/drm/amd/dal/adapter/dce110/hw_ctx_adapter_service_dce110.c new file mode 100644 index 000000000000..0994a4c8a7a7 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/dce110/hw_ctx_adapter_service_dce110.c @@ -0,0 +1,298 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#include "dal_services.h" +#include "../hw_ctx_adapter_service.h" + +#include "hw_ctx_adapter_service_dce110.h" + +#include "include/logger_interface.h" +#include "include/grph_object_id.h" + +#include "dce/dce_11_0_d.h" +#include "dce/dce_11_0_sh_mask.h" + + +#ifndef mmCC_DC_HDMI_STRAPS +#define mmCC_DC_HDMI_STRAPS 0x4819 +#define CC_DC_HDMI_STRAPS__HDMI_DISABLE_MASK 0x40 +#define CC_DC_HDMI_STRAPS__HDMI_DISABLE__SHIFT 0x6 +#define CC_DC_HDMI_STRAPS__AUDIO_STREAM_NUMBER_MASK 0x700 +#define CC_DC_HDMI_STRAPS__AUDIO_STREAM_NUMBER__SHIFT 0x8 +#endif + +static const struct graphics_object_id invalid_go = { + 0, ENUM_ID_UNKNOWN, OBJECT_TYPE_UNKNOWN, 0 +}; + +/* Macro */ +#define AUDIO_STRAPS_HDMI_ENABLE 0x2 + +#define FROM_HW_CTX(ptr) \ + container_of((ptr), struct hw_ctx_adapter_service_dce110, base) + +static const uint32_t audio_index_reg_offset[] = { + /*CZ has 3 DIGs but 4 audio endpoints*/ + mmAZF0ENDPOINT0_AZALIA_F0_CODEC_ENDPOINT_INDEX, + mmAZF0ENDPOINT1_AZALIA_F0_CODEC_ENDPOINT_INDEX, + mmAZF0ENDPOINT2_AZALIA_F0_CODEC_ENDPOINT_INDEX, + mmAZF0ENDPOINT3_AZALIA_F0_CODEC_ENDPOINT_INDEX +}; + +static const uint32_t audio_data_reg_offset[] = { + mmAZF0ENDPOINT0_AZALIA_F0_CODEC_ENDPOINT_DATA, + mmAZF0ENDPOINT1_AZALIA_F0_CODEC_ENDPOINT_DATA, + mmAZF0ENDPOINT2_AZALIA_F0_CODEC_ENDPOINT_DATA, + mmAZF0ENDPOINT3_AZALIA_F0_CODEC_ENDPOINT_DATA, +}; + +enum { + MAX_NUMBER_OF_AUDIO_PINS = 4 +}; + +static void destruct( + struct hw_ctx_adapter_service_dce110 *hw_ctx) +{ + /* There is nothing to destruct at the moment */ + dal_adapter_service_destruct_hw_ctx(&hw_ctx->base); +} + +static void destroy( + struct hw_ctx_adapter_service *ptr) +{ + struct hw_ctx_adapter_service_dce110 *hw_ctx = + FROM_HW_CTX(ptr); + + destruct(hw_ctx); + + dal_free(hw_ctx); +} + +/* + * enum_audio_object + * + * @brief enumerate audio object + * + * @param + * const struct hw_ctx_adapter_service *hw_ctx - [in] provides num of endpoints + * uint32_t index - [in] audio index + * + * @return + * grphic object id + */ +static struct graphics_object_id enum_audio_object( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index) +{ + uint32_t number_of_connected_audio_endpoints = + FROM_HW_CTX(hw_ctx)->number_of_connected_audio_endpoints; + + if (index >= number_of_connected_audio_endpoints || + number_of_connected_audio_endpoints == 0) + return invalid_go; + else + return dal_graphics_object_id_init( + AUDIO_ID_INTERNAL_AZALIA, + (enum object_enum_id)(index + 1), + OBJECT_TYPE_AUDIO); +} + +static uint32_t get_number_of_connected_audio_endpoints_multistream( + struct dal_context *dal_context) +{ + uint32_t num_connected_audio_endpoints = 0; + uint32_t i; + uint32_t default_config = + ixAZALIA_F0_CODEC_PIN_CONTROL_RESPONSE_CONFIGURATION_DEFAULT; + + /* find the total number of streams available via the + * AZALIA_F0_CODEC_PIN_CONTROL_RESPONSE_CONFIGURATION_DEFAULT + * registers (one for each pin) starting from pin 1 + * up to the max number of audio pins. + * We stop on the first pin where + * PORT_CONNECTIVITY == 1 (as instructed by HW team). + */ + for (i = 0; i < MAX_NUMBER_OF_AUDIO_PINS; i++) { + uint32_t value = 0; + + set_reg_field_value(value, + default_config, + AZALIA_F0_CODEC_ENDPOINT_INDEX, + AZALIA_ENDPOINT_REG_INDEX); + + dal_write_reg(dal_context, audio_index_reg_offset[i], value); + + value = 0; + value = dal_read_reg(dal_context, audio_data_reg_offset[i]); + + /* 1 means not supported*/ + if (get_reg_field_value(value, + AZALIA_F0_CODEC_PIN_CONTROL_RESPONSE_CONFIGURATION_DEFAULT, + PORT_CONNECTIVITY) == 1) + break; + + num_connected_audio_endpoints++; + } + + return num_connected_audio_endpoints; + +} + +/* + * get_number_of_connected_audio_endpoints + */ +static uint32_t get_number_of_connected_audio_endpoints( + struct hw_ctx_adapter_service *hw_ctx) +{ + uint32_t addr = mmCC_DC_HDMI_STRAPS; + uint32_t value = 0; + uint32_t field = 0; + + if (hw_ctx->cached_audio_straps == AUDIO_STRAPS_NOT_ALLOWED) + /* audio straps indicate no audio supported */ + return 0; + + value = dal_read_reg(hw_ctx->dal_context, addr); + + field = get_reg_field_value( + value, CC_DC_HDMI_STRAPS, AUDIO_STREAM_NUMBER); + if (field == 1) + /* multi streams not supported */ + return 1; + else if (field == 0) + /* multi streams supported */ + return get_number_of_connected_audio_endpoints_multistream( + hw_ctx->dal_context); + + /* unexpected value */ + ASSERT_CRITICAL(false); + return field; +} + + +/* + * power_up + * + * @brief + * Determine and cache audio support from register. + * + * @param + * struct hw_ctx_adapter_service *hw_ctx - [in] adapter service hw context + * + * @return + * true if succeed, false otherwise + */ +static bool power_up( + struct hw_ctx_adapter_service *hw_ctx) +{ + struct hw_ctx_adapter_service_dce110 *hw_ctx_dce11 = + FROM_HW_CTX(hw_ctx); + /* Allow DP audio all the time + * without additional pinstrap check on Fusion */ + hw_ctx->cached_audio_straps = AUDIO_STRAPS_DP_AUDIO_ALLOWED; + + { + uint32_t value = 0; + uint32_t field = 0; + + value = dal_read_reg(hw_ctx->dal_context, mmCC_DC_HDMI_STRAPS); + field = get_reg_field_value( + value, CC_DC_HDMI_STRAPS, HDMI_DISABLE); + if (field == 0) { + + value = dal_read_reg( + hw_ctx->dal_context, mmDC_PINSTRAPS); + + field = get_reg_field_value( + value, DC_PINSTRAPS, DC_PINSTRAPS_AUDIO); + if (field & AUDIO_STRAPS_HDMI_ENABLE) + /* allow HDMI audio, DP audio, + * and audio via dongle */ + hw_ctx->cached_audio_straps = + AUDIO_STRAPS_DP_HDMI_AUDIO; + } + } + + /* get the number of connected audio endpoints */ + hw_ctx_dce11->number_of_connected_audio_endpoints = + get_number_of_connected_audio_endpoints(hw_ctx); + + return true; +} + +static void update_audio_connectivity( + struct hw_ctx_adapter_service *hw_ctx, + uint32_t number_of_audio_capable_display_path, + uint32_t number_of_controllers) +{ + /* this one should be empty on DCE110 */ +} + +static const struct hw_ctx_adapter_service_funcs funcs = { + .destroy = destroy, + .power_up = power_up, + .enum_fake_path_resource = NULL, + .enum_stereo_sync_object = NULL, + .enum_sync_output_object = NULL, + .enum_audio_object = enum_audio_object, + .update_audio_connectivity = update_audio_connectivity +}; + +static bool construct( + struct hw_ctx_adapter_service_dce110 *hw_ctx, + struct dal_context *dal_context) +{ + if (!dal_adapter_service_construct_hw_ctx(&hw_ctx->base, dal_context)) { + ASSERT_CRITICAL(false); + return false; + } + + hw_ctx->base.funcs = &funcs; + hw_ctx->number_of_connected_audio_endpoints = 0; + + return true; +} + +struct hw_ctx_adapter_service * + dal_adapter_service_create_hw_ctx_dce110( + struct dal_context *dal_context) +{ + struct hw_ctx_adapter_service_dce110 *hw_ctx = + dal_alloc(sizeof(struct hw_ctx_adapter_service_dce110)); + + if (!hw_ctx) { + ASSERT_CRITICAL(false); + return NULL; + } + + if (construct(hw_ctx, dal_context)) + return &hw_ctx->base; + + ASSERT_CRITICAL(false); + + dal_free(hw_ctx); + + return NULL; +} diff --git a/drivers/gpu/drm/amd/dal/adapter/dce110/hw_ctx_adapter_service_dce110.h b/drivers/gpu/drm/amd/dal/adapter/dce110/hw_ctx_adapter_service_dce110.h new file mode 100644 index 000000000000..475a7a08d46b --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/dce110/hw_ctx_adapter_service_dce110.h @@ -0,0 +1,38 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_HW_CTX_ADAPTER_SERVICE_DCE110_H__ +#define __DAL_HW_CTX_ADAPTER_SERVICE_DCE110_H__ + +struct hw_ctx_adapter_service_dce110 { + struct hw_ctx_adapter_service base; + uint32_t number_of_connected_audio_endpoints; +}; + +struct hw_ctx_adapter_service * + dal_adapter_service_create_hw_ctx_dce110( + struct dal_context *dal_context); + +#endif /* __DAL_HW_CTX_ADAPTER_SERVICE_DCE110_H__ */ diff --git a/drivers/gpu/drm/amd/dal/adapter/hw_ctx_adapter_service.c b/drivers/gpu/drm/amd/dal/adapter/hw_ctx_adapter_service.c new file mode 100644 index 000000000000..99d76e83dacd --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/hw_ctx_adapter_service.c @@ -0,0 +1,164 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#include "dal_services.h" +#include "include/adapter_service_types.h" +#include "include/grph_object_id.h" +#include "hw_ctx_adapter_service.h" + +static const struct graphics_object_id invalid_go = { + 0, ENUM_ID_UNKNOWN, OBJECT_TYPE_UNKNOWN +}; + +static void destroy( + struct hw_ctx_adapter_service *hw_ctx) +{ + /* Attention! + * You must override impl method in derived class */ + BREAK_TO_DEBUGGER(); +} + +static bool power_up( + struct hw_ctx_adapter_service *hw_ctx) +{ + /* Attention! + * You must override impl method in derived class */ + BREAK_TO_DEBUGGER(); + + return false; +} + +static struct graphics_object_id enum_fake_path_resource( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index) +{ + return invalid_go; +} + +static struct graphics_object_id enum_stereo_sync_object( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index) +{ + return invalid_go; +} + +static struct graphics_object_id enum_sync_output_object( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index) +{ + return invalid_go; +} + +static struct graphics_object_id enum_audio_object( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index) +{ + /* by default, we only allow one audio */ + + if (index > 0) + return invalid_go; + else if (hw_ctx->cached_audio_straps == AUDIO_STRAPS_NOT_ALLOWED) + return invalid_go; + else + return dal_graphics_object_id_init( + AUDIO_ID_INTERNAL_AZALIA, + ENUM_ID_1, + OBJECT_TYPE_AUDIO); +} + +static void update_audio_connectivity( + struct hw_ctx_adapter_service *hw_ctx, + uint32_t number_of_audio_capable_display_path, + uint32_t number_of_controllers) +{ + /* Attention! + * You must override impl method in derived class */ + BREAK_TO_DEBUGGER(); +} + +static const struct hw_ctx_adapter_service_funcs funcs = { + destroy, + power_up, + enum_fake_path_resource, + enum_stereo_sync_object, + enum_sync_output_object, + enum_audio_object, + update_audio_connectivity +}; + +bool dal_adapter_service_construct_hw_ctx( + struct hw_ctx_adapter_service *hw_ctx, + struct dal_context *dal_context) +{ + + hw_ctx->dal_context = dal_context; + hw_ctx->funcs = &funcs; + hw_ctx->cached_audio_straps = AUDIO_STRAPS_NOT_ALLOWED; + + return true; +} + +union audio_support dal_adapter_service_hw_ctx_get_audio_support( + const struct hw_ctx_adapter_service *hw_ctx) +{ + union audio_support result; + + result.raw = 0; + + switch (hw_ctx->cached_audio_straps) { + case AUDIO_STRAPS_DP_HDMI_AUDIO: + result.bits.HDMI_AUDIO_NATIVE = true; + /* do not break ! */ + case AUDIO_STRAPS_DP_HDMI_AUDIO_ON_DONGLE: + result.bits.HDMI_AUDIO_ON_DONGLE = true; + /* do not break ! */ + case AUDIO_STRAPS_DP_AUDIO_ALLOWED: + result.bits.DP_AUDIO = true; + break; + default: + break; + } + + return result; +} + +void dal_adapter_service_destruct_hw_ctx( + struct hw_ctx_adapter_service *hw_ctx) +{ + /* There is nothing to destruct at the moment */ +} + +void dal_adapter_service_destroy_hw_ctx( + struct hw_ctx_adapter_service **ptr) +{ + if (!ptr || !*ptr) { + BREAK_TO_DEBUGGER(); + return; + } + + (*ptr)->funcs->destroy(*ptr); + + *ptr = NULL; +} diff --git a/drivers/gpu/drm/amd/dal/adapter/hw_ctx_adapter_service.h b/drivers/gpu/drm/amd/dal/adapter/hw_ctx_adapter_service.h new file mode 100644 index 000000000000..ea5e91c4b713 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/hw_ctx_adapter_service.h @@ -0,0 +1,86 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_HW_CTX_ADAPTER_SERVICE_H__ +#define __DAL_HW_CTX_ADAPTER_SERVICE_H__ + +enum audio_straps { + AUDIO_STRAPS_NOT_ALLOWED = 0, + AUDIO_STRAPS_DP_AUDIO_ALLOWED, + AUDIO_STRAPS_DP_HDMI_AUDIO_ON_DONGLE, + AUDIO_STRAPS_DP_HDMI_AUDIO +}; + +struct hw_ctx_adapter_service; + +struct hw_ctx_adapter_service_funcs { + void (*destroy)( + struct hw_ctx_adapter_service *hw_ctx); + /* Initializes relevant HW registers + * and caches relevant data from HW registers */ + bool (*power_up)( + struct hw_ctx_adapter_service *hw_ctx); + /* Enumerate fake path resources */ + struct graphics_object_id (*enum_fake_path_resource)( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index); + /* Enumerate stereo sync objects */ + struct graphics_object_id (*enum_stereo_sync_object)( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index); + /* Enumerate (H/V) sync output objects */ + struct graphics_object_id (*enum_sync_output_object)( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index); + /* Enumerate audio objects */ + struct graphics_object_id (*enum_audio_object)( + const struct hw_ctx_adapter_service *hw_ctx, + uint32_t index); + void (*update_audio_connectivity)( + struct hw_ctx_adapter_service *hw_ctx, + uint32_t number_of_audio_capable_display_path, + uint32_t number_of_controllers); +}; + +struct hw_ctx_adapter_service { + struct dal_context *dal_context; + const struct hw_ctx_adapter_service_funcs *funcs; + enum audio_straps cached_audio_straps; +}; + +bool dal_adapter_service_construct_hw_ctx( + struct hw_ctx_adapter_service *hw_ctx, + struct dal_context *dal_context); + +union audio_support dal_adapter_service_hw_ctx_get_audio_support( + const struct hw_ctx_adapter_service *hw_ctx); + +void dal_adapter_service_destruct_hw_ctx( + struct hw_ctx_adapter_service *hw_ctx); + +void dal_adapter_service_destroy_hw_ctx( + struct hw_ctx_adapter_service **ptr); + +#endif /* __DAL_HW_CTX_ADAPTER_SERVICE_H__ */ diff --git a/drivers/gpu/drm/amd/dal/adapter/wireless_data_source.c b/drivers/gpu/drm/amd/dal/adapter/wireless_data_source.c new file mode 100644 index 000000000000..c77adc490e8b --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/wireless_data_source.c @@ -0,0 +1,209 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + + +#include "dal_services.h" +#include "atom.h" +#include "adapter_service.h" +#include "wireless_data_source.h" + + +/*construct wireless data*/ +bool wireless_data_init(struct wireless_data *data, + struct bios_parser *bp, + struct wireless_init_data *init_data) +{ + struct firmware_info info; + + if (data == NULL || bp == NULL || init_data == NULL) { + ASSERT_CRITICAL(false); + return false; + } + + data->miracast_connector_enable = false; + data->wireless_disp_path_enable = false; + data->wireless_enable = false; + + /* Wireless it not supported if VCE is not supported */ + if (!init_data->vce_supported) + return true; + + if (init_data->miracast_target_required) + data->miracast_connector_enable = true; + + /* + * If override is in place for platform support, we will both + * enable wireless display as a feature (i.e. CCC aspect) and + * enable the wireless display path without any further checks. + */ + if (init_data->platform_override) { + data->wireless_enable = true; + data->wireless_disp_path_enable = true; + } else { + /* + * Check if SBIOS sets remote display enable, exposed + * through VBIOS. This is only valid for APU, not dGPU + */ + dal_bios_parser_get_firmware_info(bp, &info); + + if ((REMOTE_DISPLAY_ENABLE == + info.remote_display_config) && + init_data->fusion) { + data->wireless_enable = true; + data->wireless_disp_path_enable = true; + } + } + + /* + * If remote display path override is enabled, we enable just the + * remote display path. This is mainly used for testing purposes + */ + if (init_data->remote_disp_path_override) + data->wireless_disp_path_enable = true; + + return true; +} + +uint8_t wireless_get_clocks_num( + struct adapter_service *as) +{ + if (as->wireless_data.wireless_enable || + as->wireless_data.wireless_disp_path_enable) + return 1; + else + return 0; +} + +static uint8_t wireless_get_encoders_num( + struct adapter_service *as) +{ + if (as->wireless_data.wireless_enable || + as->wireless_data.wireless_disp_path_enable) + return 1; + else + return 0; +} + +uint8_t wireless_get_connectors_num( + struct adapter_service *as) +{ + uint8_t wireless_connectors_num = 0; + + if (as->wireless_data.wireless_enable && + as->wireless_data.miracast_connector_enable) + wireless_connectors_num++; + + if (as->wireless_data.wireless_disp_path_enable) + wireless_connectors_num++; + + return wireless_connectors_num; +} + +struct graphics_object_id wireless_get_connector_id( + struct adapter_service *as, + uint8_t index) +{ + struct graphics_object_id unknown_object_id = + dal_graphics_object_id_init( + 0, + ENUM_ID_UNKNOWN, + OBJECT_TYPE_UNKNOWN); + + if (!as->wireless_data.wireless_enable && + !as->wireless_data.wireless_disp_path_enable) + return unknown_object_id; + + else if (!as->wireless_data.miracast_connector_enable) + return dal_graphics_object_id_init( + CONNECTOR_ID_WIRELESS, + ENUM_ID_1, + OBJECT_TYPE_CONNECTOR); + + switch (index) { + case 0: + return dal_graphics_object_id_init( + CONNECTOR_ID_WIRELESS, + ENUM_ID_1, + OBJECT_TYPE_CONNECTOR); + break; + case 1: + return dal_graphics_object_id_init( + CONNECTOR_ID_MIRACAST, + ENUM_ID_1, + OBJECT_TYPE_CONNECTOR); + break; + default: + return unknown_object_id; + } +} + +uint8_t wireless_get_srcs_num( + struct adapter_service *as, + struct graphics_object_id id) +{ + switch (id.type) { + case OBJECT_TYPE_CONNECTOR: + return wireless_get_encoders_num(as); + case OBJECT_TYPE_ENCODER: + return 1; + + default: + ASSERT_CRITICAL(false); + break; + } + + return 0; +} + +struct graphics_object_id wireless_get_src_obj_id( + struct adapter_service *as, + struct graphics_object_id id, + uint8_t index) +{ + if (index < wireless_get_srcs_num(as, id)) { + switch (id.type) { + case OBJECT_TYPE_CONNECTOR: + return dal_graphics_object_id_init( + ENCODER_ID_INTERNAL_WIRELESS, + ENUM_ID_1, + OBJECT_TYPE_ENCODER); + break; + case OBJECT_TYPE_ENCODER: + return dal_graphics_object_id_init( + 0, + ENUM_ID_1, + OBJECT_TYPE_GPU); + break; + default: + ASSERT_CRITICAL(false); + break; + } + } + + return dal_graphics_object_id_init( + 0, + ENUM_ID_UNKNOWN, + OBJECT_TYPE_UNKNOWN); +} diff --git a/drivers/gpu/drm/amd/dal/adapter/wireless_data_source.h b/drivers/gpu/drm/amd/dal/adapter/wireless_data_source.h new file mode 100644 index 000000000000..54b140a38df9 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/adapter/wireless_data_source.h @@ -0,0 +1,80 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_WIRELESS_DATA_SOURCE_H__ +#define __DAL_WIRELESS_DATA_SOURCE_H__ + +/* Include */ +#include "include/grph_object_id.h" + +/* + * Forward declaration + */ +struct adapter_service; +struct bios_parser; + +/* Wireless data init structure */ +struct wireless_init_data { + bool fusion; /* Fusion flag */ + bool platform_override; /* Override for platform BIOS option */ + bool remote_disp_path_override; /* Override enabling wireless path */ + bool vce_supported; /* Existence of VCE block on this DCE */ + bool miracast_target_required; /* OS requires Miracast target */ +}; + +/* Wireless data */ +struct wireless_data { + bool wireless_enable; + bool wireless_disp_path_enable; + bool miracast_connector_enable; +}; + + +/*construct wireless data*/ +bool wireless_data_init( + struct wireless_data *data, + struct bios_parser *bp, + struct wireless_init_data *init_data); + +uint8_t wireless_get_clocks_num( + struct adapter_service *as); + +uint8_t wireless_get_connectors_num( + struct adapter_service *as); + +struct graphics_object_id wireless_get_connector_id( + struct adapter_service *as, + uint8_t connector_index); + +uint8_t wireless_get_srcs_num( + struct adapter_service *as, + struct graphics_object_id id); + +struct graphics_object_id wireless_get_src_obj_id( + struct adapter_service *as, + struct graphics_object_id id, + uint8_t index); + +#endif /* __DAL_WIRELESS_DATA_SOURCE_H__ */ diff --git a/drivers/gpu/drm/amd/dal/include/adapter_service_interface.h b/drivers/gpu/drm/amd/dal/include/adapter_service_interface.h new file mode 100644 index 000000000000..0f84e7119e1a --- /dev/null +++ b/drivers/gpu/drm/amd/dal/include/adapter_service_interface.h @@ -0,0 +1,628 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_ADAPTER_SERVICE_INTERFACE_H__ +#define __DAL_ADAPTER_SERVICE_INTERFACE_H__ + +#include "grph_object_ctrl_defs.h" +#include "gpio_interface.h" +#include "ddc_interface.h" +#include "irq_interface.h" +#include "bios_parser_interface.h" +#include "adapter_service_types.h" +#include "dal_types.h" +#include "asic_capability_types.h" + +/* forward declaration */ +struct bios_parser; +struct i2caux; +struct adapter_service; + + +/* + * enum adapter_feature_id + * + * Definition of all adapter features + * + * The enumeration defines the IDs of all the adapter features. The enum + * organizes all the features into several feature sets. The range of feature + * set N is from ((N-1)*32+1) to (N*32). Because there may be three value-type + * feature, boolean-type, unsigned char-type and unsinged int-type, the number + * of features should be 32, 4 and 1 in the feature set accordingly. + * + * In a boolean-type feature set N, the enumeration value of the feature should + * be ((N-1)*32+1), ((N-1)*32+2), ..., (N*32). + * + * In an unsigned char-type feature set N, the enumeration value of the + * feature should be ((N-1)*32+1), ((N-1)*32+8), ((N-1)*32+16) and (N*32). + * + * In an unsigned int-type feature set N, the enumeration value of the feature + * should be ((N-1)*32+1) + */ +enum adapter_feature_id { + FEATURE_UNKNOWN = 0, + + /* Boolean set, up to 32 entries */ + FEATURE_ENABLE_HW_EDID_POLLING = 1, + FEATURE_SET_01_START = FEATURE_ENABLE_HW_EDID_POLLING, + FEATURE_DP_SINK_DETECT_POLL_DATA_PIN, + FEATURE_UNDERFLOW_INTERRUPT, + FEATURE_ALLOW_WATERMARK_ADJUSTMENT, + FEATURE_LIGHT_SLEEP, + FEATURE_DCP_DITHER_FRAME_RANDOM_ENABLE, + FEATURE_DCP_DITHER_RGB_RANDOM_ENABLE, + FEATURE_DCP_DITHER_HIGH_PASS_RANDOM_ENABLE, + FEATURE_DETECT_REQUIRE_HPD_HIGH, + FEATURE_LINE_BUFFER_ENHANCED_PIXEL_DEPTH, /* 10th */ + FEATURE_MAXIMIZE_URGENCY_WATERMARKS, + FEATURE_MAXIMIZE_STUTTER_MARKS, + FEATURE_MAXIMIZE_NBP_MARKS, + FEATURE_RESTORE_USAGE_I2C_SW_ENGINE, + FEATURE_USE_MAX_DISPLAY_CLK, + FEATURE_ALLOW_EDP_RESOURCE_SHARING, + FEATURE_SUPPORT_DP_YUV, + FEATURE_SUPPORT_DP_Y_ONLY, + FEATURE_DISABLE_DP_GTC_SYNC, + FEATURE_NO_HPD_LOW_POLLING_VCC_OFF, /* 20th */ + FEATURE_ENABLE_DFS_BYPASS, + FEATURE_LB_HIGH_RESOLUTION, + FEATURE_DP_DISPLAY_FORCE_SS_ENABLE, + FEATURE_REPORT_CE_MODE_ONLY, + FEATURE_ALLOW_OPTIMIZED_MODE_AS_DEFAULT, + FEATURE_DDC_READ_FORCE_REPEATED_START, + FEATURE_FORCE_TIMING_RESYNC, + FEATURE_TMDS_DISABLE_DITHERING, + FEATURE_HDMI_DISABLE_DITHERING, + FEATURE_DP_DISABLE_DITHERING, /* 30th */ + FEATURE_EMBEDDED_DISABLE_DITHERING, + FEATURE_DISABLE_AZ_CLOCK_GATING, /* 32th. This set is full */ + FEATURE_SET_01_END = FEATURE_SET_01_START + 31, + + /* Boolean set, up to 32 entries */ + FEATURE_WIRELESS_ENABLE = FEATURE_SET_01_END + 1, + FEATURE_SET_02_START = FEATURE_WIRELESS_ENABLE, + FEATURE_WIRELESS_FULL_TIMING_ADJUSTMENT, + FEATURE_WIRELESS_LIMIT_720P, + FEATURE_WIRELESS_ENABLE_COMPRESSED_AUDIO, + FEATURE_WIRELESS_INCLUDE_UNVERIFIED_TIMINGS, + FEATURE_MODIFY_TIMINGS_FOR_WIRELESS, + FEATURE_ALLOW_SELF_REFRESH, + FEATURE_ALLOW_DYNAMIC_PIXEL_ENCODING_CHANGE, + FEATURE_ALLOW_HSYNC_VSYNC_ADJUSTMENT, + FEATURE_FORCE_PSR, /* 10th */ + FEATURE_PREFER_3D_TIMING, + FEATURE_VARI_BRIGHT_ENABLE, + FEATURE_PSR_ENABLE, + FEATURE_EDID_STRESS_READ, + FEATURE_DP_FRAME_PACK_STEREO3D, + FEATURE_ALLOW_HDMI_WITHOUT_AUDIO, + FEATURE_RESTORE_USAGE_I2C_SW_ENGING, + FEATURE_ABM_2_0, + FEATURE_SUPPORT_MIRABILIS, + FEATURE_LOAD_DMCU_FIRMWARE, /* 20th */ + FEATURE_ENABLE_GPU_SCALING, + FEATURE_DONGLE_SINK_COUNT_CHECK, + FEATURE_INSTANT_UP_SCALE_DOWN_SCALE, + FEATURE_TILED_DISPLAY, + FEATURE_CHANGE_I2C_SPEED_CONTROL, + FEATURE_REPORT_SINGLE_SELECTED_TIMING, + FEATURE_ALLOW_HDMI_HIGH_CLK_DP_DONGLE, + FEATURE_SUPPORT_EXTERNAL_PANEL_DRR, + FEATURE_SUPPORT_SMOOTH_BRIGHTNESS, + FEATURE_ALLOW_DIRECT_MEMORY_ACCESS_TRIG, /* 30th */ + FEATURE_POWER_GATING_LB_PORTION, /* 31nd. One more left. */ + FEATURE_SET_02_END = FEATURE_SET_02_START + 31, + + /* UInt set, 1 entry: DCP Bit Depth Reduction Mode */ + FEATURE_DCP_BIT_DEPTH_REDUCTION_MODE = FEATURE_SET_02_END + 1, + FEATURE_SET_03_START = FEATURE_DCP_BIT_DEPTH_REDUCTION_MODE, + FEATURE_SET_03_END = FEATURE_SET_03_START + 31, + + /* UInt set, 1 entry: DCP Dither Mode */ + FEATURE_DCP_DITHER_MODE = FEATURE_SET_03_END + 1, + FEATURE_SET_04_START = FEATURE_DCP_DITHER_MODE, + FEATURE_SET_04_END = FEATURE_SET_04_START + 31, + + /* UInt set, 1 entry: DCP Programming WA(workaround) */ + FEATURE_DCP_PROGRAMMING_WA = FEATURE_SET_04_END + 1, + FEATURE_SET_06_START = FEATURE_DCP_PROGRAMMING_WA, + FEATURE_SET_06_END = FEATURE_SET_06_START + 31, + + /* UInt set, 1 entry: Maximum co-functional non-DP displays */ + FEATURE_MAX_COFUNC_NON_DP_DISPLAYS = FEATURE_SET_06_END + 1, + FEATURE_SET_07_START = FEATURE_MAX_COFUNC_NON_DP_DISPLAYS, + FEATURE_SET_07_END = FEATURE_SET_07_START + 31, + + /* UInt set, 1 entry: Number of supported HDMI connection */ + FEATURE_SUPPORTED_HDMI_CONNECTION_NUM = FEATURE_SET_07_END + 1, + FEATURE_SET_08_START = FEATURE_SUPPORTED_HDMI_CONNECTION_NUM, + FEATURE_SET_08_END = FEATURE_SET_08_START + 31, + + /* UInt set, 1 entry: Maximum number of controllers */ + FEATURE_MAX_CONTROLLER_NUM = FEATURE_SET_08_END + 1, + FEATURE_SET_09_START = FEATURE_MAX_CONTROLLER_NUM, + FEATURE_SET_09_END = FEATURE_SET_09_START + 31, + + /* UInt set, 1 entry: Type of DRR support */ + FEATURE_DRR_SUPPORT = FEATURE_SET_09_END + 1, + FEATURE_SET_10_START = FEATURE_DRR_SUPPORT, + FEATURE_SET_10_END = FEATURE_SET_10_START + 31, + + /* UInt set, 1 entry: Stutter mode support */ + FEATURE_STUTTER_MODE = FEATURE_SET_10_END + 1, + FEATURE_SET_11_START = FEATURE_STUTTER_MODE, + FEATURE_SET_11_END = FEATURE_SET_11_START + 31, + + /* UInt set, 1 entry: Measure PSR setup time */ + FEATURE_PSR_SETUP_TIME_TEST = FEATURE_SET_11_END + 1, + FEATURE_SET_12_START = FEATURE_PSR_SETUP_TIME_TEST, + FEATURE_SET_12_END = FEATURE_SET_12_START + 31, + + /* Boolean set, up to 32 entries */ + FEATURE_POWER_GATING_PIPE_IN_TILE = FEATURE_SET_12_END + 1, + FEATURE_SET_13_START = FEATURE_POWER_GATING_PIPE_IN_TILE, + FEATURE_USE_PPLIB, + FEATURE_DISABLE_LPT_SUPPORT, + FEATURE_DUMMY_FBC_BACKEND, + FEATURE_DISABLE_FBC_COMP_CLK_GATE, + FEATURE_DPMS_AUDIO_ENDPOINT_CONTROL, + FEATURE_PIXEL_PERFECT_OUTPUT, + FEATURE_8BPP_SUPPORTED, + FEATURE_SET_13_END = FEATURE_SET_13_START + 31, + + /* UInt set, 1 entry: Display preferred view + * 0: no preferred view + * 1: native and preferred timing of embedded display will have high + * priority, so other displays will support it always + */ + FEATURE_DISPLAY_PREFERRED_VIEW = FEATURE_SET_13_END + 1, + FEATURE_SET_15_START = FEATURE_DISPLAY_PREFERRED_VIEW, + FEATURE_SET_15_END = FEATURE_SET_15_START + 31, + + /* UInt set, 1 entry: DAL optimization */ + FEATURE_OPTIMIZATION = FEATURE_SET_15_END + 1, + FEATURE_SET_16_START = FEATURE_OPTIMIZATION, + FEATURE_SET_16_END = FEATURE_SET_16_START + 31, + + /* UInt set, 1 entry: Performance measurement */ + FEATURE_PERF_MEASURE = FEATURE_SET_16_END + 1, + FEATURE_SET_17_START = FEATURE_PERF_MEASURE, + FEATURE_SET_17_END = FEATURE_SET_17_START + 31, + + /* UInt set, 1 entry: Minimum backlight value [0-255] */ + FEATURE_MIN_BACKLIGHT_LEVEL = FEATURE_SET_17_END + 1, + FEATURE_SET_18_START = FEATURE_MIN_BACKLIGHT_LEVEL, + FEATURE_SET_18_END = FEATURE_SET_18_START + 31, + + /* UInt set, 1 entry: Maximum backlight value [0-255] */ + FEATURE_MAX_BACKLIGHT_LEVEL = FEATURE_SET_18_END + 1, + FEATURE_SET_19_START = FEATURE_MAX_BACKLIGHT_LEVEL, + FEATURE_SET_19_END = FEATURE_SET_19_START + 31, + + /* UInt set, 1 entry: AMB setting + * + * Each byte will control the ABM configuration to use for a specific + * ABM level. + * + * HW team provided 12 different ABM min/max reduction pairs to choose + * between for each ABM level. + * + * ABM level Byte Setting + * 1 0 Default = 0 (setting 3), can be override to 1-12 + * 2 1 Default = 0 (setting 7), can be override to 1-12 + * 3 2 Default = 0 (setting 8), can be override to 1-12 + * 4 3 Default = 0 (setting 10), can be override to 1-12 + * + * For example, + * FEATURE_PREFERRED_ABM_CONFIG_SET = 0x0C060500, this represents: + * ABM level 1 use default setting (setting 3) + * ABM level 2 uses setting 5 + * ABM level 3 uses setting 6 + * ABM level 4 uses setting 12 + * Internal use only! + */ + FEATURE_PREFERRED_ABM_CONFIG_SET = FEATURE_SET_19_END + 1, + FEATURE_SET_20_START = FEATURE_PREFERRED_ABM_CONFIG_SET, + FEATURE_SET_20_END = FEATURE_SET_20_START + 31, + + /* UInt set, 1 entry: Change SW I2C speed */ + FEATURE_CHANGE_SW_I2C_SPEED = FEATURE_SET_20_END + 1, + FEATURE_SET_21_START = FEATURE_CHANGE_SW_I2C_SPEED, + FEATURE_SET_21_END = FEATURE_SET_21_START + 31, + + /* UInt set, 1 entry: Change HW I2C speed */ + FEATURE_CHANGE_HW_I2C_SPEED = FEATURE_SET_21_END + 1, + FEATURE_SET_22_START = FEATURE_CHANGE_HW_I2C_SPEED, + FEATURE_SET_22_END = FEATURE_SET_22_START + 31, + + /* UInt set, 1 entry: + * When PSR issue occurs, it is sometimes hard to debug since the + * failure occurs immediately at boot. Use this setting to skip or + * postpone PSR functionality and re-enable through DSAT. */ + FEATURE_DEFAULT_PSR_LEVEL = FEATURE_SET_22_END + 1, + FEATURE_SET_23_START = FEATURE_DEFAULT_PSR_LEVEL, + FEATURE_SET_23_END = FEATURE_SET_23_START + 31, + + /* UInt set, 1 entry: Allowed pixel clock range for LVDS */ + FEATURE_LVDS_SAFE_PIXEL_CLOCK_RANGE = FEATURE_SET_23_END + 1, + FEATURE_SET_24_START = FEATURE_LVDS_SAFE_PIXEL_CLOCK_RANGE, + FEATURE_SET_24_END = FEATURE_SET_24_START + 31, + + /* UInt set, 1 entry: Max number of clock sources */ + FEATURE_MAX_CLOCK_SOURCE_NUM = FEATURE_SET_24_END + 1, + FEATURE_SET_25_START = FEATURE_MAX_CLOCK_SOURCE_NUM, + FEATURE_SET_25_END = FEATURE_SET_25_START + 31, + + /* UInt set, 1 entry: Select the ABM configuration to use. + * + * This feature set is used to allow packaging option to be defined + * to allow OEM to select between the default ABM configuration or + * alternative predefined configurations that may be more aggressive. + * + * Note that this regkey is meant for external use to select the + * configuration OEM wants. Whereas the other PREFERRED_ABM_CONFIG_SET + * key is only used for internal use and allows full reconfiguration. + */ + FEATURE_ABM_CONFIG = FEATURE_SET_25_END + 1, + FEATURE_SET_26_START = FEATURE_ABM_CONFIG, + FEATURE_SET_26_END = FEATURE_SET_26_START + 31, + + /* UInt set, 1 entry: Select the default speed in which smooth + * brightness feature should converge towards target backlight level. + * + * For example, a setting of 500 means it takes 500ms to transition + * from current backlight level to the new requested backlight level. + */ + FEATURE_SMOOTH_BRTN_ADJ_TIME_IN_MS = FEATURE_SET_26_END + 1, + FEATURE_SET_27_START = FEATURE_SMOOTH_BRTN_ADJ_TIME_IN_MS, + FEATURE_SET_27_END = FEATURE_SET_27_START + 31, + + /* Set 28: UInt set, 1 entry: Allow runtime parameter to force specific + * Static Screen Event triggers for test purposes. */ + FEATURE_FORCE_STATIC_SCREEN_EVENT_TRIGGERS = FEATURE_SET_27_END + 1, + FEATURE_SET_28_START = FEATURE_FORCE_STATIC_SCREEN_EVENT_TRIGGERS, + FEATURE_SET_28_END = FEATURE_SET_28_START + 31, + + FEATURE_MAXIMUM +}; + +/* Adapter Service type of DRR support*/ +enum as_drr_support { + AS_DRR_SUPPORT_DISABLED = 0x0, + AS_DRR_SUPPORT_ENABLED = 0x1, + AS_DRR_SUPPORT_MIN_FORCED_FPS = 0xA +}; + +/* Adapter service initialize data structure*/ +struct as_init_data { + struct hw_asic_id hw_init_data; + struct bp_init_data bp_init_data; + struct dal_context *dal_context; + struct bdf_info bdf_info; + struct dal_override_parameters *display_param; +}; + +/* Create adapter service */ +struct adapter_service *dal_adapter_service_create( + struct as_init_data *init_data); + +/* Destroy adapter service and objects it contains */ +void dal_adapter_service_destroy( + struct adapter_service **as); + +/* Get the DCE version of current ASIC */ +enum dce_version dal_adapter_service_get_dce_version( + const struct adapter_service *as); + +/* Get firmware information from BIOS */ +bool dal_adapter_service_get_firmware_info( + struct adapter_service *as, + struct firmware_info *info); + + +/* functions to get a total number of objects of specific type */ +uint8_t dal_adapter_service_get_connectors_num( + struct adapter_service *as); + +/* Get number of controllers */ +uint8_t dal_adapter_service_get_controllers_num( + struct adapter_service *as); + +/* Get number of clock sources */ +uint8_t dal_adapter_service_get_clock_sources_num( + struct adapter_service *as); + +/* Get number of controllers */ +uint8_t dal_adapter_service_get_func_controllers_num( + struct adapter_service *as); + +/* Get number of stream engines */ +uint8_t dal_adapter_service_get_stream_engines_num( + struct adapter_service *as); + +/* functions to get object id based on object index */ +struct graphics_object_id dal_adapter_service_get_connector_obj_id( + struct adapter_service *as, + uint8_t connector_index); + +/* Get number of spread spectrum entries from BIOS */ +uint32_t dal_adapter_service_get_ss_info_num( + struct adapter_service *as, + enum as_signal_type signal); + +/* Get spread spectrum info from BIOS */ +bool dal_adapter_service_get_ss_info( + struct adapter_service *as, + enum as_signal_type signal, + uint32_t idx, + struct spread_spectrum_info *info); + +/* Check if DFS bypass is enabled */ +bool dal_adapter_service_is_dfs_bypass_enabled(struct adapter_service *as); + +/* Get memory controller latency */ +uint32_t dal_adapter_service_get_mc_latency( + struct adapter_service *as); + +/* Get the video RAM bit width set on the ASIC */ +uint32_t dal_adapter_service_get_asic_vram_bit_width( + struct adapter_service *as); + +/* Get the bug flags set on this ASIC */ +struct asic_bugs dal_adapter_service_get_asic_bugs( + struct adapter_service *as); + +/* Get efficiency of DRAM */ +uint32_t dal_adapter_service_get_dram_bandwidth_efficiency( + struct adapter_service *as); + +/* Get multiplier for the memory type */ +uint32_t dal_adapter_service_get_memory_type_multiplier( + struct adapter_service *as); + +/* Get parameters for bandwidth tuning */ +bool dal_adapter_service_get_bandwidth_tuning_params( + struct adapter_service *as, + union bandwidth_tuning_params *params); + +/* Get integrated information on BIOS */ +bool dal_adapter_service_get_integrated_info( + struct adapter_service *as, + struct integrated_info *info); + +/* Return if a given feature is supported by the ASIC */ +bool dal_adapter_service_is_feature_supported( + enum adapter_feature_id feature_id); + +/* Get the cached value of a given feature */ +bool dal_adapter_service_get_feature_value( + const enum adapter_feature_id feature_id, + void *data, + uint32_t size); + +/* Get a copy of ASIC feature flags */ +struct asic_feature_flags dal_adapter_service_get_feature_flags( + struct adapter_service *as); + +/* Obtain DDC */ +struct ddc *dal_adapter_service_obtain_ddc( + struct adapter_service *as, + struct graphics_object_id id); + +/* Release DDC */ +void dal_adapter_service_release_ddc( + struct adapter_service *as, + struct ddc *ddc); + +/* Obtain HPD interrupt request */ +struct irq *dal_adapter_service_obtain_hpd_irq( + struct adapter_service *as, + struct graphics_object_id id); + +/* Release interrupt request */ +void dal_adapter_service_release_irq( + struct adapter_service *as, + struct irq *irq); + +/* Obtain GPIO */ +struct gpio *dal_adapter_service_obtain_gpio( + struct adapter_service *as, + enum gpio_id id, + uint32_t en); + +/* Obtain GPIO for stereo3D*/ +struct gpio *dal_adapter_service_obtain_stereo_gpio(struct adapter_service *as); + +/* Release GPIO */ +void dal_adapter_service_release_gpio( + struct adapter_service *as, + struct gpio *gpio); + +/* Get SW I2C speed */ +uint32_t dal_adapter_service_get_sw_i2c_speed(struct adapter_service *as); + +/* Get HW I2C speed */ +uint32_t dal_adapter_service_get_hw_i2c_speed(struct adapter_service *as); + +/* Get line buffer size */ +uint32_t dal_adapter_service_get_line_buffer_size(struct adapter_service *as); + +/* Get information on audio support */ +union audio_support dal_adapter_service_get_audio_support( + struct adapter_service *as); + +/* Get I2C information from BIOS */ +bool dal_adapter_service_get_i2c_info( + struct adapter_service *as, + struct graphics_object_id id, + struct graphics_object_i2c_info *i2c_info); + +/* Get bios parser handler */ +struct bios_parser *dal_adapter_service_get_bios_parser( + struct adapter_service *as); + +/* Get i2c aux handler */ +struct i2caux *dal_adapter_service_get_i2caux( + struct adapter_service *as); + +struct dal_asic_runtime_flags dal_adapter_service_get_asic_runtime_flags( + struct adapter_service *as); + +bool dal_adapter_service_initialize_hw_data( + struct adapter_service *as); + +struct graphics_object_id dal_adapter_service_enum_fake_path_resource( + struct adapter_service *as, + uint32_t index); + +struct graphics_object_id dal_adapter_service_enum_stereo_sync_object( + struct adapter_service *as, + uint32_t index); + +struct graphics_object_id dal_adapter_service_enum_sync_output_object( + struct adapter_service *as, + uint32_t index); + +struct graphics_object_id dal_adapter_service_enum_audio_object( + struct adapter_service *as, + uint32_t index); + +void dal_adapter_service_update_audio_connectivity( + struct adapter_service *as, + uint32_t number_of_audio_capable_display_path); + +bool dal_adapter_service_has_embedded_display_connector( + struct adapter_service *as); + +bool dal_adapter_service_get_embedded_panel_info( + struct adapter_service *as, + struct embedded_panel_info *info); + +bool dal_adapter_service_enum_embedded_panel_patch_mode( + struct adapter_service *as, + uint32_t index, + struct embedded_panel_patch_mode *mode); + +bool dal_adapter_service_get_faked_edid_len( + struct adapter_service *as, + uint32_t *len); + +bool dal_adapter_service_get_faked_edid_buf( + struct adapter_service *as, + uint8_t *buf, + uint32_t len); + +uint32_t dal_adapter_service_get_max_cofunc_non_dp_displays(void); + +uint32_t dal_adapter_service_get_single_selected_timing_signals(void); + +bool dal_adapter_service_get_device_tag( + struct adapter_service *as, + struct graphics_object_id connector_object_id, + uint32_t device_tag_index, + struct connector_device_tag_info *info); + +bool dal_adapter_service_is_device_id_supported( + struct adapter_service *as, + struct device_id id); + +bool dal_adapter_service_is_meet_underscan_req(struct adapter_service *as); + +bool dal_adapter_service_underscan_for_hdmi_only(struct adapter_service *as); + +uint32_t dal_adapter_service_get_src_num( + struct adapter_service *as, + struct graphics_object_id id); + +struct graphics_object_id dal_adapter_service_get_src_obj( + struct adapter_service *as, + struct graphics_object_id id, + uint32_t index); + +/* Is this Fusion ASIC */ +bool dal_adapter_service_is_fusion(struct adapter_service *as); + +/* Is this ASIC support dynamic DFSbypass switch */ +bool dal_adapter_service_is_dfsbyass_dynamic(struct adapter_service *as); + +/* Reports whether driver settings allow requested optimization */ +bool dal_adapter_service_should_optimize( + struct adapter_service *as, enum optimization_feature feature); + +/* Determine if driver is in accelerated mode */ +bool dal_adapter_service_is_in_accelerated_mode(struct adapter_service *as); + +struct ddc *dal_adapter_service_obtain_ddc_from_i2c_info( + struct adapter_service *as, + struct graphics_object_i2c_info *info); + +struct bdf_info dal_adapter_service_get_adapter_info( + struct adapter_service *as); + + +/* Determine if this ASIC needs to wait on PLL lock bit */ +bool dal_adapter_service_should_psr_skip_wait_for_pll_lock( + struct adapter_service *as); + +#define SIZEOF_BACKLIGHT_LUT 101 +#define ABSOLUTE_BACKLIGHT_MAX 255 +#define DEFAULT_MIN_BACKLIGHT 12 +#define DEFAULT_MAX_BACKLIGHT 255 +#define BACKLIGHT_CURVE_COEFFB 100 +#define BACKLIGHT_CURVE_COEFFA_FACTOR 10000 +#define BACKLIGHT_CURVE_COEFFB_FACTOR 100 + +struct panel_backlight_levels { + uint32_t ac_level_percentage; + uint32_t dc_level_percentage; +}; + +bool dal_adapter_service_is_lid_open(struct adapter_service *as); + +bool dal_adapter_service_get_panel_backlight_default_levels( + struct adapter_service *as, + struct panel_backlight_levels *levels); + +bool dal_adapter_service_get_panel_backlight_boundaries( + struct adapter_service *as, + struct panel_backlight_boundaries *boundaries); + +uint32_t dal_adapter_service_get_view_port_pixel_granularity( + struct adapter_service *as); + +uint32_t dal_adapter_service_get_num_of_path_per_dp_mst_connector( + struct adapter_service *as); + +uint32_t dal_adapter_service_get_num_of_underlays( + struct adapter_service *as); + +bool dal_adapter_service_get_encoder_cap_info( + struct adapter_service *as, + struct graphics_object_id id, + struct graphics_object_encoder_cap_info *info); + +bool dal_adapter_service_is_mc_tuning_req(struct adapter_service *as); + +#endif /* __DAL_ADAPTER_SERVICE_INTERFACE_H__ */ diff --git a/drivers/gpu/drm/amd/dal/include/adapter_service_types.h b/drivers/gpu/drm/amd/dal/include/adapter_service_types.h new file mode 100644 index 000000000000..fb47ef3b1353 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/include/adapter_service_types.h @@ -0,0 +1,70 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_ADAPTER_SERVICE_TYPES_H__ +#define __DAL_ADAPTER_SERVICE_TYPES_H__ + +enum as_signal_type { + AS_SIGNAL_TYPE_NONE = 0L, /* no signal */ + AS_SIGNAL_TYPE_DVI, + AS_SIGNAL_TYPE_HDMI, + AS_SIGNAL_TYPE_LVDS, + AS_SIGNAL_TYPE_DISPLAY_PORT, + AS_SIGNAL_TYPE_GPU_PLL, + AS_SIGNAL_TYPE_UNKNOWN +}; + +/* + * Struct used for algorithm of Bandwidth tuning parameters + * the sequence of the fields is binded with runtime parameter. + */ +union bandwidth_tuning_params { + struct bandwidth_tuning_params_struct { + uint32_t read_delay_stutter_off_usec; + uint32_t ignore_hblank_time;/*bool*/ + uint32_t extra_reordering_latency_usec; + uint32_t extra_mc_latency_usec; + uint32_t data_return_bandwidth_eff;/*in %*/ + uint32_t dmif_request_bandwidth_eff;/*in %*/ + uint32_t sclock_latency_multiplier;/*in unit of 0.01*/ + uint32_t mclock_latency_multiplier;/*in unit of 0.01*/ + uint32_t fix_latency_multiplier;/*in unit of 0.01*/ + /*in unit represent in watermark*/ + uint32_t use_urgency_watermark_offset; + } tuning_info; + uint32_t arr_info[sizeof(struct bandwidth_tuning_params_struct) + / sizeof(uint32_t)]; +}; + +union audio_support { + struct { + uint32_t DP_AUDIO:1; + uint32_t HDMI_AUDIO_ON_DONGLE:1; + uint32_t HDMI_AUDIO_NATIVE:1; + } bits; + uint32_t raw; +}; + +#endif diff --git a/drivers/gpu/drm/amd/dal/include/bios_parser_interface.h b/drivers/gpu/drm/amd/dal/include/bios_parser_interface.h new file mode 100644 index 000000000000..00f3298c60a3 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/include/bios_parser_interface.h @@ -0,0 +1,294 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_BIOS_PARSER_INTERFACE_H__ +#define __DAL_BIOS_PARSER_INTERFACE_H__ + +#include "bios_parser_types.h" +#include "adapter_service_types.h" +#include "gpio_types.h" + +struct adapter_service; +struct bios_parser; + +struct bp_gpio_cntl_info { + uint32_t id; + enum gpio_pin_output_state state; +}; + +enum bp_result { + BP_RESULT_OK = 0, /* There was no error */ + BP_RESULT_BADINPUT, /*Bad input parameter */ + BP_RESULT_BADBIOSTABLE, /* Bad BIOS table */ + BP_RESULT_UNSUPPORTED, /* BIOS Table is not supported */ + BP_RESULT_NORECORD, /* Record can't be found */ + BP_RESULT_FAILURE +}; + +struct bp_init_data { + struct dal_context *dal_context; + uint8_t *bios; +}; + +struct bios_parser *dal_bios_parser_create( + struct bp_init_data *init, + struct adapter_service *as); +void dal_bios_parser_destroy( + struct bios_parser **bp); +void dal_bios_parser_power_down( + struct bios_parser *bp); +void dal_bios_parser_power_up( + struct bios_parser *bp); + +uint8_t dal_bios_parser_get_encoders_number( + struct bios_parser *bp); +uint8_t dal_bios_parser_get_connectors_number( + struct bios_parser *bp); +uint32_t dal_bios_parser_get_oem_ddc_lines_number( + struct bios_parser *bp); +struct graphics_object_id dal_bios_parser_get_encoder_id( + struct bios_parser *bp, + uint32_t i); +struct graphics_object_id dal_bios_parser_get_connector_id( + struct bios_parser *bp, + uint8_t connector_index); +uint32_t dal_bios_parser_get_src_number( + struct bios_parser *bp, + struct graphics_object_id id); +uint32_t dal_bios_parser_get_dst_number( + struct bios_parser *bp, + struct graphics_object_id id); +uint32_t dal_bios_parser_get_gpio_record( + struct bios_parser *bp, + struct graphics_object_id id, + struct bp_gpio_cntl_info *gpio_record, + uint32_t record_size); +enum bp_result dal_bios_parser_get_src_obj( + struct bios_parser *bp, + struct graphics_object_id object_id, uint32_t index, + struct graphics_object_id *src_object_id); +enum bp_result dal_bios_parser_get_dst_obj( + struct bios_parser *bp, + struct graphics_object_id object_id, uint32_t index, + struct graphics_object_id *dest_object_id); +enum bp_result dal_bios_parser_get_i2c_info( + struct bios_parser *bp, + struct graphics_object_id id, + struct graphics_object_i2c_info *info); +enum bp_result dal_bios_parser_get_oem_ddc_info( + struct bios_parser *bp, + uint32_t index, + struct graphics_object_i2c_info *info); +enum bp_result dal_bios_parser_get_voltage_ddc_info( + struct bios_parser *bp, + uint32_t index, + struct graphics_object_i2c_info *info); +enum bp_result dal_bios_parser_get_thermal_ddc_info( + struct bios_parser *bp, + uint32_t i2c_channel_id, + struct graphics_object_i2c_info *info); +enum bp_result dal_bios_parser_get_hpd_info( + struct bios_parser *bp, + struct graphics_object_id id, + struct graphics_object_hpd_info *info); +enum bp_result dal_bios_parser_get_device_tag( + struct bios_parser *bp, + struct graphics_object_id connector_object_id, + uint32_t device_tag_index, + struct connector_device_tag_info *info); +enum bp_result dal_bios_parser_get_firmware_info( + struct bios_parser *bp, + struct firmware_info *info); +enum bp_result dal_bios_parser_get_spread_spectrum_info( + struct bios_parser *bp, + enum as_signal_type signal, + uint32_t index, + struct spread_spectrum_info *ss_info); +uint32_t dal_bios_parser_get_ss_entry_number( + struct bios_parser *bp, + enum as_signal_type signal); +enum bp_result dal_bios_parser_get_embedded_panel_info( + struct bios_parser *bp, + struct embedded_panel_info *info); +enum bp_result dal_bios_parser_enum_embedded_panel_patch_mode( + struct bios_parser *bp, + uint32_t index, + struct embedded_panel_patch_mode *mode); +enum bp_result dal_bios_parser_get_gpio_pin_info( + struct bios_parser *bp, + uint32_t gpio_id, + struct gpio_pin_info *info); +enum bp_result dal_bios_parser_get_embedded_panel_info( + struct bios_parser *bp, + struct embedded_panel_info *info); +enum bp_result dal_bios_parser_get_gpio_pin_info( + struct bios_parser *bp, + uint32_t gpio_id, + struct gpio_pin_info *info); +enum bp_result dal_bios_parser_get_faked_edid_len( + struct bios_parser *bp, + uint32_t *len); +enum bp_result dal_bios_parser_get_faked_edid_buf( + struct bios_parser *bp, + uint8_t *buff, + uint32_t len); +enum bp_result dal_bios_parser_get_encoder_cap_info( + struct bios_parser *bp, + struct graphics_object_id object_id, + struct bp_encoder_cap_info *info); +enum bp_result dal_bios_parser_get_din_connector_info( + struct bios_parser *bp, + struct graphics_object_id id, + struct din_connector_info *info); + +bool dal_bios_parser_is_lid_open( + struct bios_parser *bp); +bool dal_bios_parser_is_lid_status_changed( + struct bios_parser *bp); +bool dal_bios_parser_is_display_config_changed( + struct bios_parser *bp); +bool dal_bios_parser_is_accelerated_mode( + struct bios_parser *bp); +void dal_bios_parser_set_scratch_lcd_scale( + struct bios_parser *bp, + enum lcd_scale scale); +enum lcd_scale dal_bios_parser_get_scratch_lcd_scale( + struct bios_parser *bp); +void dal_bios_parser_get_bios_event_info( + struct bios_parser *bp, + struct bios_event_info *info); +void dal_bios_parser_update_requested_backlight_level( + struct bios_parser *bp, + uint32_t backlight_8bit); +uint32_t dal_bios_parser_get_requested_backlight_level( + struct bios_parser *bp); +void dal_bios_parser_take_backlight_control( + struct bios_parser *bp, + bool cntl); +bool dal_bios_parser_is_active_display( + struct bios_parser *bp, + enum signal_type signal, + const struct connector_device_tag_info *device_tag); +enum controller_id dal_bios_parser_get_embedded_display_controller_id( + struct bios_parser *bp); +uint32_t dal_bios_parser_get_embedded_display_refresh_rate( + struct bios_parser *bp); +void dal_bios_parser_set_scratch_connected( + struct bios_parser *bp, + struct graphics_object_id connector_id, + bool connected, + const struct connector_device_tag_info *device_tag); +void dal_bios_parser_prepare_scratch_active_and_requested( + struct bios_parser *bp, + enum controller_id controller_id, + enum signal_type signal, + const struct connector_device_tag_info *device_tag); +void dal_bios_parser_set_scratch_active_and_requested( + struct bios_parser *bp); +void dal_bios_parser_set_scratch_critical_state( + struct bios_parser *bp, + bool state); +void dal_bios_parser_set_scratch_acc_mode_change( + struct bios_parser *bp); + +bool dal_bios_parser_is_device_id_supported( + struct bios_parser *bp, + struct device_id id); + +/* COMMANDS */ + +enum bp_result dal_bios_parser_encoder_control( + struct bios_parser *bp, + struct bp_encoder_control *cntl); +enum bp_result dal_bios_parser_transmitter_control( + struct bios_parser *bp, + struct bp_transmitter_control *cntl); +enum bp_result dal_bios_parser_crt_control( + struct bios_parser *bp, + enum engine_id engine_id, + bool enable, + uint32_t pixel_clock); +enum bp_result dal_bios_parser_dvo_encoder_control( + struct bios_parser *bp, + struct bp_dvo_encoder_control *cntl); +enum bp_result dal_bios_parser_enable_crtc( + struct bios_parser *bp, + enum controller_id id, + bool enable); +enum bp_result dal_bios_parser_adjust_pixel_clock( + struct bios_parser *bp, + struct bp_adjust_pixel_clock_parameters *bp_params); +enum bp_result dal_bios_parser_set_pixel_clock( + struct bios_parser *bp, + struct bp_pixel_clock_parameters *bp_params); +enum bp_result dal_bios_parser_enable_spread_spectrum_on_ppll( + struct bios_parser *bp, + struct bp_spread_spectrum_parameters *bp_params, + bool enable); +enum bp_result dal_bios_parser_program_crtc_timing( + struct bios_parser *bp, + struct bp_hw_crtc_timing_parameters *bp_params); +enum bp_result dal_bios_parser_blank_crtc( + struct bios_parser *bp, + struct bp_blank_crtc_parameters *bp_params, + bool blank); +enum bp_result dal_bios_parser_set_overscan( + struct bios_parser *bp, + struct bp_hw_crtc_overscan_parameters *bp_params); +enum bp_result dal_bios_parser_crtc_source_select( + struct bios_parser *bp, + struct bp_crtc_source_select *bp_params); +enum bp_result dal_bios_parser_program_display_engine_pll( + struct bios_parser *bp, + struct bp_pixel_clock_parameters *bp_params); +enum bp_result dal_bios_parser_get_divider_for_target_display_clock( + struct bios_parser *bp, + struct bp_display_clock_parameters *bp_params); +enum signal_type dal_bios_parser_dac_load_detect( + struct bios_parser *bp, + struct graphics_object_id encoder, + struct graphics_object_id connector, + enum signal_type display_signal); +enum bp_result dal_bios_parser_enable_memory_requests( + struct bios_parser *bp, + enum controller_id controller_id, + bool enable); +enum bp_result dal_bios_parser_external_encoder_control( + struct bios_parser *bp, + struct bp_external_encoder_control *cntl); +enum bp_result dal_bios_parser_enable_disp_power_gating( + struct bios_parser *bp, + enum controller_id controller_id, + enum bp_pipe_control_action action); + +void dal_bios_parser_post_init(struct bios_parser *bp); + +/* Parse integrated BIOS info */ +struct integrated_info *dal_bios_parser_create_integrated_info( + struct bios_parser *bp); + +/* Destroy provided integrated info */ +void dal_bios_parser_destroy_integrated_info(struct integrated_info **info); +#endif diff --git a/drivers/gpu/drm/amd/dal/include/bios_parser_types.h b/drivers/gpu/drm/amd/dal/include/bios_parser_types.h new file mode 100644 index 000000000000..142419f99370 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/include/bios_parser_types.h @@ -0,0 +1,305 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_BIOS_PARSER_TYPES_H__ +#define __DAL_BIOS_PARSER_TYPES_H__ + +#include "include/signal_types.h" +#include "include/grph_object_ctrl_defs.h" +#include "link_service_types.h" + +enum bp_encoder_control_action { + /* direct VBIOS translation! Just to simplify the translation */ + ENCODER_CONTROL_DISABLE = 0, + ENCODER_CONTROL_ENABLE, + ENCODER_CONTROL_SETUP, + ENCODER_CONTROL_INIT +}; + +enum bp_transmitter_control_action { + /* direct VBIOS translation! Just to simplify the translation */ + TRANSMITTER_CONTROL_DISABLE = 0, + TRANSMITTER_CONTROL_ENABLE, + TRANSMITTER_CONTROL_BACKLIGHT_OFF, + TRANSMITTER_CONTROL_BACKLIGHT_ON, + TRANSMITTER_CONTROL_BACKLIGHT_BRIGHTNESS, + TRANSMITTER_CONTROL_LCD_SETF_TEST_START, + TRANSMITTER_CONTROL_LCD_SELF_TEST_STOP, + TRANSMITTER_CONTROL_INIT, + TRANSMITTER_CONTROL_DEACTIVATE, + TRANSMITTER_CONTROL_ACTIAVATE, + TRANSMITTER_CONTROL_SETUP, + TRANSMITTER_CONTROL_SET_VOLTAGE_AND_PREEMPASIS, + /* ATOM_TRANSMITTER_ACTION_POWER_ON. This action is for eDP only + * (power up the panel) + */ + TRANSMITTER_CONTROL_POWER_ON, + /* ATOM_TRANSMITTER_ACTION_POWER_OFF. This action is for eDP only + * (power down the panel) + */ + TRANSMITTER_CONTROL_POWER_OFF +}; + +enum bp_external_encoder_control_action { + EXTERNAL_ENCODER_CONTROL_DISABLE = 0, + EXTERNAL_ENCODER_CONTROL_ENABLE = 1, + EXTERNAL_ENCODER_CONTROL_INIT = 0x7, + EXTERNAL_ENCODER_CONTROL_SETUP = 0xf, + EXTERNAL_ENCODER_CONTROL_UNBLANK = 0x10, + EXTERNAL_ENCODER_CONTROL_BLANK = 0x11, + EXTERNAL_ENCODER_CONTROL_DAC_LOAD_DETECT = 0x12 +}; + +enum bp_pipe_control_action { + ASIC_PIPE_DISABLE = 0, + ASIC_PIPE_ENABLE, + ASIC_PIPE_INIT +}; + +struct bp_encoder_control { + enum bp_encoder_control_action action; + enum engine_id engine_id; + enum transmitter transmitter; + enum signal_type signal; + enum lane_count lanes_number; + enum transmitter_color_depth colordepth; + bool enable_dp_audio; + uint32_t pixel_clock; /* khz */ +}; + +struct bp_external_encoder_control { + enum bp_external_encoder_control_action action; + enum engine_id engine_id; + enum link_rate link_rate; + enum lane_count lanes_number; + enum signal_type signal; + enum dp_transmitter_color_depth color_depth; + bool coherent; + struct graphics_object_id encoder_id; + struct graphics_object_id connector_obj_id; + uint32_t pixel_clock; /* in KHz */ +}; + +struct bp_crtc_source_select { + enum engine_id engine_id; + enum controller_id controller_id; + /* from GPU Tx aka asic_signal */ + enum signal_type signal; + /* sink_signal may differ from asicSignal if Translator encoder */ + enum signal_type sink_signal; + enum display_output_bit_depth display_output_bit_depth; + bool enable_dp_audio; +}; + +struct bp_transmitter_control { + enum bp_transmitter_control_action action; + enum engine_id engine_id; + enum transmitter transmitter; /* PhyId */ + enum lane_count lanes_number; + enum clock_source_id pll_id; /* needed for DCE 4.0 */ + enum signal_type signal; + enum transmitter_color_depth color_depth; /* not used for DCE6.0 */ + enum hpd_source_id hpd_sel; /* ucHPDSel, used for DCe6.0 */ + struct graphics_object_id connector_obj_id; + /* symClock; in 10kHz, pixel clock, in HDMI deep color mode, it should + * be pixel clock * deep_color_ratio (in KHz) + */ + uint32_t pixel_clock; + uint32_t lane_select; + uint32_t lane_settings; + bool coherent; + bool multi_path; + bool single_pll_mode; +}; + +enum dvo_encoder_memory_rate { + DVO_ENCODER_MEMORY_RATE_DDR, + DVO_ENCODER_MEMORY_RATE_SDR +}; + +enum dvo_encoder_interface_width { + DVO_ENCODER_INTERFACE_WIDTH_LOW12BIT, + DVO_ENCODER_INTERFACE_WIDTH_HIGH12BIT, + DVO_ENCODER_INTERFACE_WIDTH_FULL24BIT +}; + +struct bp_dvo_encoder_control { + enum bp_encoder_control_action action; + enum dvo_encoder_memory_rate memory_rate; + enum dvo_encoder_interface_width interface_width; + uint32_t pixel_clock; /* in KHz */ +}; + +struct bp_blank_crtc_parameters { + enum controller_id controller_id; + uint32_t black_color_rcr; + uint32_t black_color_gy; + uint32_t black_color_bcb; +}; + +struct bp_hw_crtc_timing_parameters { + enum controller_id controller_id; + /* horizontal part */ + uint32_t h_total; + uint32_t h_addressable; + uint32_t h_overscan_left; + uint32_t h_overscan_right; + uint32_t h_sync_start; + uint32_t h_sync_width; + + /* vertical part */ + uint32_t v_total; + uint32_t v_addressable; + uint32_t v_overscan_top; + uint32_t v_overscan_bottom; + uint32_t v_sync_start; + uint32_t v_sync_width; + + struct timing_flags { + uint32_t INTERLACE:1; + uint32_t PIXEL_REPETITION:4; + uint32_t HSYNC_POSITIVE_POLARITY:1; + uint32_t VSYNC_POSITIVE_POLARITY:1; + uint32_t HORZ_COUNT_BY_TWO:1; + } flags; +}; + +struct bp_hw_crtc_overscan_parameters { + enum controller_id controller_id; + uint32_t h_overscan_left; + uint32_t h_overscan_right; + uint32_t v_overscan_top; + uint32_t v_overscan_bottom; +}; + +struct bp_adjust_pixel_clock_parameters { + /* Input: Signal Type - to be converted to Encoder mode */ + enum signal_type signal_type; + /* Input: required by V3, display pll configure parameter defined as + * following DISPPLL_CONFIG_XXXX */ + enum disp_pll_config display_pll_config; + /* Input: Encoder object id */ + struct graphics_object_id encoder_object_id; + /* Input: Pixel Clock (requested Pixel clock based on Video timing + * standard used) in KHz + */ + uint32_t pixel_clock; + union { + /* Input: If DVO, need passing link rate and output 12bit low or + * 24bit to VBIOS Exec table */ + uint32_t dvo_config; + /* Input: If non DVO, not defined yet */ + uint32_t non_dvo_undefined; + }; + /* Output: Adjusted Pixel Clock (after VBIOS exec table) in KHz */ + uint32_t adjusted_pixel_clock; + /* Output: If non-zero, this refDiv value should be used to calculate + * other ppll params */ + uint32_t reference_divider; + /* Output: If non-zero, this postDiv value should be used to calculate + * other ppll params */ + uint32_t pixel_clock_post_divider; + /* Input: Enable spread spectrum */ + bool ss_enable; +}; + +struct bp_pixel_clock_parameters { + enum controller_id controller_id; /* (Which CRTC uses this PLL) */ + enum clock_source_id pll_id; /* Clock Source Id */ + /* signal_type -> Encoder Mode - needed by VBIOS Exec table */ + enum signal_type signal_type; + /* Adjusted Pixel Clock (after VBIOS exec table) + * that becomes Target Pixel Clock (KHz) */ + uint32_t target_pixel_clock; + /* Calculated Reference divider of Display PLL */ + uint32_t reference_divider; + /* Calculated Feedback divider of Display PLL */ + uint32_t feedback_divider; + /* Calculated Fractional Feedback divider of Display PLL */ + uint32_t fractional_feedback_divider; + /* Calculated Pixel Clock Post divider of Display PLL */ + uint32_t pixel_clock_post_divider; + struct graphics_object_id encoder_object_id; /* Encoder object id */ + /* If DVO, need passing link rate and output 12bit low or + * 24bit to VBIOS Exec table */ + uint32_t dvo_config; + /* VBIOS returns a fixed display clock when DFS-bypass feature + * is enabled (KHz) */ + uint32_t dfs_bypass_display_clock; + struct program_pixel_clock_flags { + uint32_t FORCE_PROGRAMMING_OF_PLL:1; + /* Use Engine Clock as source for Display Clock when + * programming PLL */ + uint32_t USE_E_CLOCK_AS_SOURCE_FOR_D_CLOCK:1; + /* Use external reference clock (refDivSrc for PLL) */ + uint32_t SET_EXTERNAL_REF_DIV_SRC:1; + } flags; +}; + +struct bp_display_clock_parameters { + uint32_t target_display_clock; /* KHz */ + /* Actual Display Clock set due to clock divider granularity KHz */ + uint32_t actual_display_clock; + /* Actual Post Divider ID used to generate the actual clock */ + uint32_t actual_post_divider_id; +}; + +struct spread_spectrum_flags { + /* 1 = Center Spread; 0 = down spread */ + uint32_t CENTER_SPREAD:1; + /* 1 = external; 0 = internal */ + uint32_t EXTERNAL_SS:1; + /* 1 = delta-sigma type parameter; 0 = ver1 */ + uint32_t DS_TYPE:1; +}; + +struct bp_spread_spectrum_parameters { + enum clock_source_id pll_id; + uint32_t percentage; + uint32_t ds_frac_amount; + + union { + struct { + uint32_t step; + uint32_t delay; + uint32_t range; /* In Hz unit */ + } ver1; + struct { + uint32_t feedback_amount; + uint32_t nfrac_amount; + uint32_t ds_frac_size; + } ds; + }; + + struct spread_spectrum_flags flags; +}; + +struct bp_encoder_cap_info { + uint32_t DP_HBR2_CAP:1; + uint32_t DP_HBR2_EN:1; + uint32_t RESERVED:30; +}; + +#endif diff --git a/drivers/gpu/drm/amd/dal/include/dpcd_defs.h b/drivers/gpu/drm/amd/dal/include/dpcd_defs.h new file mode 100644 index 000000000000..df73d6314c37 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/include/dpcd_defs.h @@ -0,0 +1,853 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_DPCD_DEFS_H__ +#define __DAL_DPCD_DEFS_H__ + +enum dpcd_address { +/* addresses marked with 1.2 are only defined since DP 1.2 spec */ + + /* Reciever Capability Field */ + DPCD_ADDRESS_DPCD_REV = 0x00000, + DPCD_ADDRESS_MAX_LINK_RATE = 0x00001, + DPCD_ADDRESS_MAX_LANE_COUNT = 0x00002, + DPCD_ADDRESS_MAX_DOWNSPREAD = 0x00003, + DPCD_ADDRESS_NORP = 0x00004, + DPCD_ADDRESS_DOWNSTREAM_PORT_PRESENT = 0x00005, + DPCD_ADDRESS_MAIN_LINK_CHANNEL_CODING = 0x00006, + DPCD_ADDRESS_DOWNSTREAM_PORT_COUNT = 0x00007, + DPCD_ADDRESS_RECEIVE_PORT0_CAP0 = 0x00008, + DPCD_ADDRESS_RECEIVE_PORT0_CAP1 = 0x00009, + DPCD_ADDRESS_RECEIVE_PORT1_CAP0 = 0x0000A, + DPCD_ADDRESS_RECEIVE_PORT1_CAP1 = 0x0000B, + + DPCD_ADDRESS_I2C_SPEED_CNTL_CAP = 0x0000C,/*1.2*/ + DPCD_ADDRESS_EDP_CONFIG_CAP = 0x0000D,/*1.2*/ + DPCD_ADDRESS_TRAINING_AUX_RD_INTERVAL = 0x000E,/*1.2*/ + + DPCD_ADDRESS_MSTM_CAP = 0x00021,/*1.2*/ + + /* Audio Video Sync Data Feild */ + DPCD_ADDRESS_AV_GRANULARITY = 0x0023, + DPCD_ADDRESS_AUDIO_DECODE_LATENCY1 = 0x0024, + DPCD_ADDRESS_AUDIO_DECODE_LATENCY2 = 0x0025, + DPCD_ADDRESS_AUDIO_POSTPROCESSING_LATENCY1 = 0x0026, + DPCD_ADDRESS_AUDIO_POSTPROCESSING_LATENCY2 = 0x0027, + DPCD_ADDRESS_VIDEO_INTERLACED_LATENCY = 0x0028, + DPCD_ADDRESS_VIDEO_PROGRESSIVE_LATENCY = 0x0029, + DPCD_ADDRESS_AUDIO_DELAY_INSERT1 = 0x0002B, + DPCD_ADDRESS_AUDIO_DELAY_INSERT2 = 0x0002C, + DPCD_ADDRESS_AUDIO_DELAY_INSERT3 = 0x0002D, + + /* Audio capability */ + DPCD_ADDRESS_NUM_OF_AUDIO_ENDPOINTS = 0x00022, + + DPCD_ADDRESS_GUID_START = 0x00030,/*1.2*/ + DPCD_ADDRESS_GUID_END = 0x0003f,/*1.2*/ + + DPCD_ADDRESS_PSR_SUPPORT_VER = 0x00070, + DPCD_ADDRESS_PSR_CAPABILITY = 0x00071, + + DPCD_ADDRESS_DWN_STRM_PORT0_CAPS = 0x00080,/*1.2a*/ + + /* Link Configuration Field */ + DPCD_ADDRESS_LINK_BW_SET = 0x00100, + DPCD_ADDRESS_LANE_COUNT_SET = 0x00101, + DPCD_ADDRESS_TRAINING_PATTERN_SET = 0x00102, + DPCD_ADDRESS_LANE0_SET = 0x00103, + DPCD_ADDRESS_LANE1_SET = 0x00104, + DPCD_ADDRESS_LANE2_SET = 0x00105, + DPCD_ADDRESS_LANE3_SET = 0x00106, + DPCD_ADDRESS_DOWNSPREAD_CNTL = 0x00107, + DPCD_ADDRESS_I2C_SPEED_CNTL = 0x00109,/*1.2*/ + + DPCD_ADDRESS_EDP_CONFIG_SET = 0x0010A, + DPCD_ADDRESS_LINK_QUAL_LANE0_SET = 0x0010B, + DPCD_ADDRESS_LINK_QUAL_LANE1_SET = 0x0010C, + DPCD_ADDRESS_LINK_QUAL_LANE2_SET = 0x0010D, + DPCD_ADDRESS_LINK_QUAL_LANE3_SET = 0x0010E, + + DPCD_ADDRESS_LANE0_SET2 = 0x0010F,/*1.2*/ + DPCD_ADDRESS_LANE2_SET2 = 0x00110,/*1.2*/ + + DPCD_ADDRESS_MSTM_CNTL = 0x00111,/*1.2*/ + + DPCD_ADDRESS_PSR_ENABLE_CFG = 0x0170, + + /* Payload Table Configuration Field 1.2 */ + DPCD_ADDRESS_PAYLOAD_ALLOCATE_SET = 0x001C0, + DPCD_ADDRESS_PAYLOAD_ALLOCATE_START_TIMESLOT = 0x001C1, + DPCD_ADDRESS_PAYLOAD_ALLOCATE_TIMESLOT_COUNT = 0x001C2, + + DPCD_ADDRESS_SINK_COUNT = 0x0200, + DPCD_ADDRESS_DEVICE_SERVICE_IRQ_VECTOR = 0x0201, + + /* Link / Sink Status Field */ + DPCD_ADDRESS_LANE_01_STATUS = 0x00202, + DPCD_ADDRESS_LANE_23_STATUS = 0x00203, + DPCD_ADDRESS_LANE_ALIGN_STATUS_UPDATED = 0x0204, + DPCD_ADDRESS_SINK_STATUS = 0x0205, + + /* Adjust Request Field */ + DPCD_ADDRESS_ADJUST_REQUEST_LANE0_1 = 0x0206, + DPCD_ADDRESS_ADJUST_REQUEST_LANE2_3 = 0x0207, + DPCD_ADDRESS_ADJUST_REQUEST_POST_CURSOR2 = 0x020C, + + /* Test Request Field */ + DPCD_ADDRESS_TEST_REQUEST = 0x0218, + DPCD_ADDRESS_TEST_LINK_RATE = 0x0219, + DPCD_ADDRESS_TEST_LANE_COUNT = 0x0220, + DPCD_ADDRESS_TEST_PATTERN = 0x0221, + DPCD_ADDRESS_TEST_MISC1 = 0x0232, + + /* Phy Test Pattern Field */ + DPCD_ADDRESS_TEST_PHY_PATTERN = 0x0248, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_7_0 = 0x0250, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_15_8 = 0x0251, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_23_16 = 0x0252, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_31_24 = 0x0253, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_39_32 = 0x0254, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_47_40 = 0x0255, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_55_48 = 0x0256, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_63_56 = 0x0257, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_71_64 = 0x0258, + DPCD_ADDRESS_TEST_80BIT_CUSTOM_PATTERN_79_72 = 0x0259, + + /* Test Response Field*/ + DPCD_ADDRESS_TEST_RESPONSE = 0x0260, + + /* Audio Test Pattern Field 1.2*/ + DPCD_ADDRESS_TEST_AUDIO_MODE = 0x0271, + DPCD_ADDRESS_TEST_AUDIO_PATTERN_TYPE = 0x0272, + DPCD_ADDRESS_TEST_AUDIO_PERIOD_CH_1 = 0x0273, + DPCD_ADDRESS_TEST_AUDIO_PERIOD_CH_2 = 0x0274, + DPCD_ADDRESS_TEST_AUDIO_PERIOD_CH_3 = 0x0275, + DPCD_ADDRESS_TEST_AUDIO_PERIOD_CH_4 = 0x0276, + DPCD_ADDRESS_TEST_AUDIO_PERIOD_CH_5 = 0x0277, + DPCD_ADDRESS_TEST_AUDIO_PERIOD_CH_6 = 0x0278, + DPCD_ADDRESS_TEST_AUDIO_PERIOD_CH_7 = 0x0279, + DPCD_ADDRESS_TEST_AUDIO_PERIOD_CH_8 = 0x027A, + + /* Payload Table Status Field */ + DPCD_ADDRESS_PAYLOAD_TABLE_UPDATE_STATUS = 0x002C0,/*1.2*/ + DPCD_ADDRESS_VC_PAYLOAD_ID_SLOT1 = 0x002C1,/*1.2*/ + DPCD_ADDRESS_VC_PAYLOAD_ID_SLOT63 = 0x002FF,/*1.2*/ + + /* Source Device Specific Field */ + DPCD_ADDRESS_SOURCE_DEVICE_ID_START = 0x0300, + DPCD_ADDRESS_SOURCE_DEVICE_ID_END = 0x0301, + DPCD_ADDRESS_SOURCE_RESERVED_START = 0x030C, + DPCD_ADDRESS_SOURCE_RESERVED_END = 0x03FF, + + /* Sink Device Specific Field */ + DPCD_ADDRESS_SINK_DEVICE_ID_START = 0x0400, + DPCD_ADDRESS_SINK_DEVICE_ID_END = 0x0402, + DPCD_ADDRESS_SINK_DEVICE_STR_START = 0x0403, + DPCD_ADDRESS_SINK_DEVICE_STR_END = 0x0408, + DPCD_ADDRESS_SINK_REVISION_START = 0x409, + DPCD_ADDRESS_SINK_REVISION_END = 0x40B, + + /* Branch Device Specific Field */ + DPCD_ADDRESS_BRANCH_DEVICE_ID_START = 0x0500, + DPCD_ADDRESS_BRANCH_DEVICE_ID_END = 0x0502, + DPCD_ADDRESS_BRANCH_DEVICE_STR_START = 0x0503, + DPCD_ADDRESS_BRANCH_DEVICE_STR_END = 0x0508, + + DPCD_ADDRESS_POWER_STATE = 0x0600, + + /* EDP related */ + DPCD_ADDRESS_EDP_REV = 0x0700, + DPCD_ADDRESS_EDP_CAPABILITY = 0x0701, + DPCD_ADDRESS_EDP_BACKLIGHT_ADJUST_CAP = 0x0702, + DPCD_ADDRESS_EDP_GENERAL_CAP2 = 0x0703, + + DPCD_ADDRESS_EDP_DISPLAY_CONTROL = 0x0720, + DPCD_ADDRESS_EDP_BACKLIGHT_SET = 0x0721, + DPCD_ADDRESS_EDP_BACKLIGHT_BRIGHTNESS_MSB = 0x0722, + DPCD_ADDRESS_EDP_BACKLIGHT_BRIGHTNESS_LSB = 0x0723, + DPCD_ADDRESS_EDP_PWMGEN_BIT_COUNT = 0x0724, + DPCD_ADDRESS_EDP_PWMGEN_BIT_COUNT_CAP_MIN = 0x0725, + DPCD_ADDRESS_EDP_PWMGEN_BIT_COUNT_CAP_MAX = 0x0726, + DPCD_ADDRESS_EDP_BACKLIGHT_CONTROL_STATUS = 0x0727, + DPCD_ADDRESS_EDP_BACKLIGHT_FREQ_SET = 0x0728, + DPCD_ADDRESS_EDP_REVERVED = 0x0729, + DPCD_ADDRESS_EDP_BACKLIGNT_FREQ_CAP_MIN_MSB = 0x072A, + DPCD_ADDRESS_EDP_BACKLIGNT_FREQ_CAP_MIN_MID = 0x072B, + DPCD_ADDRESS_EDP_BACKLIGNT_FREQ_CAP_MIN_LSB = 0x072C, + DPCD_ADDRESS_EDP_BACKLIGNT_FREQ_CAP_MAX_MSB = 0x072D, + DPCD_ADDRESS_EDP_BACKLIGNT_FREQ_CAP_MAX_MID = 0x072E, + DPCD_ADDRESS_EDP_BACKLIGNT_FREQ_CAP_MAX_LSB = 0x072F, + + DPCD_ADDRESS_EDP_DBC_MINIMUM_BRIGHTNESS_SET = 0x0732, + DPCD_ADDRESS_EDP_DBC_MAXIMUM_BRIGHTNESS_SET = 0x0733, + + /* Sideband MSG Buffers 1.2 */ + DPCD_ADDRESS_DOWN_REQ_START = 0x01000, + DPCD_ADDRESS_DOWN_REQ_END = 0x011ff, + + DPCD_ADDRESS_UP_REP_START = 0x01200, + DPCD_ADDRESS_UP_REP_END = 0x013ff, + + DPCD_ADDRESS_DOWN_REP_START = 0x01400, + DPCD_ADDRESS_DOWN_REP_END = 0x015ff, + + DPCD_ADDRESS_UP_REQ_START = 0x01600, + DPCD_ADDRESS_UP_REQ_END = 0x017ff, + + /* ESI (Event Status Indicator) Field 1.2 */ + DPCD_ADDRESS_SINK_COUNT_ESI = 0x02002, + DPCD_ADDRESS_DEVICE_IRQ_ESI0 = 0x02003, + DPCD_ADDRESS_DEVICE_IRQ_ESI1 = 0x02004, + /*@todo move dpcd_address_Lane01Status back here*/ + + DPCD_ADDRESS_PSR_ERROR_STATUS = 0x2006, + DPCD_ADDRESS_PSR_EVENT_STATUS = 0x2007, + DPCD_ADDRESS_PSR_SINK_STATUS = 0x2008, + DPCD_ADDRESS_PSR_DBG_REGISTER0 = 0x2009, + DPCD_ADDRESS_PSR_DBG_REGISTER1 = 0x200A, + + /* Travis specific addresses */ + DPCD_ADDRESS_TRAVIS_SINK_DEV_SEL = 0x5f0, + DPCD_ADDRESS_TRAVIS_SINK_ACCESS_OFFSET = 0x5f1, + DPCD_ADDRESS_TRAVIS_SINK_ACCESS_REG = 0x5f2, +}; + +enum dpcd_revision { + DPCD_REV_10 = 0x10, + DPCD_REV_11 = 0x11, + DPCD_REV_12 = 0x12 +}; + +enum dp_pwr_state { + DP_PWR_STATE_D0 = 1,/* direct HW translation! */ + DP_PWR_STATE_D3 +}; + +/* these are the types stored at DOWNSTREAMPORT_PRESENT */ +enum dpcd_downstream_port_type { + DOWNSTREAM_DP = 0, + DOWNSTREAM_VGA, + DOWNSTREAM_DVI_HDMI, + DOWNSTREAM_NONDDC /* has no EDID (TV,CV) */ +}; + +enum dpcd_link_test_patterns { + LINK_TEST_PATTERN_NONE = 0, + LINK_TEST_PATTERN_COLOR_RAMP, + LINK_TEST_PATTERN_VERTICAL_BARS, + LINK_TEST_PATTERN_COLOR_SQUARES +}; + +enum dpcd_test_color_format { + TEST_COLOR_FORMAT_RGB = 0, + TEST_COLOR_FORMAT_YCBCR422, + TEST_COLOR_FORMAT_YCBCR444 +}; + +enum dpcd_test_bit_depth { + TEST_BIT_DEPTH_6 = 0, + TEST_BIT_DEPTH_8, + TEST_BIT_DEPTH_10, + TEST_BIT_DEPTH_12, + TEST_BIT_DEPTH_16 +}; + +/* PHY (encoder) test patterns +The order of test patterns follows DPCD register PHY_TEST_PATTERN (0x248) */ +enum dpcd_phy_test_patterns { + PHY_TEST_PATTERN_NONE = 0, + PHY_TEST_PATTERN_D10_2, + PHY_TEST_PATTERN_SYMBOL_ERROR, + PHY_TEST_PATTERN_PRBS7, + PHY_TEST_PATTERN_80BIT_CUSTOM,/* For DP1.2 only */ + PHY_TEST_PATTERN_HBR2_COMPLIANCE_EYE/* For DP1.2 only */ +}; + +enum dpcd_test_dyn_range { + TEST_DYN_RANGE_VESA = 0, + TEST_DYN_RANGE_CEA +}; + +enum dpcd_audio_test_pattern { + AUDIO_TEST_PATTERN_OPERATOR_DEFINED = 0,/* direct HW translation */ + AUDIO_TEST_PATTERN_SAWTOOTH +}; + +enum dpcd_audio_sampling_rate { + AUDIO_SAMPLING_RATE_32KHZ = 0,/* direct HW translation */ + AUDIO_SAMPLING_RATE_44_1KHZ, + AUDIO_SAMPLING_RATE_48KHZ, + AUDIO_SAMPLING_RATE_88_2KHZ, + AUDIO_SAMPLING_RATE_96KHZ, + AUDIO_SAMPLING_RATE_176_4KHZ, + AUDIO_SAMPLING_RATE_192KHZ +}; + +enum dpcd_audio_channels { + AUDIO_CHANNELS_1 = 0,/* direct HW translation */ + AUDIO_CHANNELS_2, + AUDIO_CHANNELS_3, + AUDIO_CHANNELS_4, + AUDIO_CHANNELS_5, + AUDIO_CHANNELS_6, + AUDIO_CHANNELS_7, + AUDIO_CHANNELS_8, + + AUDIO_CHANNELS_COUNT +}; + +enum dpcd_audio_test_pattern_periods { + DPCD_AUDIO_TEST_PATTERN_PERIOD_NOTUSED = 0,/* direct HW translation */ + DPCD_AUDIO_TEST_PATTERN_PERIOD_3, + DPCD_AUDIO_TEST_PATTERN_PERIOD_6, + DPCD_AUDIO_TEST_PATTERN_PERIOD_12, + DPCD_AUDIO_TEST_PATTERN_PERIOD_24, + DPCD_AUDIO_TEST_PATTERN_PERIOD_48, + DPCD_AUDIO_TEST_PATTERN_PERIOD_96, + DPCD_AUDIO_TEST_PATTERN_PERIOD_192, + DPCD_AUDIO_TEST_PATTERN_PERIOD_384, + DPCD_AUDIO_TEST_PATTERN_PERIOD_768, + DPCD_AUDIO_TEST_PATTERN_PERIOD_1536 +}; + +/* This enum is for programming DPCD TRAINING_PATTERN_SET */ +enum dpcd_training_patterns { + DPCD_TRAINING_PATTERN_VIDEOIDLE = 0,/* direct HW translation! */ + DPCD_TRAINING_PATTERN_1, + DPCD_TRAINING_PATTERN_2, + DPCD_TRAINING_PATTERN_3 +}; + +/* This enum is for use with PsrSinkPsrStatus.bits.sinkSelfRefreshStatus +It defines the possible PSR states. */ +enum dpcd_psr_sink_states { + PSR_SINK_STATE_INACTIVE = 0, + PSR_SINK_STATE_ACTIVE_CAPTURE_DISPLAY_ON_SOURCE_TIMING = 1, + PSR_SINK_STATE_ACTIVE_DISPLAY_FROM_SINK_RFB = 2, + PSR_SINK_STATE_ACTIVE_CAPTURE_DISPLAY_ON_SINK_TIMING = 3, + PSR_SINK_STATE_ACTIVE_CAPTURE_TIMING_RESYNC = 4, + PSR_SINK_STATE_SINK_INTERNAL_ERROR = 7, +}; + +/* This enum defines the Panel's eDP revision at DPCD 700h + * 00h = eDP v1.1 or lower + * 01h = eDP v1.2 + * 02h = eDP v1.3 (PSR support starts here) + * 03h = eDP v1.4 + * If unknown revision, treat as eDP v1.1, meaning least functionality set. + * This enum has values matched to eDP spec, thus values should not change. + */ +enum dpcd_edp_revision { + DPCD_EDP_REVISION_EDP_V1_1 = 0, + DPCD_EDP_REVISION_EDP_V1_2 = 1, + DPCD_EDP_REVISION_EDP_V1_3 = 2, + DPCD_EDP_REVISION_EDP_V1_4 = 3, + DPCD_EDP_REVISION_EDP_UNKNOWN = DPCD_EDP_REVISION_EDP_V1_1, +}; + +union dpcd_rev { + struct { + uint8_t MINOR:4; + uint8_t MAJOR:4; + } bits; + uint8_t raw; +}; + +union max_lane_count { + struct { + uint8_t MAX_LANE_COUNT:5; + uint8_t POST_LT_ADJ_REQ_SUPPORTED:1; + uint8_t TPS3_SUPPORTED:1; + uint8_t ENHANCED_FRAME_CAP:1; + } bits; + uint8_t raw; +}; + +union max_down_spread { + struct { + uint8_t MAX_DOWN_SPREAD:1; + uint8_t RESERVED:5; + uint8_t NO_AUX_HANDSHAKE_LINK_TRAINING:1; + uint8_t RESERVED1:1; + } bits; + uint8_t raw; +}; + +union mstm_cap { + struct { + uint8_t MST_CAP:1; + uint8_t RESERVED:7; + } bits; + uint8_t raw; +}; + +union mstm_cntl { + struct { + uint8_t MST_EN:1; + uint8_t UP_REQ_EN:1; + uint8_t UPSTREAM_IS_SRC:1; + uint8_t RESERVED:5; + } bits; + uint8_t raw; +}; + +union lane_count_set { + struct { + uint8_t LANE_COUNT_SET:5; + uint8_t POST_LT_ADJ_REQ_GRANTED:1; + uint8_t RESERVED:1; + uint8_t ENHANCED_FRAMING:1; + } bits; + uint8_t raw; +}; + +/* for DPCD_ADDRESS_I2C_SPEED_CNTL_CAP + * and DPCD_ADDRESS_I2C_SPEED_CNTL + */ +union i2c_speed { + struct { + uint8_t _1KBPS:1; + uint8_t _5KBPS:1; + uint8_t _10KBPS:1; + uint8_t _100KBPS:1; + uint8_t _400KBPS:1; + uint8_t _1MBPS:1; + uint8_t reserved:2; + } bits; + uint8_t raw; +}; + +union payload_table_update_status { + struct { + uint8_t VC_PAYLOAD_TABLE_UPDATED:1; + uint8_t ACT_HANDLED:1; + } bits; + uint8_t raw; +}; + +union device_irq_esi_0 { + struct { + uint8_t REMOTE_CONTROL_CMD_PENDING:1; + uint8_t AUTOMATED_TEST_REQUEST:1; + uint8_t CP_IRQ:1; + uint8_t MCCS_IRQ:1; + uint8_t DOWN_REP_MSG_RDY:1; + uint8_t UP_REQ_MSG_RDY:1; + uint8_t SINK_SPECIFIC_IRQ:1; + uint8_t RESERVED:1; + } bits; + uint8_t raw; +}; + +union lane_status { + struct { + uint8_t CR_DONE_0:1; + uint8_t CHANNEL_EQ_DONE_0:1; + uint8_t SYMBOL_LOCKED_0:1; + uint8_t RESERVED0:1; + uint8_t CR_DONE_1:1; + uint8_t CHANNEL_EQ_DONE_1:1; + uint8_t SYMBOL_LOCKED_1:1; + uint8_t RESERVED_1:1; + } bits; + uint8_t raw; +}; + +union device_service_irq { + struct { + uint8_t REMOTE_CONTROL_CMD_PENDING:1; + uint8_t AUTOMATED_TEST:1; + uint8_t CP_IRQ:1; + uint8_t reserved:5; + } bits; + uint8_t raw; +}; + +union downstream_port { + struct { + uint8_t PRESENT:1; + uint8_t TYPE:2; + uint8_t FORMAT_CONV:1; + uint8_t DETAILED_CAPS:1; + uint8_t RESERVED:3; + } bits; + uint8_t raw; +}; + +union sink_count { + struct { + uint8_t SINK_COUNT:6; + uint8_t CPREADY:1; + uint8_t RESERVED:1; + } bits; + uint8_t raw; +}; + +union lane_align_status_updated { + struct { + uint8_t INTERLANE_ALIGN_DONE:1; + uint8_t POST_LT_ADJ_REQ_IN_PROGRESS:1; + uint8_t RESERVED:4; + uint8_t DOWNSTREAM_PORT_STATUS_CHANGED:1; + uint8_t LINK_STATUS_UPDATED:1; + } bits; + uint8_t raw; +}; + +union lane_adjust { + struct { + uint8_t VOLTAGE_SWING_LANE:2; + uint8_t PRE_EMPHASIS_LANE:2; + uint8_t RESERVED:4; + } bits; + uint8_t raw; +}; + +/* Automated test structures */ +union test_request { + struct { + uint8_t LINK_TRAINING:1; + uint8_t LINK_TEST_PATTERN:1; + uint8_t EDID_READ:1; + uint8_t PHY_TEST_PATTERN:1; + uint8_t AUDIO_TEST_PATTERN:1; + uint8_t AUDIO_TEST_NO_VIDEO:1; + uint8_t RESERVED:1; + uint8_t TEST_STEREO_3D:1; + } bits; + uint8_t raw; +}; + +union test_response { + struct { + uint8_t ACK:1; + uint8_t NO_ACK:1; + uint8_t RESERVED:6; + } bits; + uint8_t raw; +}; + +union link_test_pattern { + struct { + uint8_t PATTERN:2;/*DpcdLinkTestPatterns*/ + uint8_t RESERVED:6; + } bits; + uint8_t raw; +}; + +union test_misc { + struct dpcd_test_misc_bits { + uint8_t SYNC_CLOCK:1; + uint8_t CLR_FORMAT:2;/*DpcdTestColorFormat*/ + uint8_t DYN_RANGE:1;/*DpcdTestDynRange*/ + uint8_t YCBCR:1;/*DpcdTestYCbCrStandard*/ + uint8_t BPC:3;/*DpcdTestBitDepth*/ + } bits; + uint8_t raw; +}; + +union phy_test_pattern { + struct { + /* This field is 2 bits for DP1.1 and 3 bits for DP1.2.*/ + uint8_t PATTERN:3; + uint8_t RESERVED:5;/* BY spec, bit7:2 is 0 for DP1.1.*/ + } bits; + uint8_t raw; +}; + +union audio_test_mode { + struct { + uint8_t SAMPLING_RATE:4; + uint8_t CHANNEL_COUNT:4; + } bits; + uint8_t raw; +}; + +union audio_tes_tpattern_period { + struct { + uint8_t PATTERN_PERIOD:4; + uint8_t RESERVED:4; + } bits; + uint8_t raw; +}; + +struct audio_test_pattern_type { + uint8_t value; +}; + +union dpcd_training_pattern { + struct { + uint8_t TRAINING_PATTERN_SET:2; + uint8_t LINK_QUAL_PATTERN_SET:2; + uint8_t RECOVERED_CLOCK_OUT_EN:1; + uint8_t SCRAMBLING_DISABLE:1; + uint8_t RESERVED:2; + } bits; + uint8_t raw; +}; + +/* Training Lane is used to configure downstream DP device's voltage swing +and pre-emphasis levels*/ +/* The DPCD addresses are from 0x103 to 0x106*/ +union dpcd_training_lane { + struct { + uint8_t VOLTAGE_SWING_SET:2; + uint8_t MAX_SWING_REACHED:1; + uint8_t PRE_EMPHASIS_SET:2; + uint8_t MAX_PRE_EMPHASIS_REACHED:1; + uint8_t RESERVED:2; + } bits; + uint8_t raw; +}; + +/*Training Lane Set 2 is used to configure downstream DP device's +post cursor 2 level of Training Pattern 2 or 3*/ +/* The DPCD addresses are 0x10F (TRAINING_LANE0_1_SET2) +and 0x110 (TRAINING_LANE2_3_SET2)*/ +union dpcd_training_lane_set2 { + struct { + uint8_t POST_CURSOR2_SET:2; + uint8_t MAX_POST_CURSOR2_REACHED:1; + uint8_t RESERVED:1; + } bits; + uint8_t raw; +}; + +union dpcd_psr_configuration { + struct { + uint8_t ENABLE:1; + uint8_t TRANSMITTER_ACTIVE_IN_PSR:1; + uint8_t CRC_VERIFICATION:1; + uint8_t FRAME_CAPTURE_INDICATION:1; + uint8_t LINE_CAPTURE_INDICATION:1; + uint8_t IRQ_HPD_WITH_CRC_ERROR:1; + uint8_t RESERVED:2; + } bits; + uint8_t raw; +}; + +union psr_error_status { + struct { + uint8_t LINK_CRC_ERROR:1; + uint8_t RFB_STORAGE_ERROR:1; + uint8_t RESERVED:6; + } bits; + uint8_t raw; +}; + +union psr_event_status_ind { + struct { + uint8_t SINK_PSR_CAP_CHANGE:1; + uint8_t RESERVED:7; + } bits; + uint8_t raw; +}; + +union psr_sink_psr_status { + struct { + uint8_t SINK_SELF_REFRESH_STATUS:3; + uint8_t RESERVED:5; + } bits; + uint8_t raw; +}; + +/* EDP related 0x701 */ +union edp_generial_cap1 { + struct { + uint8_t TCON_BACKLIGHT_ADJUSTMENT_CAPABLE:1; + uint8_t BACKLIGHT_PIN_ENABLE_CAPABLE:1; + uint8_t BACKLIGHT_AUX_ENABLE_CAPABLE:1; + uint8_t PANEL_SELFTEST_PIN_ENABLE_CAPABLE:1; + uint8_t BACKLIGHT_SELFTEST_AUX_ENABLE_CAPABLE:1; + uint8_t FRC_ENABLE_CAPABLE:1; + uint8_t COLOR_ENGINE_CAPABLE:1; + /*bit 7, pane can be controlled by 0x600*/ + uint8_t SET_POWER_CAPABLE:1; + } bits; + uint8_t raw; +}; + +/* TMDS-converter related */ +union dwnstream_port_caps_byte0 { + struct { + uint8_t DWN_STRM_PORTX_TYPE:3; + uint8_t DWN_STRM_PORTX_HPD:1; + uint8_t RESERVERD:4; + } bits; + uint8_t raw; +}; + +/* these are the detailed types stored at DWN_STRM_PORTX_CAP (00080h)*/ +enum dpcd_downstream_port_detailed_type { + DOWN_STREAM_DETAILED_DP = 0, + DOWN_STREAM_DETAILED_VGA, + DOWN_STREAM_DETAILED_DVI, + DOWN_STREAM_DETAILED_HDMI, + DOWN_STREAM_DETAILED_NONDDC,/* has no EDID (TV,CV)*/ + DOWN_STREAM_DETAILED_DP_PLUS_PLUS +}; + +union dwnstream_port_caps_byte2 { + struct { + uint8_t MAX_BITS_PER_COLOR_COMPONENT:2; + uint8_t RESERVED:6; + } bits; + uint8_t raw; +}; + +union dwnstream_port_caps_byte3_dvi { + struct { + uint8_t RESERVED1:1; + uint8_t DUAL_LINK:1; + uint8_t HIGH_COLOR_DEPTH:1; + uint8_t RESERVED2:5; + } bits; + uint8_t raw; +}; + +union dwnstream_port_caps_byte3_hdmi { + struct { + uint8_t FRAME_SEQ_TO_FRAME_PACK:1; + uint8_t RESERVED:7; + } bits; + uint8_t raw; +}; + +/*4-byte structure for detailed capabilities of a down-stream port +(DP-to-TMDS converter).*/ +union dwnstream_portx_caps { + struct { + union dwnstream_port_caps_byte0 byte0; + uint8_t max_tmds_clk;/* byte1 */ + union dwnstream_port_caps_byte2 byte2; + + union { + union dwnstream_port_caps_byte3_dvi byte_dvi; + union dwnstream_port_caps_byte3_hdmi byte_hdmi; + } byte3; + } bytes; + uint8_t raw[4]; +}; + +union sink_status { + struct { + uint8_t RX_PORT0_STATUS:1; + uint8_t RX_PORT1_STATUS:1; + uint8_t RESERVED:6; + } bits; + uint8_t raw; +}; + +/*6-byte structure corresponding to 6 registers (200h-205h) +read during handling of HPD-IRQ*/ +union hpd_irq_data { + struct { + union sink_count sink_cnt;/* 200h */ + union device_service_irq device_Service_Irq;/* 201h */ + union lane_status lane01_status;/* 202h */ + union lane_status lane23_status;/* 203h */ + union lane_align_status_updated lane_Status_Updated;/* 204h */ + union sink_status sink_status; + } bytes; + uint8_t raw[6]; +}; + +union down_stream_port_count { + struct { + uint8_t DOWN_STR_PORT_COUNT:4; + uint8_t RESERVED:2; /*Bits 5:4 = RESERVED. Read all 0s.*/ + /*Bit 6 = MSA_TIMING_PAR_IGNORED + 0 = Sink device requires the MSA timing parameters + 1 = Sink device is capable of rendering incoming video + stream without MSA timing parameters*/ + uint8_t IGNORE_MSA_TIMING_PARAM:1; + /*Bit 7 = OUI Support + 0 = OUI not supported + 1 = OUI supported + (OUI and Device Identification mandatory for DP 1.2)*/ + uint8_t OUI_SUPPORT:1; + } bits; + uint8_t raw; +}; + +union down_spread_ctrl { + struct { + uint8_t RESERVED1:4;/* Bit 3:0 = RESERVED. Read all 0s*/ + /* Bits 4 = SPREAD_AMP. Spreading amplitude + 0 = Main link signal is not downspread + 1 = Main link signal is downspread <= 0.5% + with frequency in the range of 30kHz ~ 33kHz*/ + uint8_t SPREAD_AMP:1; + uint8_t RESERVED2:2;/*Bit 6:5 = RESERVED. Read all 0s*/ + /*Bit 7 = MSA_TIMING_PAR_IGNORE_EN + 0 = Source device will send valid data for the MSA Timing Params + 1 = Source device may send invalid data for these MSA Timing Params*/ + uint8_t IGNORE_MSA_TIMING_PARAM:1; + } bits; + uint8_t raw; +}; + +union dpcd_edp_config { + struct { + uint8_t ALT_SCRAMBLER_RESET_ENABLE:1; + uint8_t FRAMING_CHANGE_ENABLE:1; + uint8_t RESERVED:5; + uint8_t PANEL_SELF_TEST_ENABLE:1; + } bits; + uint8_t raw; +}; + +struct dp_device_vendor_id { + uint8_t ieee_oui[3];/*24-bit IEEE OUI*/ + uint8_t ieee_device_id[6];/*usually 6-byte ASCII name*/ +}; + +struct dp_sink_hw_fw_revision { + uint8_t ieee_hw_rev; + uint8_t ieee_fw_rev[2]; +}; + +/*DPCD register of DP receiver capability field bits-*/ +union edp_configuration_cap { + struct { + uint8_t ALT_SCRAMBLER_RESET:1; + uint8_t FRAMING_CHANGE:1; + uint8_t RESERVED:1; + uint8_t DPCD_DISPLAY_CONTROL_CAPABLE:1; + uint8_t RESERVED2:4; + } bits; + uint8_t raw; +}; + +union psr_capabilities { + struct { + uint8_t EXIT_LT_NOT_REQ:1; + uint8_t RFB_SETUP_TIME:3; + uint8_t RESERVED:4; + } bits; + uint8_t raw; +}; + +#endif /* __DAL_DPCD_DEFS_H__ */ diff --git a/drivers/gpu/drm/amd/dal/include/i2caux_interface.h b/drivers/gpu/drm/amd/dal/include/i2caux_interface.h new file mode 100644 index 000000000000..d9e3dc366926 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/include/i2caux_interface.h @@ -0,0 +1,127 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_I2CAUX_INTERFACE_H__ +#define __DAL_I2CAUX_INTERFACE_H__ + +#include "ddc_interface.h" +#include "adapter_service_interface.h" + +struct i2c_payload { + bool write; + uint8_t address; + uint8_t length; + uint8_t *data; +}; + +enum i2c_command_engine { + I2C_COMMAND_ENGINE_DEFAULT, + I2C_COMMAND_ENGINE_SW, + I2C_COMMAND_ENGINE_HW +}; + +struct i2c_command { + struct i2c_payload *payloads; + uint8_t number_of_payloads; + + enum i2c_command_engine engine; + + /* expressed in KHz + * zero means "use default value" */ + uint32_t speed; +}; + +#define DEFAULT_AUX_MAX_DATA_SIZE 16 +#define AUX_MAX_DEFER_WRITE_RETRY 20 + +struct aux_payload { + /* set following flag to read/write I2C data, + * reset it to read/write DPCD data */ + bool i2c_over_aux; + /* set following flag to write data, + * reset it to read data */ + bool write; + uint32_t address; + uint8_t length; + uint8_t *data; +}; + +struct aux_command { + struct aux_payload *payloads; + uint8_t number_of_payloads; + + /* expressed in milliseconds + * zero means "use default value" */ + uint32_t defer_delay; + + /* zero means "use default value" */ + uint32_t max_defer_write_retry; +}; + +union aux_config { + struct { + uint32_t ALLOW_AUX_WHEN_HPD_LOW:1; + } bits; + uint32_t raw; +}; + +struct i2caux; + +struct i2caux *dal_i2caux_create( + struct adapter_service *as, + struct dal_context *dal_context); + +bool dal_i2caux_submit_i2c_command( + struct i2caux *i2caux, + struct ddc *ddc, + struct i2c_command *cmd); + +bool dal_i2caux_submit_aux_command( + struct i2caux *i2caux, + struct ddc *ddc, + struct aux_command *cmd); + +void dal_i2caux_keep_engine_power_up( + struct i2caux *i2caux, + struct ddc *ddc, + bool keep_power_up); + +bool dal_i2caux_start_gtc_sync( + struct i2caux *i2caux, + struct ddc *ddc); + +bool dal_i2caux_stop_gtc_sync( + struct i2caux *i2caux, + struct ddc *ddc); + +void dal_i2caux_configure_aux( + struct i2caux *i2caux, + struct ddc *ddc, + union aux_config cfg); + +void dal_i2caux_destroy( + struct i2caux **ptr); + +#endif diff --git a/drivers/gpu/drm/amd/dal/include/link_service_types.h b/drivers/gpu/drm/amd/dal/include/link_service_types.h new file mode 100644 index 000000000000..a241fbb1c632 --- /dev/null +++ b/drivers/gpu/drm/amd/dal/include/link_service_types.h @@ -0,0 +1,426 @@ +/* + * Copyright 2012-15 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DAL_LINK_SERVICE_TYPES_H__ +#define __DAL_LINK_SERVICE_TYPES_H__ + +#include "dal_services_types.h" + +#include "grph_object_id.h" +#include "dpcd_defs.h" +#include "dal_types.h" +#include "irq_types.h" + +/*struct mst_mgr_callback_object;*/ +struct ddc; +struct irq_manager; + +enum link_service_type { + LINK_SERVICE_TYPE_LEGACY = 0, + LINK_SERVICE_TYPE_DP_SST, + LINK_SERVICE_TYPE_DP_MST, + LINK_SERVICE_TYPE_MAX +}; + +struct link_validation_flags { + uint32_t DYNAMIC_VALIDATION:1; + uint32_t CANDIDATE_TIMING:1; + uint32_t START_OF_VALIDATION:1; +}; + +/* Post Cursor 2 is optional for transmitter + * and it applies only to the main link operating at HBR2 + */ +enum post_cursor2 { + POST_CURSOR2_DISABLED = 0, /* direct HW translation! */ + POST_CURSOR2_LEVEL1, + POST_CURSOR2_LEVEL2, + POST_CURSOR2_LEVEL3, + POST_CURSOR2_MAX_LEVEL = POST_CURSOR2_LEVEL3, +}; + +enum voltage_swing { + VOLTAGE_SWING_LEVEL0 = 0, /* direct HW translation! */ + VOLTAGE_SWING_LEVEL1, + VOLTAGE_SWING_LEVEL2, + VOLTAGE_SWING_LEVEL3, + VOLTAGE_SWING_MAX_LEVEL = VOLTAGE_SWING_LEVEL3 +}; + +enum pre_emphasis { + PRE_EMPHASIS_DISABLED = 0, /* direct HW translation! */ + PRE_EMPHASIS_LEVEL1, + PRE_EMPHASIS_LEVEL2, + PRE_EMPHASIS_LEVEL3, + PRE_EMPHASIS_MAX_LEVEL = PRE_EMPHASIS_LEVEL3 +}; + +enum dpcd_value_mask { + DPCD_VALUE_MASK_MAX_LANE_COUNT_LANE_COUNT = 0x1F, + DPCD_VALUE_MASK_MAX_LANE_COUNT_TPS3_SUPPORTED = 0x40, + DPCD_VALUE_MASK_MAX_LANE_COUNT_ENHANCED_FRAME_EN = 0x80, + DPCD_VALUE_MASK_MAX_DOWNSPREAD = 0x01, + DPCD_VALUE_MASK_LANE_ALIGN_STATUS_INTERLANE_ALIGN_DONE = 0x01 +}; + +enum dp_power_state { + DP_POWER_STATE_D0 = 1, + DP_POWER_STATE_D3 +}; + +enum dpcd_downstream_port_types { + DPCD_DOWNSTREAM_DP, + DPCD_DOWNSTREAM_VGA, + DPCD_DOWNSTREAM_DVI_HDMI, + /* has no EDID (TV, CV) */ + DPCD_DOWNSTREAM_NON_DDC +}; + +enum edp_revision { + /* eDP version 1.1 or lower */ + EDP_REVISION_11 = 0x00, + /* eDP version 1.2 */ + EDP_REVISION_12 = 0x01, + /* eDP version 1.3 */ + EDP_REVISION_13 = 0x02 +}; + +enum lane_count { + LANE_COUNT_UNKNOWN = 0, + LANE_COUNT_ONE = 1, + LANE_COUNT_TWO = 2, + LANE_COUNT_FOUR = 4, + LANE_COUNT_EIGHT = 8, + LANE_COUNT_DP_MAX = LANE_COUNT_FOUR +}; + +/* This is actually a reference clock (27MHz) multiplier + * 162MBps bandwidth for 1.62GHz like rate, + * 270MBps for 2.70GHz, + * 324MBps for 3.24Ghz, + * 540MBps for 5.40GHz + */ +enum link_rate { + LINK_RATE_UNKNOWN = 0, + LINK_RATE_LOW = 0x06, + LINK_RATE_HIGH = 0x0A, + LINK_RATE_RBR2 = 0x0C, + LINK_RATE_HIGH2 = 0x14 +}; + +enum { + LINK_RATE_REF_FREQ_IN_KHZ = 27000 /*27MHz*/ +}; + +enum link_spread { + LINK_SPREAD_DISABLED = 0x00, + /* 0.5 % downspread 30 kHz */ + LINK_SPREAD_05_DOWNSPREAD_30KHZ = 0x10, + /* 0.5 % downspread 33 kHz */ + LINK_SPREAD_05_DOWNSPREAD_33KHZ = 0x11 +}; + +/* DPCD_ADDR_DOWNSTREAM_PORT_PRESENT register value */ +union dpcd_downstream_port { + struct { +#if defined(LITTLEENDIAN_CPU) + uint8_t PRESENT:1; + uint8_t TYPE:2; + uint8_t FORMAT_CONV:1; + uint8_t RESERVED:4; +#elif defined(BIGENDIAN_CPU) + uint8_t RESERVED:4; + uint8_t FORMAT_CONV:1; + uint8_t TYPE:2; + uint8_t PRESENT:1; +#else + #error ARCH not defined! +#endif + } bits; + + uint8_t raw; +}; + +/* DPCD_ADDR_SINK_COUNT register value */ +union dpcd_sink_count { + struct { +#if defined(LITTLEENDIAN_CPU) + uint8_t SINK_COUNT:6; + uint8_t CP_READY:1; + uint8_t RESERVED:1; +#elif defined(BIGENDIAN_CPU) + uint8_t RESERVED:1; + uint8_t CP_READY:1; + uint8_t SINK_COUNT:6; +#else + #error ARCH not defined! +#endif + } bits; + + uint8_t raw; +}; + +struct link_settings { + enum lane_count lane_count; + enum link_rate link_rate; + enum link_spread link_spread; +}; + +struct lane_settings { + enum voltage_swing VOLTAGE_SWING:4; + enum pre_emphasis PRE_EMPHASIS:4; + enum post_cursor2 POST_CURSOR2:4; +}; + +struct link_training_settings { + struct link_settings link_settings; + struct lane_settings lane_settings[LANE_COUNT_DP_MAX]; + bool allow_invalid_msa_timing_param; +}; + +enum hw_dp_training_pattern { + HW_DP_TRAINING_PATTERN_1 = 0, + HW_DP_TRAINING_PATTERN_2, + HW_DP_TRAINING_PATTERN_3 +}; + +/*TODO: Move this enum test harness*/ +/* Test patterns*/ +enum dp_test_pattern { + /* Input data is pass through Scrambler + * and 8b10b Encoder straight to output*/ + DP_TEST_PATTERN_VIDEO_MODE = 0, + /* phy test patterns*/ + DP_TEST_PATTERN_D102, + DP_TEST_PATTERN_SYMBOL_ERROR, + DP_TEST_PATTERN_PRBS7, + + DP_TEST_PATTERN_80BIT_CUSTOM, + DP_TEST_PATTERN_HBR2_COMPLIANCE_EYE, + + /* Link Training Patterns */ + DP_TEST_PATTERN_TRAINING_PATTERN1, + DP_TEST_PATTERN_TRAINING_PATTERN2, + DP_TEST_PATTERN_TRAINING_PATTERN3, + + /* link test patterns*/ + DP_TEST_PATTERN_COLOR_SQUARES, + DP_TEST_PATTERN_COLOR_SQUARES_CEA, + DP_TEST_PATTERN_VERTICAL_BARS, + DP_TEST_PATTERN_HORIZONTAL_BARS, + DP_TEST_PATTERN_COLOR_RAMP, + + /* audio test patterns*/ + DP_TEST_PATTERN_AUDIO_OPERATOR_DEFINED, + DP_TEST_PATTERN_AUDIO_SAWTOOTH, + + DP_TEST_PATTERN_UNSUPPORTED +}; + +enum dp_alt_scrambler_reset { + /* not required */ + DP_ALT_SCRAMBLER_RESET_NONE, + /* standard mode for eDP */ + DP_ALT_SCRAMBLER_RESET_STANDARD, + /* external chips specific settings */ + DP_ALT_SCRAMBLER_RESET_SPECIAL +}; + +/** + * @brief LinkServiceInitOptions to set certain bits + */ +struct link_service_init_options { + uint32_t APPLY_MISALIGNMENT_BUG_WORKAROUND:1; +}; + +/** + * @brief data required to initialize LinkService + */ +struct link_service_init_data { + /* number of displays indices which the MST Mgr would manange*/ + uint32_t num_of_displays; + enum link_service_type link_type; + /*struct mst_mgr_callback_object*topology_change_callback;*/ + /* native aux access */ + struct ddc_service *dpcd_access_srv; + /* for calling HWSS to program HW */ + struct hw_sequencer *hwss; + /* the source which to register IRQ on */ + enum dal_irq_source irq_src_hpd_rx; + enum dal_irq_source irq_src_dp_sink; + /* other init options such as SW Workarounds */ + struct link_service_init_options init_options; + uint32_t connector_enum_id; + struct graphics_object_id connector_id; + struct adapter_service *adapter_service; + struct dal_context *dal_context; + struct topology_mgr *tm; +}; + +/** + * @brief LinkServiceInitOptions to set certain bits + */ +struct LinkServiceInitOptions { + uint32_t APPLY_MISALIGNMENT_BUG_WORKAROUND:1; +}; + +/* DPCD_ADDR_TRAINING_LANEx_SET registers value */ +union dpcd_training_lane_set { + struct { +#if defined(LITTLEENDIAN_CPU) + uint8_t VOLTAGE_SWING_SET:2; + uint8_t MAX_SWING_REACHED:1; + uint8_t PRE_EMPHASIS_SET:2; + uint8_t MAX_PRE_EMPHASIS_REACHED:1; + /* following is reserved in DP 1.1 */ + uint8_t POST_CURSOR2_SET:2; +#elif defined(BIGENDIAN_CPU) + uint8_t POST_CURSOR2_SET:2; + uint8_t MAX_PRE_EMPHASIS_REACHED:1; + uint8_t PRE_EMPHASIS_SET:2; + uint8_t MAX_SWING_REACHED:1; + uint8_t VOLTAGE_SWING_SET:2; +#else + #error ARCH not defined! +#endif + } bits; + + uint8_t raw; +}; + +/* DPCD_ADDR_TRAINING_LANEx_SET2 registers value - since DP 1.2 */ +union dpcd_training_lanes_set2 { + struct { +#if defined(LITTLEENDIAN_CPU) + uint8_t LANE0_POST_CURSOR2_SET:2; + uint8_t LANE0_MAX_POST_CURSOR2_REACHED:1; + uint8_t LANE0_RESERVED:1; + uint8_t LANE1_POST_CURSOR2_SET:2; + uint8_t LANE1_MAX_POST_CURSOR2_REACHED:1; + uint8_t LANE1_RESERVED:1; +#elif defined(BIGENDIAN_CPU) + uint8_t LANE1_RESERVED:1; + uint8_t LANE1_MAX_POST_CURSOR2_REACHED:1; + uint8_t LANE1_POST_CURSOR2_SET:2; + uint8_t LANE0_RESERVED:1; + uint8_t LANE0_MAX_POST_CURSOR2_REACHED:1; + uint8_t LANE0_POST_CURSOR2_SET:2; +#else + #error ARCH not defined! +#endif + } bits; + + uint8_t raw; +}; + +/** + * @brief represent the 16 byte + * global unique identifier + */ +struct mst_guid { + uint8_t ids[16]; +}; + +/** + * @brief represents the relative address used + * to identify a node in MST topology network + */ +struct mst_rad { + /* number of links. rad[0] up to + * rad [linkCount - 1] are valid. */ + uint32_t rad_link_count; + /* relative address. rad[0] is the + * first device connected to the source. */ + uint8_t rad[15]; + /* extra 10 bytes for underscores; for e.g.:2_1_8*/ + int8_t rad_str[25]; +}; + +/** + * @brief this structure is used to report + * properties associated to a sink device + */ +struct mst_sink_info { + /* global unique identifier */ + struct mst_guid guid; + /* relative address */ + struct mst_rad rad; + /* total bandwidth available on the DP connector */ + uint32_t total_available_bandwidth_in_mbps; + /* bandwidth allocated to the sink device. */ + uint32_t allocated_bandwidth_in_mbps; + /* bandwidth consumed to support for the current mode. */ + uint32_t consumed_bandwidth_in_mbps; +}; + +/** + * @brief represent device information in MST topology + */ +struct mst_device_info { + /* global unique identifier*/ + struct mst_guid guid; + /* relative address*/ + struct mst_rad rad; +}; + +/* DP MST stream allocation (payload bandwidth number) */ +struct dp_mst_stream_allocation { + /* stream engine id (DIG) */ + enum engine_id engine; + /* number of slots required for the DP stream in + * transport packet */ + uint32_t slot_count; +}; + +/* DP MST stream allocation table */ +struct dp_mst_stream_allocation_table { + /* number of DP video streams */ + uint32_t stream_count; + /* array of stream allocations */ + struct dp_mst_stream_allocation stream_allocations[1]; +}; + +struct dp_test_event_data { + /*size of parameters (starting from params) in bytes*/ + uint32_t size; + /*parameters block*/ + uint32_t params[1]; +}; + +struct psr_caps { + /* These parameters are from PSR capabilities reported by Sink DPCD. */ + uint8_t psr_version; + uint32_t psr_rfb_setup_time; + bool psr_exit_link_training_req; + + /* These parameters are calculated in Driver, based on display timing + * and Sink capabilities. + * If VBLANK region is too small and Sink takes a long time to power up + * Remote Frame Buffer, it may take an extra frame to enter PSR */ + bool psr_frame_capture_indication_req; + uint32_t psr_sdp_transmit_line_num_deadline; +}; + +#endif /*__DAL_LINK_SERVICE_TYPES_H__*/ |