dtrm/edid: Allow comma separated edid binaries. (v3)

Allow comma separated filenames in the edid_firmware parameter.

For example:

edid_firmware=eDP-1:edid/1280x480.bin,DP-2:edid/1920x1080.bin

v2: Use strsep() to simplify parsing of comma seperated string. (Matt)
    Move initial bail before strdup. (Matt)
v3: Changed conditionals after while loop to make more readable (Jani)
    Updated kernel-parameters.txt to reflect changes (Jani)

Reviewed-by: Jani Nikula <jani.nikula@intel.com>
Reviewed-by: Matt Roper <matthew.d.roper@intel.com>
Signed-off-by: Bob Paauwe <bob.j.paauwe@intel.com>
[danvet: Flatten else control flow and appease checkpatch.]
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
This commit is contained in:
Bob Paauwe 2015-08-27 10:04:13 -07:00 коммит произвёл Daniel Vetter
Родитель f8aeb41c4b
Коммит 96206e2922
2 изменённых файлов: 42 добавлений и 14 удалений

Просмотреть файл

@ -927,11 +927,11 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
The filter can be disabled or changed to another
driver later using sysfs.
drm_kms_helper.edid_firmware=[<connector>:]<file>
Broken monitors, graphic adapters and KVMs may
send no or incorrect EDID data sets. This parameter
allows to specify an EDID data set in the
/lib/firmware directory that is used instead.
drm_kms_helper.edid_firmware=[<connector>:]<file>[,[<connector>:]<file>]
Broken monitors, graphic adapters, KVMs and EDIDless
panels may send no or incorrect EDID data sets.
This parameter allows to specify an EDID data sets
in the /lib/firmware directory that are used instead.
Generic built-in EDID data sets are used, if one of
edid/1024x768.bin, edid/1280x1024.bin,
edid/1680x1050.bin, or edid/1920x1080.bin is given
@ -940,7 +940,10 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
available in Documentation/EDID/HOWTO.txt. An EDID
data set will only be used for a particular connector,
if its name and a colon are prepended to the EDID
name.
name. Each connector may use a unique EDID data
set by separating the files with a comma. An EDID
data set with no connector name will be used for
any connectors not explicitly specified.
dscc4.setup= [NET]

Просмотреть файл

@ -264,20 +264,43 @@ out:
int drm_load_edid_firmware(struct drm_connector *connector)
{
const char *connector_name = connector->name;
char *edidname = edid_firmware, *last, *colon;
char *edidname, *last, *colon, *fwstr, *edidstr, *fallback = NULL;
int ret;
struct edid *edid;
if (*edidname == '\0')
if (edid_firmware[0] == '\0')
return 0;
colon = strchr(edidname, ':');
if (colon != NULL) {
if (strncmp(connector_name, edidname, colon - edidname))
return 0;
edidname = colon + 1;
if (*edidname == '\0')
/*
* If there are multiple edid files specified and separated
* by commas, search through the list looking for one that
* matches the connector.
*
* If there's one or more that don't't specify a connector, keep
* the last one found one as a fallback.
*/
fwstr = kstrdup(edid_firmware, GFP_KERNEL);
edidstr = fwstr;
while ((edidname = strsep(&edidstr, ","))) {
colon = strchr(edidname, ':');
if (colon != NULL) {
if (strncmp(connector_name, edidname, colon - edidname))
continue;
edidname = colon + 1;
break;
}
if (*edidname != '\0') /* corner case: multiple ',' */
fallback = edidname;
}
if (!edidname) {
if (!fallback) {
kfree(fwstr);
return 0;
}
edidname = fallback;
}
last = edidname + strlen(edidname) - 1;
@ -285,6 +308,8 @@ int drm_load_edid_firmware(struct drm_connector *connector)
*last = '\0';
edid = edid_load(connector, edidname, connector_name);
kfree(fwstr);
if (IS_ERR_OR_NULL(edid))
return 0;