summaryrefslogtreecommitdiffstats
path: root/lib/libalpm/hook.c
diff options
context:
space:
mode:
authorAndrew Gregory <andrew.gregory.8@gmail.com>2015-10-28 05:04:05 +0100
committerAllan McRae <allan@archlinux.org>2015-10-28 05:22:09 +0100
commitdcc1b22cb33a7a9d9477ffc84f833317860bf751 (patch)
treec74a92c5da3506cf062d6f979c79361fd3625531 /lib/libalpm/hook.c
parent1142a32c7f6f8ab82528581277b7c7cac6b2d1ae (diff)
downloadpacman-dcc1b22cb33a7a9d9477ffc84f833317860bf751.tar.gz
pacman-dcc1b22cb33a7a9d9477ffc84f833317860bf751.tar.xz
_alpm_hook_run: check path length before copying
If a hook path equals or exceeds PATH_MAX characters the path will be left unterminated. Pre-calculating the path length also allows us to use the more efficient memcpy over strncpy. Signed-off-by: Andrew Gregory <andrew.gregory.8@gmail.com> Signed-off-by: Allan McRae <allan@archlinux.org>
Diffstat (limited to 'lib/libalpm/hook.c')
-rw-r--r--lib/libalpm/hook.c27
1 files changed, 19 insertions, 8 deletions
diff --git a/lib/libalpm/hook.c b/lib/libalpm/hook.c
index 463b76a2..0191a21e 100644
--- a/lib/libalpm/hook.c
+++ b/lib/libalpm/hook.c
@@ -410,30 +410,41 @@ int _alpm_hook_run(alpm_handle_t *handle, enum _alpm_hook_when_t when)
struct dirent entry, *result;
DIR *d;
- if(!(d = opendir(i->data))) {
+ if((dirlen = strlen(i->data)) >= PATH_MAX) {
+ _alpm_log(handle, ALPM_LOG_ERROR, _("could not open directory: %s: %s\n"),
+ (char *)i->data, strerror(ENAMETOOLONG));
+ ret = -1;
+ continue;
+ }
+ memcpy(path, i->data, dirlen + 1);
+
+ if(!(d = opendir(path))) {
if(errno == ENOENT) {
continue;
} else {
- _alpm_log(handle, ALPM_LOG_ERROR, _("could not open directory: %s: %s\n"),
- (char *)i->data, strerror(errno));
+ _alpm_log(handle, ALPM_LOG_ERROR,
+ _("could not open directory: %s: %s\n"), path, strerror(errno));
ret = -1;
continue;
}
}
- strncpy(path, i->data, PATH_MAX);
- dirlen = strlen(i->data);
-
while((err = readdir_r(d, &entry, &result)) == 0 && result) {
struct _alpm_hook_cb_ctx ctx = { handle, NULL };
struct stat buf;
- size_t name_len = strlen(entry.d_name);
+ size_t name_len;
if(strcmp(entry.d_name, ".") == 0 || strcmp(entry.d_name, "..") == 0) {
continue;
}
- strncpy(path + dirlen, entry.d_name, PATH_MAX - dirlen);
+ if((name_len = strlen(entry.d_name)) >= PATH_MAX - dirlen) {
+ _alpm_log(handle, ALPM_LOG_ERROR, _("could not open file: %s%s: %s\n"),
+ path, entry.d_name, strerror(ENAMETOOLONG));
+ ret = -1;
+ continue;
+ }
+ memcpy(path + dirlen, entry.d_name, name_len + 1);
if(name_len < suflen
|| strcmp(entry.d_name + name_len - suflen, suffix) != 0) {