The DisplayPort driver's sysfs nodes may be present to the userspace before typec_altmode_set_drvdata() completes in dp_altmode_probe. This means that a sysfs read can trigger a NULL pointer error by deferencing dp->hpd in hpd_show or dp->lock in pin_assignment_show, as dev_get_drvdata() returns NULL in those cases.
Verify dp drvdata is present in sysfs reads and writes before proceeding.
Fixes: 0e3bb7d6894d ("usb: typec: Add driver for DisplayPort alternate mode") Cc: stable@vger.kernel.org Signed-off-by: RD Babiera rdbabiera@google.com --- drivers/usb/typec/altmodes/displayport.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+)
diff --git a/drivers/usb/typec/altmodes/displayport.c b/drivers/usb/typec/altmodes/displayport.c index 5a80776c7255..0423326219d8 100644 --- a/drivers/usb/typec/altmodes/displayport.c +++ b/drivers/usb/typec/altmodes/displayport.c @@ -518,6 +518,9 @@ configuration_store(struct device *dev, struct device_attribute *attr, int con; int ret = 0;
+ if (!dp) + return -ENODEV; + con = sysfs_match_string(configurations, buf); if (con < 0) return con; @@ -563,6 +566,9 @@ static ssize_t configuration_show(struct device *dev, u8 cur; int i;
+ if (!dp) + return -ENODEV; + mutex_lock(&dp->lock);
cap = DP_CAP_CAPABILITY(dp->alt->vdo); @@ -615,6 +621,9 @@ pin_assignment_store(struct device *dev, struct device_attribute *attr, u32 conf; int ret;
+ if (!dp) + return -ENODEV; + ret = sysfs_match_string(pin_assignments, buf); if (ret < 0) return ret; @@ -666,6 +675,9 @@ static ssize_t pin_assignment_show(struct device *dev, u8 cur; int i;
+ if (!dp) + return -ENODEV; + mutex_lock(&dp->lock);
cur = get_count_order(DP_CONF_GET_PIN_ASSIGN(dp->data.conf)); @@ -698,6 +710,9 @@ static ssize_t hpd_show(struct device *dev, struct device_attribute *attr, char { struct dp_altmode *dp = dev_get_drvdata(dev);
+ if (!dp) + return -ENODEV; + return sysfs_emit(buf, "%d\n", dp->hpd); } static DEVICE_ATTR_RO(hpd);
base-commit: f1a27f081c1fa1eeebf38406e45f29636114470f