iio: adc: gyroadc: fix leak of device node iterator
Subsystems (3)
PATCH v2 1/1 iio: adc: gyroadc: fix leak of device node iterator
Add missing of_node_put calls when exiting the for_each_child_of_node loop in rcar_gyroadc_parse_subdevs early.
Also add goto-exception handling for the error paths in that loop.
---
v2:
- added an of_node_put to the non-error "break" at the end
- used gotos for the error cases, doesn't look as bad as I thought
drivers/iio/adc/rcar-gyroadc.c | 21 +++++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-)
drivers/iio/adc/rcar-gyroadc.c +15 -6
@@ -357,7 +357,7 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev) num_channels =ARRAY_SIZE (rcar_gyroadc_iio_channels_3);break ;default : -return -EINVAL ; + goto err_e_inval; }/*
@@ -374,7 +374,7 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)dev_err (dev,"Failed to get child reg property of ADC \"%pOFn\".\n" , child); -return ret; + goto err_of_node_put; }/* Channel number is too high. */
@@ -382,7 +382,7 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)dev_err (dev,"Only %i channels supported with %pOFn, but reg = <%i>.\n" , num_channels, child, reg); -return -EINVAL ; + goto err_e_inval; } }
@@ -391,7 +391,7 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)dev_err (dev,"Channel %i uses different ADC mode than the rest.\n" , reg); -return -EINVAL ; + goto err_e_inval; }/* Channel is valid, grab the regulator. */
@@ -401,7 +401,8 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)if (IS_ERR (vref)) {dev_dbg (dev,"Channel %i 'vref' supply not connected.\n" , reg); -return PTR_ERR (vref); + ret =PTR_ERR (vref); + goto err_of_node_put; } priv->vref[reg] = vref;
@@ -425,8 +426,10 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)* attached to the GyroADC at a time, so if we found it, * we can stop parsing here. */ -if (childmode ==RCAR_GYROADC_MODE_SELECT_1_MB88101A ) +if (childmode ==RCAR_GYROADC_MODE_SELECT_1_MB88101A ) { +of_node_put (child);break ; + } }if (first) {
@@ -435,6 +438,12 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev) }return 0 ; + +err_e_inval: + ret = -EINVAL ; +err_of_node_put: +of_node_put (child); +return ret; }static void rcar_gyroadc_deinit_supplies (struct iio_dev *indio_dev)
Signature · 1 line
2.20.1
Quoted 11 lines · On Sat, 26 Sep 2020 18:19:46 +0200 Tobias Jordan <[email protected]> wrote:
Add missing
of_node_putcalls when exiting thefor_each_child_of_nodeloop inrcar_gyroadc_parse_subdevsearly.Also add goto-exception handling for the error paths in that loop.
Fixes 059c53b32329 ("iio: adc: Add Renesas GyroADC driver")Signed-off-by Tobias Jordan <[email protected]>---
v2:
- added anof_node_putto the non-error "break" at the end
- used gotos for the error cases, doesn't look as bad as I thought
Was marginal, so I'll go with it.
Applied to the fixes-togreg branch of iio.git and marked for stable.
Quoted 79 lines
drivers/iio/adc/rcar-gyroadc.c | 21 +++++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-)drivers/iio/adc/rcar-gyroadc.c +15
-6@@ -357,7 +357,7 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev) num_channels =ARRAY_SIZE (rcar_gyroadc_iio_channels_3);break ;default : -return -EINVAL ; + goto err_e_inval; }/* @@ -374,7 +374,7 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)dev_err (dev,"Failed to get child reg property of ADC \"%pOFn\".\n" , child); -return ret; + goto err_of_node_put; }/* Channel number is too high. */ @@ -382,7 +382,7 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)dev_err (dev,"Only %i channels supported with %pOFn, but reg = <%i>.\n" , num_channels, child, reg); -return -EINVAL ; + goto err_e_inval; } }@@ -391,7 +391,7 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)dev_err (dev,"Channel %i uses different ADC mode than the rest.\n" , reg); -return -EINVAL ; + goto err_e_inval; }/* Channel is valid, grab the regulator. */ @@ -401,7 +401,8 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)if (IS_ERR (vref)) {dev_dbg (dev,"Channel %i 'vref' supply not connected.\n" , reg); -return PTR_ERR (vref); + ret =PTR_ERR (vref); + goto err_of_node_put; } priv->vref[reg] = vref;@@ -425,8 +426,10 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev)* attached to the GyroADC at a time, so if we found it, * we can stop parsing here. */ -if (childmode ==RCAR_GYROADC_MODE_SELECT_1_MB88101A ) +if (childmode ==RCAR_GYROADC_MODE_SELECT_1_MB88101A ) { +of_node_put (child);break ; + } }if (first) {@@ -435,6 +438,12 @@ static int rcar_gyroadc_parse_subdevs(struct iio_dev *indio_dev) }return 0 ; + +err_e_inval: + ret = -EINVAL ; +err_of_node_put: +of_node_put (child); +return ret; }static void rcar_gyroadc_deinit_supplies (struct iio_dev *indio_dev)