diff options
Diffstat (limited to 'drivers/gpu/drm/drm_edid.c')
-rw-r--r-- | drivers/gpu/drm/drm_edid.c | 55 |
1 files changed, 55 insertions, 0 deletions
diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c index a207cc3f2c57..1688ff500513 100644 --- a/drivers/gpu/drm/drm_edid.c +++ b/drivers/gpu/drm/drm_edid.c | |||
@@ -125,6 +125,9 @@ static struct edid_quirk { | |||
125 | 125 | ||
126 | /* ViewSonic VA2026w */ | 126 | /* ViewSonic VA2026w */ |
127 | { "VSC", 5020, EDID_QUIRK_FORCE_REDUCED_BLANKING }, | 127 | { "VSC", 5020, EDID_QUIRK_FORCE_REDUCED_BLANKING }, |
128 | |||
129 | /* Medion MD 30217 PG */ | ||
130 | { "MED", 0x7b8, EDID_QUIRK_PREFER_LARGE_75 }, | ||
128 | }; | 131 | }; |
129 | 132 | ||
130 | /* | 133 | /* |
@@ -2882,6 +2885,58 @@ int drm_edid_to_sad(struct edid *edid, struct cea_sad **sads) | |||
2882 | EXPORT_SYMBOL(drm_edid_to_sad); | 2885 | EXPORT_SYMBOL(drm_edid_to_sad); |
2883 | 2886 | ||
2884 | /** | 2887 | /** |
2888 | * drm_edid_to_speaker_allocation - extracts Speaker Allocation Data Blocks from EDID | ||
2889 | * @edid: EDID to parse | ||
2890 | * @sadb: pointer to the speaker block | ||
2891 | * | ||
2892 | * Looks for CEA EDID block and extracts the Speaker Allocation Data Block from it. | ||
2893 | * Note: returned pointer needs to be kfreed | ||
2894 | * | ||
2895 | * Return number of found Speaker Allocation Blocks or negative number on error. | ||
2896 | */ | ||
2897 | int drm_edid_to_speaker_allocation(struct edid *edid, u8 **sadb) | ||
2898 | { | ||
2899 | int count = 0; | ||
2900 | int i, start, end, dbl; | ||
2901 | const u8 *cea; | ||
2902 | |||
2903 | cea = drm_find_cea_extension(edid); | ||
2904 | if (!cea) { | ||
2905 | DRM_DEBUG_KMS("SAD: no CEA Extension found\n"); | ||
2906 | return -ENOENT; | ||
2907 | } | ||
2908 | |||
2909 | if (cea_revision(cea) < 3) { | ||
2910 | DRM_DEBUG_KMS("SAD: wrong CEA revision\n"); | ||
2911 | return -ENOTSUPP; | ||
2912 | } | ||
2913 | |||
2914 | if (cea_db_offsets(cea, &start, &end)) { | ||
2915 | DRM_DEBUG_KMS("SAD: invalid data block offsets\n"); | ||
2916 | return -EPROTO; | ||
2917 | } | ||
2918 | |||
2919 | for_each_cea_db(cea, i, start, end) { | ||
2920 | const u8 *db = &cea[i]; | ||
2921 | |||
2922 | if (cea_db_tag(db) == SPEAKER_BLOCK) { | ||
2923 | dbl = cea_db_payload_len(db); | ||
2924 | |||
2925 | /* Speaker Allocation Data Block */ | ||
2926 | if (dbl == 3) { | ||
2927 | *sadb = kmalloc(dbl, GFP_KERNEL); | ||
2928 | memcpy(*sadb, &db[1], dbl); | ||
2929 | count = dbl; | ||
2930 | break; | ||
2931 | } | ||
2932 | } | ||
2933 | } | ||
2934 | |||
2935 | return count; | ||
2936 | } | ||
2937 | EXPORT_SYMBOL(drm_edid_to_speaker_allocation); | ||
2938 | |||
2939 | /** | ||
2885 | * drm_av_sync_delay - HDMI/DP sink audio-video sync delay in millisecond | 2940 | * drm_av_sync_delay - HDMI/DP sink audio-video sync delay in millisecond |
2886 | * @connector: connector associated with the HDMI/DP sink | 2941 | * @connector: connector associated with the HDMI/DP sink |
2887 | * @mode: the display mode | 2942 | * @mode: the display mode |