[lttng-dev] [PATCH lttng-tools 1/2] Fix: d_type validity is not guaranteed on all nfs versions
Jonathan Rajotte Julien
Jonathan.rajotte-julien at efficios.com
Fri Mar 18 21:02:32 UTC 2016
Those two patches can also be backported to stable-2.7 with the
condition that commit
c4b765f0d3892d57bb7e8828c324d304e9c4d5e9 [1] is also backported since it
fix the
d_type problem in src/common/utils.c.
Thanks
[1]
commit c4b765f0d3892d57bb7e8828c324d304e9c4d5e9
Author: Michael Jeanson <mjeanson at efficios.com>
Date: Wed Oct 14 16:02:45 2015 -0400
Port: Replace dirent->d_type by stat
dirent->d_type is Linux specific while 'stat' is part of POSIX
Signed-off-by: Michael Jeanson <mjeanson at efficios.com>
Signed-off-by: J<C3><A9>r<C3><A9>mie Galarneau
<jeremie.galarneau at efficios.com>
On 2016-03-18 01:20 PM, Jonathan Rajotte wrote:
> When using lttng-crash on files mounted on a nfs mount the d_type from the dirent
> struct is not necessarily set and result in DT_UNKNOWN d_type.
>
> stat() provide the valid information on an nfs mount.
>
> Signed-off-by: Jonathan Rajotte <jonathan.rajotte-julien at efficios.com>
> ---
> src/bin/lttng-crash/lttng-crash.c | 80 +++++++++++++++++++++++++++++----------
> 1 file changed, 61 insertions(+), 19 deletions(-)
>
> diff --git a/src/bin/lttng-crash/lttng-crash.c b/src/bin/lttng-crash/lttng-crash.c
> index 653e4d0..8eddbd9 100644
> --- a/src/bin/lttng-crash/lttng-crash.c
> +++ b/src/bin/lttng-crash/lttng-crash.c
> @@ -976,6 +976,7 @@ int extract_trace_recursive(const char *output_path,
> DIR *dir;
> int dir_fd, ret = 0, closeret;
> struct dirent *entry;
> + size_t path_len;
> int has_warning = 0;
>
> /* Open directory */
> @@ -984,6 +985,9 @@ int extract_trace_recursive(const char *output_path,
> PERROR("Cannot open '%s' path", input_path);
> return -1;
> }
> +
> + path_len = strlen(input_path);
> +
> dir_fd = dirfd(dir);
> if (dir_fd < 0) {
> PERROR("dirfd");
> @@ -991,13 +995,34 @@ int extract_trace_recursive(const char *output_path,
> }
>
> while ((entry = readdir(dir))) {
> + struct stat st;
> + size_t name_len;
> + char filename[PATH_MAX];
> +
> if (!strcmp(entry->d_name, ".")
> || !strcmp(entry->d_name, "..")) {
> continue;
> }
> - switch (entry->d_type) {
> - case DT_DIR:
> - {
> +
> + name_len = strlen(entry->d_name);
> + if (path_len + name_len + 2 > sizeof(filename)) {
> + ERR("Failed to remove file: path name too long (%s/%s)",
> + input_path, entry->d_name);
> + continue;
> + }
> +
> + if (snprintf(filename, sizeof(filename), "%s/%s",
> + input_path, entry->d_name) < 0) {
> + ERR("Failed to format path.");
> + continue;
> + }
> +
> + if (stat(filename, &st)) {
> + PERROR("stat");
> + continue;
> + }
> +
> + if (S_ISDIR(st.st_mode)) {
> char output_subpath[PATH_MAX];
> char input_subpath[PATH_MAX];
>
> @@ -1029,22 +1054,17 @@ int extract_trace_recursive(const char *output_path,
> if (ret) {
> has_warning = 1;
> }
> - break;
> - }
> - case DT_REG:
> - case DT_LNK:
> + } else if (S_ISREG(st.st_mode) || S_ISLNK(st.st_mode)) {
> if (!strcmp(entry->d_name, "metadata")) {
> ret = extract_one_trace(output_path,
> input_path);
> if (ret) {
> WARN("Error extracting trace '%s', continuing anyway.",
> input_path);
> - has_warning = 1;
> + has_warning = 2;
> }
> }
> - /* Ignore other files */
> - break;
> - default:
> + } else {
> has_warning = 1;
> goto end;
> }
> @@ -1062,6 +1082,7 @@ int delete_dir_recursive(const char *path)
> {
> DIR *dir;
> int dir_fd, ret = 0, closeret;
> + size_t path_len;
> struct dirent *entry;
>
> /* Open trace directory */
> @@ -1071,6 +1092,9 @@ int delete_dir_recursive(const char *path)
> ret = -errno;
> goto end;
> }
> +
> + path_len = strlen(path);
> +
> dir_fd = dirfd(dir);
> if (dir_fd < 0) {
> PERROR("dirfd");
> @@ -1079,13 +1103,34 @@ int delete_dir_recursive(const char *path)
> }
>
> while ((entry = readdir(dir))) {
> + struct stat st;
> + size_t name_len;
> + char filename[PATH_MAX];
> +
> if (!strcmp(entry->d_name, ".")
> || !strcmp(entry->d_name, "..")) {
> continue;
> }
> - switch (entry->d_type) {
> - case DT_DIR:
> - {
> +
> + name_len = strlen(entry->d_name);
> + if (path_len + name_len + 2 > sizeof(filename)) {
> + ERR("Failed to remove file: path name too long (%s/%s)",
> + path, entry->d_name);
> + continue;
> + }
> +
> + if (snprintf(filename, sizeof(filename), "%s/%s",
> + path, entry->d_name) < 0) {
> + ERR("Failed to format path.");
> + continue;
> + }
> +
> + if (stat(filename, &st)) {
> + PERROR("stat");
> + continue;
> + }
> +
> + if (S_ISDIR(st.st_mode)) {
> char *subpath = zmalloc(PATH_MAX);
>
> if (!subpath) {
> @@ -1106,16 +1151,13 @@ int delete_dir_recursive(const char *path)
> /* Error occured, abort traversal. */
> goto end;
> }
> - break;
> - }
> - case DT_REG:
> + } else if (S_ISREG(st.st_mode)) {
> ret = unlinkat(dir_fd, entry->d_name, 0);
> if (ret) {
> PERROR("Unlinking '%s'", entry->d_name);
> goto end;
> }
> - break;
> - default:
> + } else {
> ret = -EINVAL;
> goto end;
> }
--
Jonathan R. Julien
Efficios
More information about the lttng-dev
mailing list