diff options
author | Paulo Zanoni <paulo.r.zanoni@intel.com> | 2013-06-12 16:27:26 -0400 |
---|---|---|
committer | Daniel Vetter <daniel.vetter@ffwll.ch> | 2013-06-28 08:14:18 -0400 |
commit | b2f246a8998ccf9e00477c8829a62139804e9857 (patch) | |
tree | b91ee5f946cd548bb9a2a97a28de58613a5f1ba0 | |
parent | 16c255335b0ec39b4e5e976f4b260978aeed5a68 (diff) |
drm/i915: fix the "ghost eDP" connector unwind path
Because calling intel_dp_destroy inside intel_edp_init_connector is
just wrong. This is the initialization path, so we should properly
unwind all the initialization through the whole caller stack.
On the intel_dp_destroy function we do the following:
1 - Free edid if it exists
2 - Call intel_panel_fini in case it's eDP
3 - Call drm_sysfs_connector_remove
4 - Call drm_connector_cleanup
5 - Free the connector
And here is how we unwind each specific step:
1 - No need as we still didn't assign anything
2 - No need as we still didn't call intel_panel_init
3 - Call it in the same function that called drm_sysfs_connector_add
4 - Call it in the same function that called drm_connector_init
5 - Free it in the same function that allocated it
Signed-off-by: Paulo Zanoni <paulo.r.zanoni@intel.com>
Reviewed-by: Zoltan Nyul <zoltan.nyul@intel.com>
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
-rw-r--r-- | drivers/gpu/drm/i915/intel_ddi.c | 4 | ||||
-rw-r--r-- | drivers/gpu/drm/i915/intel_dp.c | 9 |
2 files changed, 9 insertions, 4 deletions
diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index 0f835d15c18b..aed363cabe07 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c | |||
@@ -1356,8 +1356,10 @@ void intel_ddi_init(struct drm_device *dev, enum port port) | |||
1356 | intel_encoder->cloneable = false; | 1356 | intel_encoder->cloneable = false; |
1357 | intel_encoder->hot_plug = intel_ddi_hot_plug; | 1357 | intel_encoder->hot_plug = intel_ddi_hot_plug; |
1358 | 1358 | ||
1359 | if (!intel_dp_init_connector(intel_dig_port, dp_connector)) | 1359 | if (!intel_dp_init_connector(intel_dig_port, dp_connector)) { |
1360 | kfree(dp_connector); | ||
1360 | return; | 1361 | return; |
1362 | } | ||
1361 | 1363 | ||
1362 | if (intel_encoder->type != INTEL_OUTPUT_EDP) { | 1364 | if (intel_encoder->type != INTEL_OUTPUT_EDP) { |
1363 | hdmi_connector = kzalloc(sizeof(struct intel_connector), | 1365 | hdmi_connector = kzalloc(sizeof(struct intel_connector), |
diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 1a429cf55291..5ba0a612d463 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c | |||
@@ -2987,7 +2987,6 @@ static bool intel_edp_init_connector(struct intel_dp *intel_dp, | |||
2987 | /* if this fails, presume the device is a ghost */ | 2987 | /* if this fails, presume the device is a ghost */ |
2988 | DRM_INFO("failed to retrieve link info, disabling eDP\n"); | 2988 | DRM_INFO("failed to retrieve link info, disabling eDP\n"); |
2989 | intel_dp_encoder_destroy(&intel_dig_port->base.base); | 2989 | intel_dp_encoder_destroy(&intel_dig_port->base.base); |
2990 | intel_dp_destroy(connector); | ||
2991 | return false; | 2990 | return false; |
2992 | } | 2991 | } |
2993 | 2992 | ||
@@ -3146,8 +3145,11 @@ intel_dp_init_connector(struct intel_digital_port *intel_dig_port, | |||
3146 | 3145 | ||
3147 | intel_dp_i2c_init(intel_dp, intel_connector, name); | 3146 | intel_dp_i2c_init(intel_dp, intel_connector, name); |
3148 | 3147 | ||
3149 | if (!intel_edp_init_connector(intel_dp, intel_connector)) | 3148 | if (!intel_edp_init_connector(intel_dp, intel_connector)) { |
3149 | drm_sysfs_connector_remove(connector); | ||
3150 | drm_connector_cleanup(connector); | ||
3150 | return false; | 3151 | return false; |
3152 | } | ||
3151 | 3153 | ||
3152 | intel_dp_add_properties(intel_dp, connector); | 3154 | intel_dp_add_properties(intel_dp, connector); |
3153 | 3155 | ||
@@ -3206,5 +3208,6 @@ intel_dp_init(struct drm_device *dev, int output_reg, enum port port) | |||
3206 | intel_encoder->cloneable = false; | 3208 | intel_encoder->cloneable = false; |
3207 | intel_encoder->hot_plug = intel_dp_hot_plug; | 3209 | intel_encoder->hot_plug = intel_dp_hot_plug; |
3208 | 3210 | ||
3209 | intel_dp_init_connector(intel_dig_port, intel_connector); | 3211 | if (!intel_dp_init_connector(intel_dig_port, intel_connector)) |
3212 | kfree(intel_connector); | ||
3210 | } | 3213 | } |