#include "dirname.h"
#include "error.h"
#include "relpath.h"
-#include "xalloc.h"
#include "pathmax.h"
#ifndef PATH_MAX
return false;
}
-/* Output the relative representation if possible.
- If BUF is non NULL, write to that buffer rather than to stdout. */
+
bool
relpath (const char *can_fname, const char *can_reldir, char *buf, size_t len)
{
}
else
{
- buf_err |= buffer_or_output (*fname_suffix ? fname_suffix : ".",
- &buf, &len);
+ buf_err |= buffer_or_output (*fname_suffix ? fname_suffix : ".",
+ &buf, &len);
}
if (buf_err)
char *
convert_abs_rel (const char *from, const char *target)
{
- char *realtarget = canonicalize_filename_mode (target, CAN_MISSING);
- char *realfrom = canonicalize_filename_mode (from, CAN_MISSING);
+ char *realtarget = NULL;
+ char *realfrom = NULL;
+ char *relative_from = NULL;
+ char *res = NULL;
+
+ realtarget = canonicalize_filename_mode (target, CAN_MISSING);
+ if (!realtarget)
+ goto end;
+ realfrom = canonicalize_filename_mode (from, CAN_MISSING);
+ if (!realfrom)
+ goto end;
/* Write to a PATH_MAX buffer. */
- char *relative_from = xmalloc (PATH_MAX);
+ relative_from = malloc (PATH_MAX);
+ if (!relative_from)
+ {
+ /* It's easier to set errno to ENOMEM than to rely on the
+ 'malloc-posix' gnulib module. */
+ errno = ENOMEM;
+ goto end;
+ }
/* Get dirname to generate paths relative to. */
realtarget[dir_len (realtarget)] = '\0';
free (relative_from);
relative_from = NULL;
}
-
- free (realtarget);
- free (realfrom);
-
- return relative_from ? relative_from : xstrdup (from);
+ res = relative_from ? relative_from : xstrdup (from);
+
+ end:
+ {
+ int saved_errno = errno;
+ free (realtarget);
+ free (realfrom);
+ errno = saved_errno;
+ }
+ return res;
}
# define _RELPATH_H
/* Output the relative representation if possible.
- If BUF is non NULL, write to that buffer rather than to stdout. */
+ If BUF is non NULL, write to that buffer rather than to stdout.
+ Return true iff success. */
bool
relpath (const char *can_fname, const char *can_reldir, char *buf, size_t len);
-/* Return FROM represented as relative to the dir of TARGET.
- The result is malloced. */
+/* Return FROM represented as relative to the dir of TARGET. The
+ result is malloced, or NULL upon error (described by errno). */
char *
convert_abs_rel (const char *from, const char *target);