summaryrefslogtreecommitdiff
path: root/include/linux/gpio
diff options
context:
space:
mode:
authorMuchun Song <smuchun@gmail.com>2018-11-01 16:12:50 +0300
committerLinus Walleij <linus.walleij@linaro.org>2018-11-05 10:54:42 +0300
commit18534df419041e6c1f4b41af56ee7d41f757815c (patch)
tree07b00d6af2d33db869f1bb53f6da1f28ad11b473 /include/linux/gpio
parent02cb87f79b6dfd17bb16b71ec30652e76c6d8cf2 (diff)
downloadlinux-18534df419041e6c1f4b41af56ee7d41f757815c.tar.xz
gpiolib: Fix possible use after free on label
gpiod_request_commit() copies the pointer to the label passed as an argument only to be used later. But there's a chance the caller could immediately free the passed string(e.g., local variable). This could trigger a use after free when we use gpio label(e.g., gpiochip_unlock_as_irq(), gpiochip_is_requested()). To be on the safe side: duplicate the string with kstrdup_const() so that if an unaware user passes an address to a stack-allocated buffer, we won't get the arbitrary label. Also fix gpiod_set_consumer_name(). Signed-off-by: Muchun Song <smuchun@gmail.com> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
Diffstat (limited to 'include/linux/gpio')
-rw-r--r--include/linux/gpio/consumer.h6
1 files changed, 4 insertions, 2 deletions
diff --git a/include/linux/gpio/consumer.h b/include/linux/gpio/consumer.h
index f2f887795d43..ed070512b40e 100644
--- a/include/linux/gpio/consumer.h
+++ b/include/linux/gpio/consumer.h
@@ -162,7 +162,7 @@ int gpiod_is_active_low(const struct gpio_desc *desc);
int gpiod_cansleep(const struct gpio_desc *desc);
int gpiod_to_irq(const struct gpio_desc *desc);
-void gpiod_set_consumer_name(struct gpio_desc *desc, const char *name);
+int gpiod_set_consumer_name(struct gpio_desc *desc, const char *name);
/* Convert between the old gpio_ and new gpiod_ interfaces */
struct gpio_desc *gpio_to_desc(unsigned gpio);
@@ -495,10 +495,12 @@ static inline int gpiod_to_irq(const struct gpio_desc *desc)
return -EINVAL;
}
-static inline void gpiod_set_consumer_name(struct gpio_desc *desc, const char *name)
+static inline int gpiod_set_consumer_name(struct gpio_desc *desc,
+ const char *name)
{
/* GPIO can never have been requested */
WARN_ON(1);
+ return -EINVAL;
}
static inline struct gpio_desc *gpio_to_desc(unsigned gpio)