<div dir="ltr">When getting this patch for -collector I noticed it conflicts with mgag200 and break its compilation.</div><div class="gmail_extra"><br><br><div class="gmail_quote">On Wed, Jun 11, 2014 at 3:55 AM, Chris Wilson <span dir="ltr"><<a href="mailto:chris@chris-wilson.co.uk" target="_blank">chris@chris-wilson.co.uk</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">i915.ko has a custom fbdev initialisation routine that aims to preserve<br>
the current mode set by the BIOS, unless overruled by the user. The<br>
user's wishes are determined by what, if any, mode is specified on the<br>
command line (via the video= parameter). However, that command line mode<br>
is first parsed by drm_fb_helper_initial_config() which is called after<br>
i915.ko's custom initial_config() as a fallback method. So in order for<br>
us to honour it, we need to move the cmdline parser earlier. If we<br>
perform the connector cmdline parsing as soon as we initialise the<br>
connector, that cmdline mode and forced status is then available even if<br>
the fbdev helper is not compiled in or never called.<br>
<br>
We also then expose the cmdline user mode in the connector mode lists.<br>
<br>
v2: Rebase after connector->name upheaval.<br>
<br>
Bugzilla: <a href="https://bugs.freedesktop.org/show_bug.cgi?id=73154" target="_blank">https://bugs.freedesktop.org/show_bug.cgi?id=73154</a><br>
Signed-off-by: Chris Wilson <<a href="mailto:chris@chris-wilson.co.uk">chris@chris-wilson.co.uk</a>><br>
Cc: Jesse Barnes <<a href="mailto:jbarnes@virtuousgeek.org">jbarnes@virtuousgeek.org</a>><br>
Cc: Ville Syrjälä <<a href="mailto:ville.syrjala@linux.intel.com">ville.syrjala@linux.intel.com</a>><br>
Cc: Daniel Vetter <<a href="mailto:daniel.vetter@ffwll.ch">daniel.vetter@ffwll.ch</a>><br>
Reviewed-by: Jesse Barnes <<a href="mailto:jbarnes@virtuousgeek.org">jbarnes@virtuousgeek.org</a>><br>
Cc: <a href="mailto:dri-devel@lists.freedesktop.org">dri-devel@lists.freedesktop.org</a><br>
---<br>
 drivers/gpu/drm/drm_crtc.c         | 55 ++++++++++++++++++++++++++++++++<br>
 drivers/gpu/drm/drm_fb_helper.c    | 64 ++------------------------------------<br>
 drivers/gpu/drm/drm_modes.c        |  1 +<br>
 drivers/gpu/drm/drm_probe_helper.c | 17 ++++++++++<br>
 include/drm/drm_crtc.h             |  1 +<br>
 include/drm/drm_fb_helper.h        |  1 -<br>
 6 files changed, 77 insertions(+), 62 deletions(-)<br>
<br>
diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c<br>
index fe94cc10cd35..b9de156515b6 100644<br>
--- a/drivers/gpu/drm/drm_crtc.c<br>
+++ b/drivers/gpu/drm/drm_crtc.c<br>
@@ -819,6 +819,59 @@ static void drm_mode_remove(struct drm_connector *connector,<br>
 }<br>
<br>
 /**<br>
+ * drm_connector_get_cmdline_mode - reads the user's cmdline mode<br>
+ * @connector: connector to quwery<br>
+ * @mode: returned mode<br>
+ *<br>
+ * The kernel supports per-connector configration of its consoles through<br>
+ * use of the video= parameter. This function parses that option and<br>
+ * extracts the user's specified mode (or enable/disable status) for a<br>
+ * particular connector. This is typically only used during the early fbdev<br>
+ * setup.<br>
+ */<br>
+static void drm_connector_get_cmdline_mode(struct drm_connector *connector)<br>
+{<br>
+       struct drm_cmdline_mode *mode = &connector->cmdline_mode;<br>
+       char *option = NULL;<br>
+<br>
+       if (fb_get_options(connector->name, &option))<br>
+               return;<br>
+<br>
+       if (!drm_mode_parse_command_line_for_connector(option,<br>
+                                                      connector,<br>
+                                                      mode))<br>
+               return;<br>
+<br>
+       if (mode->force) {<br>
+               const char *s;<br>
+<br>
+               switch (mode->force) {<br>
+               case DRM_FORCE_OFF:<br>
+                       s = "OFF";<br>
+                       break;<br>
+               case DRM_FORCE_ON_DIGITAL:<br>
+                       s = "ON - dig";<br>
+                       break;<br>
+               default:<br>
+               case DRM_FORCE_ON:<br>
+                       s = "ON";<br>
+                       break;<br>
+               }<br>
+<br>
+               DRM_INFO("forcing %s connector %s\n", connector->name, s);<br>
+               connector->force = mode->force;<br>
+       }<br>
+<br>
+       DRM_DEBUG_KMS("cmdline mode for connector %s %dx%d@%dHz%s%s%s\n",<br>
+                     connector->name,<br>
+                     mode->xres, mode->yres,<br>
+                     mode->refresh_specified ? mode->refresh : 60,<br>
+                     mode->rb ? " reduced blanking" : "",<br>
+                     mode->margins ? " with margins" : "",<br>
+                     mode->interlace ?  " interlaced" : "");<br>
+}<br>
+<br>
+/**<br>
  * drm_connector_init - Init a preallocated connector<br>
  * @dev: DRM device<br>
  * @connector: the connector to init<br>
@@ -870,6 +923,8 @@ int drm_connector_init(struct drm_device *dev,<br>
        connector->edid_blob_ptr = NULL;<br>
        connector->status = connector_status_unknown;<br>
<br>
+       drm_connector_get_cmdline_mode(connector);<br>
+<br>
        list_add_tail(&connector->head, &dev->mode_config.connector_list);<br>
        dev->mode_config.num_connector++;<br>
<br>
diff --git a/drivers/gpu/drm/drm_fb_helper.c b/drivers/gpu/drm/drm_fb_helper.c<br>
index d5d8cea1a679..18988dc3de91 100644<br>
--- a/drivers/gpu/drm/drm_fb_helper.c<br>
+++ b/drivers/gpu/drm/drm_fb_helper.c<br>
@@ -105,60 +105,6 @@ fail:<br>
 }<br>
 EXPORT_SYMBOL(drm_fb_helper_single_add_all_connectors);<br>
<br>
-static int drm_fb_helper_parse_command_line(struct drm_fb_helper *fb_helper)<br>
-{<br>
-       struct drm_fb_helper_connector *fb_helper_conn;<br>
-       int i;<br>
-<br>
-       for (i = 0; i < fb_helper->connector_count; i++) {<br>
-               struct drm_cmdline_mode *mode;<br>
-               struct drm_connector *connector;<br>
-               char *option = NULL;<br>
-<br>
-               fb_helper_conn = fb_helper->connector_info[i];<br>
-               connector = fb_helper_conn->connector;<br>
-               mode = &fb_helper_conn->cmdline_mode;<br>
-<br>
-               /* do something on return - turn off connector maybe */<br>
-               if (fb_get_options(connector->name, &option))<br>
-                       continue;<br>
-<br>
-               if (drm_mode_parse_command_line_for_connector(option,<br>
-                                                             connector,<br>
-                                                             mode)) {<br>
-                       if (mode->force) {<br>
-                               const char *s;<br>
-                               switch (mode->force) {<br>
-                               case DRM_FORCE_OFF:<br>
-                                       s = "OFF";<br>
-                                       break;<br>
-                               case DRM_FORCE_ON_DIGITAL:<br>
-                                       s = "ON - dig";<br>
-                                       break;<br>
-                               default:<br>
-                               case DRM_FORCE_ON:<br>
-                                       s = "ON";<br>
-                                       break;<br>
-                               }<br>
-<br>
-                               DRM_INFO("forcing %s connector %s\n",<br>
-                                        connector->name, s);<br>
-                               connector->force = mode->force;<br>
-                       }<br>
-<br>
-                       DRM_DEBUG_KMS("cmdline mode for connector %s %dx%d@%dHz%s%s%s\n",<br>
-                                     connector->name,<br>
-                                     mode->xres, mode->yres,<br>
-                                     mode->refresh_specified ? mode->refresh : 60,<br>
-                                     mode->rb ? " reduced blanking" : "",<br>
-                                     mode->margins ? " with margins" : "",<br>
-                                     mode->interlace ?  " interlaced" : "");<br>
-               }<br>
-<br>
-       }<br>
-       return 0;<br>
-}<br>
-<br>
 static void drm_fb_helper_save_lut_atomic(struct drm_crtc *crtc, struct drm_fb_helper *helper)<br>
 {<br>
        uint16_t *r_base, *g_base, *b_base;<br>
@@ -936,7 +882,7 @@ static int drm_fb_helper_single_fb_probe(struct drm_fb_helper *fb_helper,<br>
                struct drm_fb_helper_connector *fb_helper_conn = fb_helper->connector_info[i];<br>
                struct drm_cmdline_mode *cmdline_mode;<br>
<br>
-               cmdline_mode = &fb_helper_conn->cmdline_mode;<br>
+               cmdline_mode = &fb_helper_conn->connector->cmdline_mode;<br>
<br>
                if (cmdline_mode->bpp_specified) {<br>
                        switch (cmdline_mode->bpp) {<br>
@@ -1184,9 +1130,7 @@ EXPORT_SYMBOL(drm_has_preferred_mode);<br>
<br>
 static bool drm_has_cmdline_mode(struct drm_fb_helper_connector *fb_connector)<br>
 {<br>
-       struct drm_cmdline_mode *cmdline_mode;<br>
-       cmdline_mode = &fb_connector->cmdline_mode;<br>
-       return cmdline_mode->specified;<br>
+       return fb_connector->connector->cmdline_mode.specified;<br>
 }<br>
<br>
 struct drm_display_mode *drm_pick_cmdline_mode(struct drm_fb_helper_connector *fb_helper_conn,<br>
@@ -1196,7 +1140,7 @@ struct drm_display_mode *drm_pick_cmdline_mode(struct drm_fb_helper_connector *f<br>
        struct drm_display_mode *mode = NULL;<br>
        bool prefer_non_interlace;<br>
<br>
-       cmdline_mode = &fb_helper_conn->cmdline_mode;<br>
+       cmdline_mode = &fb_helper_conn->connector->cmdline_mode;<br>
        if (cmdline_mode->specified == false)<br>
                return mode;<br>
<br>
@@ -1581,8 +1525,6 @@ bool drm_fb_helper_initial_config(struct drm_fb_helper *fb_helper, int bpp_sel)<br>
        struct drm_device *dev = fb_helper->dev;<br>
        int count = 0;<br>
<br>
-       drm_fb_helper_parse_command_line(fb_helper);<br>
-<br>
        mutex_lock(&dev->mode_config.mutex);<br>
        count = drm_fb_helper_probe_connector_modes(fb_helper,<br>
                                                    dev->mode_config.max_width,<br>
diff --git a/drivers/gpu/drm/drm_modes.c b/drivers/gpu/drm/drm_modes.c<br>
index bedf1894e17e..d1b7d2006529 100644<br>
--- a/drivers/gpu/drm/drm_modes.c<br>
+++ b/drivers/gpu/drm/drm_modes.c<br>
@@ -1259,6 +1259,7 @@ drm_mode_create_from_cmdline_mode(struct drm_device *dev,<br>
        if (!mode)<br>
                return NULL;<br>
<br>
+       mode->type |= DRM_MODE_TYPE_USERDEF;<br>
        drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);<br>
        return mode;<br>
 }<br>
diff --git a/drivers/gpu/drm/drm_probe_helper.c b/drivers/gpu/drm/drm_probe_helper.c<br>
index d22676b89cbb..59f663879fd4 100644<br>
--- a/drivers/gpu/drm/drm_probe_helper.c<br>
+++ b/drivers/gpu/drm/drm_probe_helper.c<br>
@@ -82,6 +82,22 @@ static void drm_mode_validate_flag(struct drm_connector *connector,<br>
        return;<br>
 }<br>
<br>
+static int drm_helper_probe_add_cmdline_mode(struct drm_connector *connector)<br>
+{<br>
+       struct drm_display_mode *mode;<br>
+<br>
+       if (!connector->cmdline_mode.specified)<br>
+               return 0;<br>
+<br>
+       mode = drm_mode_create_from_cmdline_mode(connector->dev,<br>
+                                                &connector->cmdline_mode);<br>
+       if (mode == NULL)<br>
+               return 0;<br>
+<br>
+       drm_mode_probed_add(connector, mode);<br>
+       return 1;<br>
+}<br>
+<br>
 static int drm_helper_probe_single_connector_modes_merge_bits(struct drm_connector *connector,<br>
                                                              uint32_t maxX, uint32_t maxY, bool merge_type_bits)<br>
 {<br>
@@ -134,6 +150,7 @@ static int drm_helper_probe_single_connector_modes_merge_bits(struct drm_connect<br>
<br>
        if (count == 0 && connector->status == connector_status_connected)<br>
                count = drm_add_modes_noedid(connector, 1024, 768);<br>
+       count += drm_helper_probe_add_cmdline_mode(connector);<br>
        if (count == 0)<br>
                goto prune;<br>
<br>
diff --git a/include/drm/drm_crtc.h b/include/drm/drm_crtc.h<br>
index 251b75e6bf7a..abaed07a4b3b 100644<br>
--- a/include/drm/drm_crtc.h<br>
+++ b/include/drm/drm_crtc.h<br>
@@ -532,6 +532,7 @@ struct drm_connector {<br>
        void *helper_private;<br>
<br>
        /* forced on connector */<br>
+       struct drm_cmdline_mode cmdline_mode;<br>
        enum drm_connector_force force;<br>
        uint32_t encoder_ids[DRM_CONNECTOR_MAX_ENCODER];<br>
        struct drm_encoder *encoder; /* currently active encoder */<br>
diff --git a/include/drm/drm_fb_helper.h b/include/drm/drm_fb_helper.h<br>
index 7997246d4039..28ead2b6f59b 100644<br>
--- a/include/drm/drm_fb_helper.h<br>
+++ b/include/drm/drm_fb_helper.h<br>
@@ -77,7 +77,6 @@ struct drm_fb_helper_funcs {<br>
<br>
 struct drm_fb_helper_connector {<br>
        struct drm_connector *connector;<br>
-       struct drm_cmdline_mode cmdline_mode;<br>
 };<br>
<br>
 struct drm_fb_helper {<br>
<span class="HOEnZb"><font color="#888888">--<br>
2.0.0<br>
<br>
_______________________________________________<br>
Intel-gfx mailing list<br>
<a href="mailto:Intel-gfx@lists.freedesktop.org">Intel-gfx@lists.freedesktop.org</a><br>
<a href="http://lists.freedesktop.org/mailman/listinfo/intel-gfx" target="_blank">http://lists.freedesktop.org/mailman/listinfo/intel-gfx</a><br>
</font></span></blockquote></div><br><br clear="all"><div><br></div>-- <br><div>Rodrigo Vivi</div><div>Blog: <a href="http://blog.vivi.eng.br" target="_blank">http://blog.vivi.eng.br</a></div><div> </div>
</div>