예제 #1
0
파일: util.c 프로젝트: GalaxyTab4/workbench
/* Finds out a relative path from first to second, i.e. goes as many ..
 * as needed up in first and then goes down using second */
char *diff_two_paths (const char *first, const char *second) 
{
    char *p, *q, *r, *s, *buf = 0;
    int i, j, prevlen = -1, currlen;
    char *my_first = NULL, *my_second = NULL;
    
    my_first = resolve_symlinks (first);
    if (my_first == NULL)
        return NULL;
    for (j = 0; j < 2; j++) {
	p = my_first;
	if (j) {
	    my_second = resolve_symlinks (second);
	    if (my_second == NULL) {
		g_free (my_first);
	        return buf;
	    }
	}
	q = my_second;
	for (;;) {
	    r = strchr (p, PATH_SEP);
	    s = strchr (q, PATH_SEP);
	    if (!r || !s)
	      break;
	    *r = 0; *s = 0;
	    if (strcmp (p, q)) {
		*r = PATH_SEP; *s = PATH_SEP;
		break;
	    } else {
		*r = PATH_SEP; *s = PATH_SEP;
	    }
	    p = r + 1;
	    q = s + 1;
	}
	p--;
	for (i = 0; (p = strchr (p + 1, PATH_SEP)) != NULL; i++);
	currlen = (i + 1) * 3 + strlen (q) + 1;
	if (j) {
	    if (currlen < prevlen)
	        g_free (buf);
	    else {
		 g_free (my_first);
		 g_free (my_second);
		return buf;
	    }
	}
	p = buf = g_malloc (currlen);
	prevlen = currlen;
	for (; i >= 0; i--, p += 3)
	  strcpy (p, "../");
	strcpy (p, q);
    }
    g_free (my_first);
    g_free (my_second);
    return buf;
}
예제 #2
0
/*
 * find_my_exec -- find an absolute path to a valid executable
 *
 *	argv0 is the name passed on the command line
 *	retpath is the output area (must be of size MAXPGPATH)
 *	Returns 0 if OK, -1 if error.
 *
 * The reason we have to work so hard to find an absolute path is that
 * on some platforms we can't do dynamic loading unless we know the
 * executable's location.  Also, we need a full path not a relative
 * path because we will later change working directory.  Finally, we want
 * a true path not a symlink location, so that we can locate other files
 * that are part of our installation relative to the executable.
 *
 * This function is not thread-safe because it calls validate_exec(),
 * which calls getgrgid().	This function should be used only in
 * non-threaded binaries, not in library routines.
 */
int
find_my_exec(const char *argv0, char *retpath)
{
	char		cwd[MAXPGPATH],
				test_path[MAXPGPATH];
	char	   *path;

	if (!getcwd(cwd, MAXPGPATH))
	{
		log_error(_("could not identify current directory: %s"),
				  strerror(errno));
		return -1;
	}

	/*
	 * If argv0 contains a separator, then PATH wasn't used.
	 */
	if (first_dir_separator(argv0) != NULL)
	{
		if (is_absolute_path(argv0))
			StrNCpy(retpath, argv0, MAXPGPATH);
		else
			join_path_components(retpath, cwd, argv0);
		canonicalize_path(retpath);

		if (validate_exec(retpath) == 0)
			return resolve_symlinks(retpath);

		log_error(_("invalid binary \"%s\""), retpath);
		return -1;
	}

#ifdef WIN32
	/* Win32 checks the current directory first for names without slashes */
	join_path_components(retpath, cwd, argv0);
	if (validate_exec(retpath) == 0)
		return resolve_symlinks(retpath);
#endif

	/*
	 * Since no explicit path was supplied, the user must have been relying on
	 * PATH.  We'll search the same PATH.
	 */
	if ((path = getenv("PATH")) && *path)
	{
		char	   *startp = NULL,
				   *endp = NULL;

		do
		{
			if (!startp)
				startp = path;
			else
				startp = endp + 1;

			endp = first_path_separator(startp);
			if (!endp)
				endp = startp + strlen(startp); /* point to end */

			StrNCpy(test_path, startp, Min(endp - startp + 1, MAXPGPATH));

			if (is_absolute_path(test_path))
				join_path_components(retpath, test_path, argv0);
			else
			{
				join_path_components(retpath, cwd, test_path);
				join_path_components(retpath, retpath, argv0);
			}
			canonicalize_path(retpath);

			switch (validate_exec(retpath))
			{
				case 0: /* found ok */
					return resolve_symlinks(retpath);
				case -1:		/* wasn't even a candidate, keep looking */
					break;
				case -2:		/* found but disqualified */
					log_error(_("could not read binary \"%s\""),
							  retpath);
					break;
			}
		} while (*endp);
	}

	log_error(_("could not find a \"%s\" to execute"), argv0);
	return -1;
}
예제 #3
0
파일: util.c 프로젝트: JBurant/mc
char *
diff_two_paths (const vfs_path_t * vpath1, const vfs_path_t * vpath2)
{
    char *p, *q, *r, *s, *buf = NULL;
    int i, j, prevlen = -1, currlen;
    char *my_first = NULL, *my_second = NULL;

    my_first = resolve_symlinks (vpath1);
    if (my_first == NULL)
        goto ret;

    my_second = resolve_symlinks (vpath2);
    if (my_second == NULL)
        goto ret;

    for (j = 0; j < 2; j++)
    {
        p = my_first;
        q = my_second;
        while (TRUE)
        {
            r = strchr (p, PATH_SEP);
            s = strchr (q, PATH_SEP);
            if (r == NULL || s == NULL)
                break;
            *r = '\0';
            *s = '\0';
            if (strcmp (p, q) != 0)
            {
                *r = PATH_SEP;
                *s = PATH_SEP;
                break;
            }

            *r = PATH_SEP;
            *s = PATH_SEP;

            p = r + 1;
            q = s + 1;
        }
        p--;
        for (i = 0; (p = strchr (p + 1, PATH_SEP)) != NULL; i++)
            ;
        currlen = (i + 1) * 3 + strlen (q) + 1;
        if (j != 0)
        {
            if (currlen < prevlen)
                g_free (buf);
            else
                goto ret;
        }
        p = buf = g_malloc (currlen);
        prevlen = currlen;
        for (; i >= 0; i--, p += 3)
            strcpy (p, "../");
        strcpy (p, q);
    }

  ret:
    g_free (my_first);
    g_free (my_second);
    return buf;
}