drm/modes: Fix the command line parser to take force options into account
authorMaxime Ripard <maxime.ripard@bootlin.com>
Tue, 27 Aug 2019 11:58:48 +0000 (13:58 +0200)
committerMaxime Ripard <mripard@kernel.org>
Fri, 30 Aug 2019 08:19:15 +0000 (10:19 +0200)
The command line parser when it has been rewritten introduced a regression
when the only thing on the command line is an option to force the detection
of a connector (such as video=HDMI-A-1:d), which are completely valid.

It's been further broken by the support for the named modes which take
anything that is not a resolution as a named mode.

Let's fix this by running the extra command line option parser on the named
modes if they only take a single character.

Fixes: e08ab74bd4c7 ("drm/modes: Rewrite the command line parser")
Reported-by: Jernej Škrabec <jernej.skrabec@gmail.com>
Reported-by: Thomas Graichen <thomas.graichen@googlemail.com>
Signed-off-by: Maxime Ripard <maxime.ripard@bootlin.com>
Tested-by: Thomas Graichen <thomas.graichen@gmail.com>
Reviewed-by: Jernej Skrabec <jernej.skrabec@siol.net>
Signed-off-by: Maxime Ripard <mripard@kernel.org>
Link: https://patchwork.freedesktop.org/patch/msgid/20190827115850.25731-2-mripard@kernel.org
drivers/gpu/drm/drm_modes.c

index 3d10425f6b181506d1c4327ce5a7112f25f34d26..27fe410bba5c4ff3ca6bed71dd7d73eb509c2c5a 100644 (file)
@@ -1733,16 +1733,30 @@ bool drm_mode_parse_command_line_for_connector(const char *mode_option,
         * bunch of things:
         *   - We need to make sure that the first character (which
         *     would be our resolution in X) is a digit.
-        *   - However, if the X resolution is missing, then we end up
-        *     with something like x<yres>, with our first character
-        *     being an alpha-numerical character, which would be
-        *     considered a named mode.
+        *   - If not, then it's either a named mode or a force on/off.
+        *     To distinguish between the two, we need to run the
+        *     extra parsing function, and if not, then we consider it
+        *     a named mode.
         *
         * If this isn't enough, we should add more heuristics here,
         * and matching unit-tests.
         */
-       if (!isdigit(name[0]) && name[0] != 'x')
+       if (!isdigit(name[0]) && name[0] != 'x') {
+               unsigned int namelen = strlen(name);
+
+               /*
+                * Only the force on/off options can be in that case,
+                * and they all take a single character.
+                */
+               if (namelen == 1) {
+                       ret = drm_mode_parse_cmdline_extra(name, namelen, true,
+                                                          connector, mode);
+                       if (!ret)
+                               return true;
+               }
+
                named_mode = true;
+       }
 
        /* Try to locate the bpp and refresh specifiers, if any */
        bpp_ptr = strchr(name, '-');