Beispiel #1
0
str *_resolve_link(str *path) {
    /**
    Internal helper function.  Takes a path and follows symlinks
    until we either arrive at something that isn't a symlink, or
    encounter a path we've seen before (meaning that there's a loop).
    */
    list<str *> *paths_seen;
    str *dir, *resolved;

    paths_seen = (new list<str *>());

    while(islink(path)) {
        if (paths_seen->__contains__(path)) {
            return 0;
        }
        paths_seen->append(path);
        resolved = __os__::readlink(path);
        if ((!isabs(resolved))) {
            dir = dirname(path);
            path = normpath(join(2, dir, resolved));
        }
        else {
            path = normpath(resolved);
        }
    }
    return path;
}
Beispiel #2
0
static char *
relpath(char *from, char *to)
{
	int up;
	char *p = to, *rel;

	assert(from[0] == '/');
	assert(to[0] == '/');
	normpath(from);
	normpath(to);

	for (; *from == *to && *to; from++, to++) {
		if (*to == '/')
			p = to;
	}

	for (up = -1, from--; from && *from; from = strchr(from + 1, '/'), up++);

	rel = calloc(3 * up + strlen(p), sizeof(char));

	while (up--)
		strcat(rel, "../");
	if (*p)
		strcat(rel, p+1);
	return rel;
}
Beispiel #3
0
static std::string pathcat(std::string path, std::string label)
{
  if (path.empty())
    return normpath(label);
  else if (label.empty())
    return normpath(path);
  else
    return normpath(path+"/"+label);
}
Beispiel #4
0
// Normalize a file path.
//  remove relative path component (..\ and .\),
//  replace slashes by backslashes,
//  convert to long form.
//
// Returns a pointer to a memory allocated block containing the normalized string.
//   The caller is responsible for freeing the block.
//   Returns NULL if the file does not exist or if a memory allocation fails.
//
// Precondition: the file must exist on the file system.
//
// Note:
//   - the case of the root component is preserved
//   - the case of rest is set to the way it is stored on the file system
//
// e.g. suppose the a file "C:\foo\Bar.Pdf" exists on the file system then
//    "c:\foo\bar.pdf" becomes "c:\foo\Bar.Pdf"
//    "C:\foo\BAR.PDF" becomes "C:\foo\Bar.Pdf"
WCHAR *Normalize(const WCHAR *path)
{
    // convert to absolute path, change slashes into backslashes
    DWORD cch = GetFullPathName(path, 0, NULL, NULL);
    if (!cch)
        return str::Dup(path);
    ScopedMem<WCHAR> fullpath(AllocArray<WCHAR>(cch));
    GetFullPathName(path, cch, fullpath, NULL);
    // convert to long form
    cch = GetLongPathName(fullpath, NULL, 0);
    if (!cch)
        return fullpath.StealData();
    ScopedMem<WCHAR> normpath(AllocArray<WCHAR>(cch));
    GetLongPathName(fullpath, normpath, cch);
    if (cch <= MAX_PATH)
        return normpath.StealData();
    // handle overlong paths: first, try to shorten the path
    cch = GetShortPathName(fullpath, NULL, 0);
    if (cch && cch <= MAX_PATH) {
        ScopedMem<WCHAR> shortpath(AllocArray<WCHAR>(cch));
        GetShortPathName(fullpath, shortpath, cch);
        if (str::Len(path::GetBaseName(normpath)) + path::GetBaseName(shortpath) - shortpath < MAX_PATH) {
            // keep the long filename if possible
            *(WCHAR *)path::GetBaseName(shortpath) = '\0';
            return str::Join(shortpath, path::GetBaseName(normpath));
        }
        return shortpath.StealData();
    }
    // else mark the path as overlong
    if (str::StartsWith(normpath.Get(), L"\\\\?\\"))
        return normpath.StealData();
    return str::Join(L"\\\\?\\", normpath);
}
Beispiel #5
0
//prepends cwd, normpathifys, etc
static int prepare_path(const unsigned char *pathin, unsigned char *pathout, int outsize) {
  if (pathin[0] == '/') { //do nothing?
    strncpy(pathout, pathin, outsize);
    return 0;
  }
  
  Process *p = process_get_current(0);
  
  if (!p) {
    strncpy(pathout, pathin, outsize);
    pathout[outsize-1] = 0;
    
    return -1;
  }
  
  pathout[0] = 0;
  strcat(pathout, p->working_path);
  int len = strlen(pathout);
  
  if (len == 0 && pathin[0] != '/') {
    strcat(pathout, "/");
  } else if (len != 0 && pathin[0] == '/' && pathout[len-1] == '/') {
    pathout[len-1] = 0;
  }
  
  strcat(pathout, (unsigned char*)pathin);
  normpath(pathout, outsize);
  
  return 0;
}
Beispiel #6
0
// Normalizes the file path and the converts it into a short form that
// can be used for interaction with non-UNICODE aware applications
WCHAR *ShortPath(const WCHAR *path)
{
    ScopedMem<WCHAR> normpath(Normalize(path));
    DWORD cch = GetShortPathName(normpath, NULL, 0);
    if (!cch)
        return normpath.StealData();
    WCHAR *shortpath = AllocArray<WCHAR>(cch);
    GetShortPathName(normpath, shortpath, cch);
    return shortpath;
}
Beispiel #7
0
gchar *
get_full_path(const gchar * location, const gchar * path)
{
	gchar *dir;

	dir = g_path_get_dirname(location);
	setptr(dir, g_build_filename(dir, path, NULL));
	setptr(dir, normpath(dir));
	return dir;
}
Beispiel #8
0
str *abspath(str *path) {
    /**
    Return an absolute path.
    */

    if ((!isabs(path))) {
        path = join(2, __os__::getcwd(), path);
    }
    return normpath(path);
}
Beispiel #9
0
gchar *
get_relative_path(const gchar * location, const gchar * path)
{
	gchar *dir;
	gchar *pth;
	gchar *ret = NULL;

	gint plen;
	gint dlen;

	if (!g_path_is_absolute(path))
	{
		return g_strdup(path);
	}

	dir = normpath(location);
	pth = normpath(path);

	plen = strlen(pth);
	dlen = strlen(dir);

	if (strstr(pth, dir) == pth)
	{
		if (plen > dlen)
		{
			ret = g_strdup(path + strlen(dir) + 1);
		}
		else if (plen == dlen)
		{
			ret = g_strdup(".");
		}
	}
	g_free(dir);
	g_free(pth);
	return ret;
}
Beispiel #10
0
static const char *
normpath(char *path)
{
	char *seg, *p;

	for (p = path, seg = NULL; *p; p++) {
		if (strncmp(p, "/../", 4) == 0 || strncmp(p, "/..", 4) == 0) {
			memmove(seg ? seg : p, p+3, strlen(p+3) + 1);
			return normpath(path);
		} else if (strncmp(p, "/./", 3) == 0 || strncmp(p, "/.", 3) == 0) {
			memmove(p, p+2, strlen(p+2) + 1);
		} else if (strncmp(p, "//", 2) == 0 || strncmp(p, "/", 2) == 0) {
			memmove(p, p+1, strlen(p+1) + 1);
		}
		if (*p == '/')
			seg = p;
	}
	return path;
}
char *win_realpath(const char *path, char *resolved_path)
{
    return normpath(path, resolved_path);
}
Beispiel #12
0
 std::string abspath(const std::string & path)
 {
     std::string p = path;
     if(!isabs(p)) p = join(getcwd(), p);
     return normpath(p);
 }
Beispiel #13
0
/* Open a zip-compatible archive and extract all files
 * into the specified directory (which is assumed to exist)
 */
BOOL
unzip_archive(SCHEME *scheme, char *dirname, char *data, DWORD size,
              NOTIFYPROC notify)
{
    int n;
    char pathname[MAX_PATH];
    char *new_part;

    /* read the end of central directory record */
    struct eof_cdir *pe = (struct eof_cdir *)&data[size - sizeof
                                                   (struct eof_cdir)];

    int arc_start = size - sizeof (struct eof_cdir) - pe->nBytesCDir -
        pe->ofsCDir;

    /* set position to start of central directory */
    int pos = arc_start + pe->ofsCDir;

    /* make sure this is a zip file */
    if (pe->tag != 0x06054b50)
        return FALSE;

    /* Loop through the central directory, reading all entries */
    for (n = 0; n < pe->nTotalCDir; ++n) {
        int i;
        char *fname;
        char *pcomp;
        char *dst;
        struct cdir *pcdir;
        struct fhdr *pfhdr;

        pcdir = (struct cdir *)&data[pos];
        pfhdr = (struct fhdr *)&data[pcdir->ofs_local_header +
                                     arc_start];

        if (pcdir->tag != 0x02014b50)
            return FALSE;
        if (pfhdr->tag != 0x04034b50)
            return FALSE;
        pos += sizeof(struct cdir);
        fname = (char *)&data[pos]; /* This is not null terminated! */
        pos += pcdir->fname_length + pcdir->extra_length +
            pcdir->comment_length;

        pcomp = &data[pcdir->ofs_local_header
                      + sizeof(struct fhdr)
                      + arc_start
                      + pfhdr->fname_length
                      + pfhdr->extra_length];

        /* dirname is the Python home directory (prefix) */
        strcpy(pathname, dirname);
        if (pathname[strlen(pathname)-1] != '\\')
            strcat(pathname, "\\");
        new_part = &pathname[lstrlen(pathname)];
        /* we must now match the first part of the pathname
         * in the archive to a component in the installation
         * scheme (PURELIB, PLATLIB, HEADERS, SCRIPTS, or DATA)
         * and replace this part by the one in the scheme to use
         */
        for (i = 0; scheme[i].name; ++i) {
            if (0 == strnicmp(scheme[i].name, fname,
                              strlen(scheme[i].name))) {
                char *rest;
                int len;

                /* length of the replaced part */
                int namelen = strlen(scheme[i].name);

                strcat(pathname, scheme[i].prefix);

                rest = fname + namelen;
                len = pfhdr->fname_length - namelen;

                if ((pathname[strlen(pathname)-1] != '\\')
                    && (pathname[strlen(pathname)-1] != '/'))
                    strcat(pathname, "\\");
                /* Now that pathname ends with a separator,
                 * we must make sure rest does not start with
                 * an additional one.
                 */
                if ((rest[0] == '\\') || (rest[0] == '/')) {
                    ++rest;
                    --len;
                }

                strncat(pathname, rest, len);
                goto Done;
            }
        }
        /* no prefix to replace found, go unchanged */
        strncat(pathname, fname, pfhdr->fname_length);
      Done:
        normpath(pathname);
        if (pathname[strlen(pathname)-1] != '\\') {
            /*
             * The local file header (pfhdr) does not always
             * contain the compressed and uncompressed sizes of
             * the data depending on bit 3 of the flags field.  So
             * it seems better to use the data from the central
             * directory (pcdir).
             */
            dst = map_new_file(0, pathname, new_part,
                               pcdir->uncomp_size,
                               pcdir->last_mod_file_date,
                               pcdir->last_mod_file_time, notify);
            if (dst) {
                if (!extract_file(dst, pcomp, pfhdr->method,
                                  pcdir->comp_size,
                                  pcdir->uncomp_size,
                                  notify))
                    return FALSE;
            } /* else ??? */
        }
        if (notify)
            notify(NUM_FILES, new_part, (int)pe->nTotalCDir,
                   (int)n+1);
    }
    return TRUE;
}
Beispiel #14
0
std::string path::expand(const std::string &path) {
    return normpath(expandvars(expanduser(path)));
}