提交 ba1d379c 编写于 作者: L Laine Stump 提交者: Daniel Veillard

Cleanup of large buffer on stack in virFileMakePath

virFileMakePath is a recursive function that was creates a buffer
PATH_MAX bytes long for each recursion (one recursion for each element
in the path). This changes it to have no buffers on the stack, and to
allocate just one buffer total, no matter how many elements are in the
path. Because the modified algorithm requires a char* to be passed in
rather than const char *, it is now 2 functions - a toplevel API
function that remains identical in function, and a 2nd helper function
called for the recursions, which 1) doesn't allocate anything, and 2)
takes a char* arg, so it can modify the contents.
* src/util/util.c: rewrite virFileMakePath
上级 854111f9
...@@ -1443,34 +1443,68 @@ int virDirCreate(const char *path, mode_t mode, ...@@ -1443,34 +1443,68 @@ int virDirCreate(const char *path, mode_t mode,
} }
#endif #endif
int virFileMakePath(const char *path) static int virFileMakePathHelper(char *path) {
{
struct stat st; struct stat st;
char parent[PATH_MAX]; char *p = NULL;
char *p;
int err; int err;
if (stat(path, &st) >= 0) if (stat(path, &st) >= 0)
return 0; return 0;
if (virStrcpyStatic(parent, path) == NULL) if ((p = strrchr(path, '/')) == NULL)
return EINVAL;
if (!(p = strrchr(parent, '/')))
return EINVAL; return EINVAL;
if (p != parent) { if (p != path) {
*p = '\0'; *p = '\0';
if ((err = virFileMakePath(parent))) err = virFileMakePathHelper(path);
*p = '/';
if (err != 0)
return err; return err;
} }
if (mkdir(path, 0777) < 0 && errno != EEXIST) if (mkdir(path, 0777) < 0 && errno != EEXIST) {
return errno; return errno;
}
return 0; return 0;
} }
int virFileMakePath(const char *path)
{
struct stat st;
char *parent = NULL;
char *p;
int err = 0;
if (stat(path, &st) >= 0)
goto cleanup;
if ((parent = strdup(path)) == NULL) {
err = ENOMEM;
goto cleanup;
}
if ((p = strrchr(parent, '/')) == NULL) {
err = EINVAL;
goto cleanup;
}
if (p != parent) {
*p = '\0';
if ((err = virFileMakePathHelper(parent)) != 0) {
goto cleanup;
}
}
if (mkdir(path, 0777) < 0 && errno != EEXIST) {
err = errno;
goto cleanup;
}
cleanup:
VIR_FREE(parent);
return err;
}
/* Build up a fully qualfiied path for a config file to be /* Build up a fully qualfiied path for a config file to be
* associated with a persistent guest or network */ * associated with a persistent guest or network */
int virFileBuildPath(const char *dir, int virFileBuildPath(const char *dir,
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册