Commit f7aa8a53 authored by Rémi Denis-Courmont's avatar Rémi Denis-Courmont

make_path: make a local file path from an URI

parent 34a55d15
......@@ -49,6 +49,7 @@ VLC_EXPORT( char *, decode_URI_duplicate, ( const char *psz ) );
VLC_EXPORT( char *, decode_URI, ( char *psz ) );
VLC_EXPORT( char *, encode_URI_component, ( const char *psz ) );
VLC_EXPORT( char *, make_URI, ( const char *path ) );
VLC_EXPORT( char *, make_path, ( const char *url ) );
/*****************************************************************************
* vlc_UrlParse:
......
......@@ -227,6 +227,7 @@ libvlc_InternalWait
libvlc_Quit
LocaleFree
make_URI
make_path
mdate
module_config_free
module_config_get
......
......@@ -1146,3 +1146,93 @@ char *make_URI (const char *path)
return buf;
}
}
/**
* Tries to convert an URI to a local (UTF-8-encoded) file path.
* @param url URI to convert
* @return NULL on error, a nul-terminated string otherwise
* (use free() to release it)
*/
char *make_path (const char *url)
{
char *ret = NULL;
char *end;
char *path = strstr (url, "://");
if (path == NULL)
return NULL; /* unsupported scheme or invalid syntax */
end = memchr (url, '/', path - url);
size_t schemelen = ((end != NULL) ? end : path) - url;
path += 3; /* skip "://" */
/* Remove HTML anchor if present */
end = strchr (path, '#');
if (end)
path = strndup (path, end - path);
else
path = strdup (path);
if (unlikely(path == NULL))
return NULL; /* boom! */
/* Decode path */
decode_URI (path);
if (schemelen == 4 && !strncasecmp (url, "file", 4))
{
#if (DIR_SEP_CHAR != '/')
for (char *p = strchr (path, '/'); p; p = strchr (p, '/'))
*p == DIR_SEP_CHAR;
#endif
if (*path == DIR_SEP_CHAR)
return path;
/* Local path disguised as a remote one (MacOS X) */
if (!strncasecmp (path, "localhost"DIR_SEP, 10))
{
memmove (path, path + 9, strlen (path + 9) + 1);
return path;
}
#ifdef WIN32
if (*path && asprintf (&ret, "\\\\%s", path) == -1)
ret = NULL;
#endif
/* non-local path :-( */
}
else
if (schemelen == 2 && !strncasecmp (url, "fd", 2))
{
int fd = strtol (path, &end, 0);
if (*end)
goto out;
#ifndef WIN32
switch (fd)
{
case 0:
ret = strdup ("/dev/stdin");
break;
case 1:
ret = strdup ("/dev/stdout");
break;
case 2:
ret = strdup ("/dev/strerr");
break;
default:
if (asprintf (&ret, "/dev/fd/%d", fd) == -1)
ret = NULL;
}
#else
if (fd < 2)
ret = strdup ("CON");
else
ret = NULL;
#endif
}
out:
free (path);
return ret; /* unknown scheme */
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment