mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2026-08-30 11:03:07 -04:00
pinctrl: generic: free maps on pinctrl_generic_to_map() failure
pinctrl_generic_to_map() parses DT configuration and allocates pinctrl
maps via pinctrl_utils_reserve_map().
If subsequent steps (such as pinctrl_utils_add_map_mux(),
pinctrl_generic_add_group(), pinconf_generic_parse_dt_config(), or
pinctrl_utils_add_map_configs()) return an error, *maps may contain
partially allocated map entries. Returning the error directly without
freeing *maps leaks the allocated mapping memory across all drivers
that rely on pinctrl_generic_to_map().
Fix this by calling pinctrl_utils_free_map() and resetting *maps,
*num_maps, and *num_reserved_maps in the error path of
pinctrl_generic_to_map().
Fixes: aaaf31be04 ("pinctrl: extract pinctrl_generic_to_map() from pinctrl_generic_pins_function_dt_node_to_map()")
Signed-off-by: Surendra Singh Chouhan <kr494167@gmail.com>
Signed-off-by: Linus Walleij <linusw@kernel.org>
This commit is contained in:
committed by
Linus Walleij
parent
f9af1329b9
commit
17007cd700
@@ -42,33 +42,44 @@ int pinctrl_generic_to_map(struct pinctrl_dev *pctldev, struct device_node *pare
|
||||
ret = pinctrl_utils_add_map_mux(pctldev, maps, num_reserved_maps, num_maps, group_name,
|
||||
parent->name);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
goto err_free_map;
|
||||
|
||||
ret = pinctrl_generic_add_group(pctldev, group_name, pins, npins, data);
|
||||
if (ret < 0)
|
||||
return dev_err_probe(dev, ret, "failed to add group %s: %d\n",
|
||||
if (ret < 0) {
|
||||
dev_err_probe(dev, ret, "failed to add group %s: %d\n",
|
||||
group_name, ret);
|
||||
goto err_free_map;
|
||||
}
|
||||
|
||||
ret = pinconf_generic_parse_dt_config(np, pctldev, &configs, &num_configs);
|
||||
if (ret)
|
||||
return dev_err_probe(dev, ret, "failed to parse pin config of group %s\n",
|
||||
if (ret) {
|
||||
dev_err_probe(dev, ret, "failed to parse pin config of group %s\n",
|
||||
group_name);
|
||||
goto err_free_map;
|
||||
}
|
||||
|
||||
if (num_configs == 0)
|
||||
return 0;
|
||||
|
||||
ret = pinctrl_utils_reserve_map(pctldev, maps, num_reserved_maps, num_maps, reserve);
|
||||
if (ret)
|
||||
return ret;
|
||||
goto err_free_map;
|
||||
|
||||
ret = pinctrl_utils_add_map_configs(pctldev, maps, num_reserved_maps, num_maps, group_name,
|
||||
configs,
|
||||
num_configs, PIN_MAP_TYPE_CONFIGS_GROUP);
|
||||
kfree(configs);
|
||||
if (ret)
|
||||
return ret;
|
||||
goto err_free_map;
|
||||
|
||||
return 0;
|
||||
|
||||
err_free_map:
|
||||
pinctrl_utils_free_map(pctldev, *maps, *num_maps);
|
||||
*maps = NULL;
|
||||
*num_maps = 0;
|
||||
*num_reserved_maps = 0;
|
||||
return ret;
|
||||
};
|
||||
EXPORT_SYMBOL_GPL(pinctrl_generic_to_map);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user