@@ -262,6 +262,26 @@ static bool drm_kms_helper_enable_hpd(struct drm_device *dev)
262262}
263263
264264#define DRM_OUTPUT_POLL_PERIOD (10*HZ)
265+ static void reschedule_output_poll_work (struct drm_device * dev )
266+ {
267+ unsigned long delay = DRM_OUTPUT_POLL_PERIOD ;
268+
269+ if (dev -> mode_config .delayed_event )
270+ /*
271+ * FIXME:
272+ *
273+ * Use short (1s) delay to handle the initial delayed event.
274+ * This delay should not be needed, but Optimus/nouveau will
275+ * fail in a mysterious way if the delayed event is handled as
276+ * soon as possible like it is done in
277+ * drm_helper_probe_single_connector_modes() in case the poll
278+ * was enabled before.
279+ */
280+ delay = HZ ;
281+
282+ schedule_delayed_work (& dev -> mode_config .output_poll_work , delay );
283+ }
284+
265285/**
266286 * drm_kms_helper_poll_enable - re-enable output polling.
267287 * @dev: drm_device
@@ -279,37 +299,41 @@ static bool drm_kms_helper_enable_hpd(struct drm_device *dev)
279299 */
280300void drm_kms_helper_poll_enable (struct drm_device * dev )
281301{
282- bool poll = false;
283- unsigned long delay = DRM_OUTPUT_POLL_PERIOD ;
284-
285302 if (!dev -> mode_config .poll_enabled || !drm_kms_helper_poll ||
286303 dev -> mode_config .poll_running )
287304 return ;
288305
289- poll = drm_kms_helper_enable_hpd (dev );
290-
291- if (dev -> mode_config .delayed_event ) {
292- /*
293- * FIXME:
294- *
295- * Use short (1s) delay to handle the initial delayed event.
296- * This delay should not be needed, but Optimus/nouveau will
297- * fail in a mysterious way if the delayed event is handled as
298- * soon as possible like it is done in
299- * drm_helper_probe_single_connector_modes() in case the poll
300- * was enabled before.
301- */
302- poll = true;
303- delay = HZ ;
304- }
305-
306- if (poll )
307- schedule_delayed_work (& dev -> mode_config .output_poll_work , delay );
306+ if (drm_kms_helper_enable_hpd (dev ) ||
307+ dev -> mode_config .delayed_event )
308+ reschedule_output_poll_work (dev );
308309
309310 dev -> mode_config .poll_running = true;
310311}
311312EXPORT_SYMBOL (drm_kms_helper_poll_enable );
312313
314+ /**
315+ * drm_kms_helper_poll_reschedule - reschedule the output polling work
316+ * @dev: drm_device
317+ *
318+ * This function reschedules the output polling work, after polling for a
319+ * connector has been enabled.
320+ *
321+ * Drivers must call this helper after enabling polling for a connector by
322+ * setting %DRM_CONNECTOR_POLL_CONNECT / %DRM_CONNECTOR_POLL_DISCONNECT flags
323+ * in drm_connector::polled. Note that after disabling polling by clearing these
324+ * flags for a connector will stop the output polling work automatically if
325+ * the polling is disabled for all other connectors as well.
326+ *
327+ * The function can be called only after polling has been enabled by calling
328+ * drm_kms_helper_poll_init() / drm_kms_helper_poll_enable().
329+ */
330+ void drm_kms_helper_poll_reschedule (struct drm_device * dev )
331+ {
332+ if (dev -> mode_config .poll_running )
333+ reschedule_output_poll_work (dev );
334+ }
335+ EXPORT_SYMBOL (drm_kms_helper_poll_reschedule );
336+
313337static enum drm_connector_status
314338drm_helper_probe_detect_ctx (struct drm_connector * connector , bool force )
315339{
0 commit comments