mirror of
https://gitlab.gnome.org/GNOME/glib.git
synced 2024-11-10 03:16:17 +01:00
New functions to convert between local pahtnames and file: uris.
2001-08-26 Alex Larsson <alexl@redhat.com> * glib/gconvert.[ch] (g_filename_from_uri, g_filename_to_uri): New functions to convert between local pahtnames and file: uris. * tests/Makefile.am: * tests/uri-test.c: Tests for the new functions.
This commit is contained in:
parent
a7a76cfac7
commit
4e11203c54
10
ChangeLog
10
ChangeLog
@ -1,3 +1,13 @@
|
||||
2001-08-26 Alex Larsson <alexl@redhat.com>
|
||||
|
||||
* glib/gconvert.[ch] (g_filename_from_uri,
|
||||
g_filename_to_uri): New functions to convert
|
||||
between local pahtnames and file: uris.
|
||||
|
||||
* tests/Makefile.am:
|
||||
* tests/uri-test.c:
|
||||
Tests for the new functions.
|
||||
|
||||
2001-08-25 Alexander Larsson <alla@lysator.liu.se>
|
||||
|
||||
* glib/gstrfuncs.[ch]:
|
||||
|
@ -1,3 +1,13 @@
|
||||
2001-08-26 Alex Larsson <alexl@redhat.com>
|
||||
|
||||
* glib/gconvert.[ch] (g_filename_from_uri,
|
||||
g_filename_to_uri): New functions to convert
|
||||
between local pahtnames and file: uris.
|
||||
|
||||
* tests/Makefile.am:
|
||||
* tests/uri-test.c:
|
||||
Tests for the new functions.
|
||||
|
||||
2001-08-25 Alexander Larsson <alla@lysator.liu.se>
|
||||
|
||||
* glib/gstrfuncs.[ch]:
|
||||
|
@ -1,3 +1,13 @@
|
||||
2001-08-26 Alex Larsson <alexl@redhat.com>
|
||||
|
||||
* glib/gconvert.[ch] (g_filename_from_uri,
|
||||
g_filename_to_uri): New functions to convert
|
||||
between local pahtnames and file: uris.
|
||||
|
||||
* tests/Makefile.am:
|
||||
* tests/uri-test.c:
|
||||
Tests for the new functions.
|
||||
|
||||
2001-08-25 Alexander Larsson <alla@lysator.liu.se>
|
||||
|
||||
* glib/gstrfuncs.[ch]:
|
||||
|
@ -1,3 +1,13 @@
|
||||
2001-08-26 Alex Larsson <alexl@redhat.com>
|
||||
|
||||
* glib/gconvert.[ch] (g_filename_from_uri,
|
||||
g_filename_to_uri): New functions to convert
|
||||
between local pahtnames and file: uris.
|
||||
|
||||
* tests/Makefile.am:
|
||||
* tests/uri-test.c:
|
||||
Tests for the new functions.
|
||||
|
||||
2001-08-25 Alexander Larsson <alla@lysator.liu.se>
|
||||
|
||||
* glib/gstrfuncs.[ch]:
|
||||
|
@ -1,3 +1,13 @@
|
||||
2001-08-26 Alex Larsson <alexl@redhat.com>
|
||||
|
||||
* glib/gconvert.[ch] (g_filename_from_uri,
|
||||
g_filename_to_uri): New functions to convert
|
||||
between local pahtnames and file: uris.
|
||||
|
||||
* tests/Makefile.am:
|
||||
* tests/uri-test.c:
|
||||
Tests for the new functions.
|
||||
|
||||
2001-08-25 Alexander Larsson <alla@lysator.liu.se>
|
||||
|
||||
* glib/gstrfuncs.[ch]:
|
||||
|
@ -1,3 +1,13 @@
|
||||
2001-08-26 Alex Larsson <alexl@redhat.com>
|
||||
|
||||
* glib/gconvert.[ch] (g_filename_from_uri,
|
||||
g_filename_to_uri): New functions to convert
|
||||
between local pahtnames and file: uris.
|
||||
|
||||
* tests/Makefile.am:
|
||||
* tests/uri-test.c:
|
||||
Tests for the new functions.
|
||||
|
||||
2001-08-25 Alexander Larsson <alla@lysator.liu.se>
|
||||
|
||||
* glib/gstrfuncs.[ch]:
|
||||
|
@ -1,3 +1,13 @@
|
||||
2001-08-26 Alex Larsson <alexl@redhat.com>
|
||||
|
||||
* glib/gconvert.[ch] (g_filename_from_uri,
|
||||
g_filename_to_uri): New functions to convert
|
||||
between local pahtnames and file: uris.
|
||||
|
||||
* tests/Makefile.am:
|
||||
* tests/uri-test.c:
|
||||
Tests for the new functions.
|
||||
|
||||
2001-08-25 Alexander Larsson <alla@lysator.liu.se>
|
||||
|
||||
* glib/gstrfuncs.[ch]:
|
||||
|
@ -1,3 +1,13 @@
|
||||
2001-08-26 Alex Larsson <alexl@redhat.com>
|
||||
|
||||
* glib/gconvert.[ch] (g_filename_from_uri,
|
||||
g_filename_to_uri): New functions to convert
|
||||
between local pahtnames and file: uris.
|
||||
|
||||
* tests/Makefile.am:
|
||||
* tests/uri-test.c:
|
||||
Tests for the new functions.
|
||||
|
||||
2001-08-25 Alexander Larsson <alla@lysator.liu.se>
|
||||
|
||||
* glib/gstrfuncs.[ch]:
|
||||
|
371
glib/gconvert.c
371
glib/gconvert.c
@ -563,11 +563,24 @@ static gchar *
|
||||
strdup_len (const gchar *string,
|
||||
gssize len,
|
||||
gsize *bytes_written,
|
||||
gsize *bytes_read)
|
||||
gsize *bytes_read,
|
||||
GError **error)
|
||||
|
||||
{
|
||||
gsize real_len;
|
||||
|
||||
if (!g_utf8_validate (string, -1, NULL))
|
||||
{
|
||||
if (bytes_read)
|
||||
*bytes_read = 0;
|
||||
if (bytes_written)
|
||||
*bytes_written = 0;
|
||||
|
||||
g_set_error (error, G_CONVERT_ERROR, G_CONVERT_ERROR_ILLEGAL_SEQUENCE,
|
||||
_("Invalid byte sequence in conversion input"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (len < 0)
|
||||
real_len = strlen (string);
|
||||
else
|
||||
@ -718,7 +731,7 @@ g_locale_to_utf8 (const gchar *opsysstring,
|
||||
const char *charset;
|
||||
|
||||
if (g_get_charset (&charset))
|
||||
return strdup_len (opsysstring, len, bytes_read, bytes_written);
|
||||
return strdup_len (opsysstring, len, bytes_read, bytes_written, error);
|
||||
else
|
||||
return g_convert (opsysstring, len,
|
||||
"UTF-8", charset, bytes_read, bytes_written, error);
|
||||
@ -864,7 +877,7 @@ g_locale_from_utf8 (const gchar *utf8string,
|
||||
const gchar *charset;
|
||||
|
||||
if (g_get_charset (&charset))
|
||||
return strdup_len (utf8string, len, bytes_read, bytes_written);
|
||||
return strdup_len (utf8string, len, bytes_read, bytes_written, error);
|
||||
else
|
||||
return g_convert (utf8string, len,
|
||||
charset, "UTF-8", bytes_read, bytes_written, error);
|
||||
@ -907,12 +920,13 @@ g_filename_to_utf8 (const gchar *opsysstring,
|
||||
bytes_read, bytes_written,
|
||||
error);
|
||||
#else /* !G_PLATFORM_WIN32 */
|
||||
|
||||
if (getenv ("G_BROKEN_FILENAMES"))
|
||||
return g_locale_to_utf8 (opsysstring, len,
|
||||
bytes_read, bytes_written,
|
||||
error);
|
||||
else
|
||||
return strdup_len (opsysstring, len, bytes_read, bytes_written);
|
||||
return strdup_len (opsysstring, len, bytes_read, bytes_written, error);
|
||||
#endif /* !G_PLATFORM_WIN32 */
|
||||
}
|
||||
|
||||
@ -955,6 +969,353 @@ g_filename_from_utf8 (const gchar *utf8string,
|
||||
bytes_read, bytes_written,
|
||||
error);
|
||||
else
|
||||
return strdup_len (utf8string, len, bytes_read, bytes_written);
|
||||
return strdup_len (utf8string, len, bytes_read, bytes_written, error);
|
||||
#endif /* !G_PLATFORM_WIN32 */
|
||||
}
|
||||
|
||||
/* Test of haystack has the needle prefix, comparing case
|
||||
* insensitive. haystack may be UTF-8, but needle must
|
||||
* contain only ascii. */
|
||||
static gboolean
|
||||
has_case_prefix (const gchar *haystack, const gchar *needle)
|
||||
{
|
||||
const gchar *h, *n;
|
||||
|
||||
/* Eat one character at a time. */
|
||||
h = haystack;
|
||||
n = needle;
|
||||
|
||||
while (*n && *h &&
|
||||
g_ascii_tolower (*n) == g_ascii_tolower (*h))
|
||||
{
|
||||
n++;
|
||||
h++;
|
||||
}
|
||||
|
||||
return *n == '\0';
|
||||
}
|
||||
|
||||
typedef enum {
|
||||
UNSAFE_ALL = 0x1, /* Escape all unsafe characters */
|
||||
UNSAFE_ALLOW_PLUS = 0x2, /* Allows '+' */
|
||||
UNSAFE_PATH = 0x4, /* Allows '/' and '?' and '&' and '=' */
|
||||
UNSAFE_DOS_PATH = 0x8, /* Allows '/' and '?' and '&' and '=' and ':' */
|
||||
UNSAFE_HOST = 0x10, /* Allows '/' and ':' and '@' */
|
||||
UNSAFE_SLASHES = 0x20 /* Allows all characters except for '/' and '%' */
|
||||
} UnsafeCharacterSet;
|
||||
|
||||
static const guchar acceptable[96] = {
|
||||
/* X0 X1 X2 X3 X4 X5 X6 X7 X8 X9 XA XB XC XD XE XF */
|
||||
0x00,0x3F,0x20,0x20,0x20,0x00,0x2C,0x3F,0x3F,0x3F,0x3F,0x22,0x20,0x3F,0x3F,0x1C, /* 2X !"#$%&'()*+,-./ */
|
||||
0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x38,0x20,0x20,0x2C,0x20,0x2C, /* 3X 0123456789:;<=>? */
|
||||
0x30,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F, /* 4X @ABCDEFGHIJKLMNO */
|
||||
0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x20,0x20,0x20,0x20,0x3F, /* 5X PQRSTUVWXYZ[\]^_ */
|
||||
0x20,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F, /* 6X `abcdefghijklmno */
|
||||
0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x3F,0x20,0x20,0x20,0x3F,0x20 /* 7X pqrstuvwxyz{|}~DEL */
|
||||
};
|
||||
|
||||
static const gchar hex[16] = "0123456789ABCDEF";
|
||||
|
||||
/* Note: This escape function works on file: URIs, but if you want to
|
||||
* escape something else, please read RFC-2396 */
|
||||
static gchar *
|
||||
g_escape_uri_string (const gchar *string,
|
||||
UnsafeCharacterSet mask)
|
||||
{
|
||||
#define ACCEPTABLE(a) ((a)>=32 && (a)<128 && (acceptable[(a)-32] & use_mask))
|
||||
|
||||
const gchar *p;
|
||||
gchar *q;
|
||||
gchar *result;
|
||||
int c;
|
||||
gint unacceptable;
|
||||
UnsafeCharacterSet use_mask;
|
||||
|
||||
g_return_val_if_fail (mask == UNSAFE_ALL
|
||||
|| mask == UNSAFE_ALLOW_PLUS
|
||||
|| mask == UNSAFE_PATH
|
||||
|| mask == UNSAFE_DOS_PATH
|
||||
|| mask == UNSAFE_HOST
|
||||
|| mask == UNSAFE_SLASHES, NULL);
|
||||
|
||||
unacceptable = 0;
|
||||
use_mask = mask;
|
||||
for (p = string; *p != '\0'; p++)
|
||||
{
|
||||
c = *p;
|
||||
if (!ACCEPTABLE (c))
|
||||
unacceptable++;
|
||||
}
|
||||
|
||||
result = g_malloc (p - string + unacceptable * 2 + 1);
|
||||
|
||||
use_mask = mask;
|
||||
for (q = result, p = string; *p != '\0'; p++)
|
||||
{
|
||||
c = (unsigned char)*p;
|
||||
|
||||
if (!ACCEPTABLE (c))
|
||||
{
|
||||
*q++ = '%'; /* means hex coming */
|
||||
*q++ = hex[c >> 4];
|
||||
*q++ = hex[c & 15];
|
||||
}
|
||||
else
|
||||
*q++ = *p;
|
||||
}
|
||||
|
||||
*q = '\0';
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
static gchar *
|
||||
g_escape_file_uri (const gchar *hostname,
|
||||
const gchar *pathname)
|
||||
{
|
||||
char *escaped_hostname = NULL;
|
||||
char *escaped_path;
|
||||
char *res;
|
||||
|
||||
if (hostname && *hostname != '\0')
|
||||
{
|
||||
escaped_hostname = g_escape_uri_string (hostname, UNSAFE_HOST);
|
||||
}
|
||||
|
||||
escaped_path = g_escape_uri_string (pathname, UNSAFE_DOS_PATH);
|
||||
|
||||
res = g_strconcat ("file://",
|
||||
(escaped_hostname) ? escaped_hostname : "",
|
||||
(*escaped_path != '/') ? "/" : "",
|
||||
escaped_path,
|
||||
NULL);
|
||||
|
||||
g_free (escaped_hostname);
|
||||
g_free (escaped_path);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
static int
|
||||
unescape_character (const char *scanner)
|
||||
{
|
||||
int first_digit;
|
||||
int second_digit;
|
||||
|
||||
first_digit = g_ascii_xdigit_value (*scanner++);
|
||||
|
||||
if (first_digit < 0)
|
||||
return -1;
|
||||
|
||||
second_digit = g_ascii_xdigit_value (*scanner++);
|
||||
if (second_digit < 0)
|
||||
return -1;
|
||||
|
||||
return (first_digit << 4) | second_digit;
|
||||
}
|
||||
|
||||
static gchar *
|
||||
g_unescape_uri_string (const gchar *escaped,
|
||||
const gchar *illegal_characters,
|
||||
int len)
|
||||
{
|
||||
const gchar *in, *in_end;
|
||||
gchar *out, *result;
|
||||
int character;
|
||||
|
||||
if (escaped == NULL)
|
||||
return NULL;
|
||||
|
||||
if (len < 0)
|
||||
len = strlen (escaped);
|
||||
|
||||
result = g_malloc (len + 1);
|
||||
|
||||
out = result;
|
||||
for (in = escaped, in_end = escaped + len; in < in_end && *in != '\0'; in++)
|
||||
{
|
||||
character = *in;
|
||||
if (character == '%')
|
||||
{
|
||||
character = unescape_character (in + 1);
|
||||
|
||||
/* Check for an illegal character. We consider '\0' illegal here. */
|
||||
if (character == 0
|
||||
|| (illegal_characters != NULL
|
||||
&& strchr (illegal_characters, (char)character) != NULL))
|
||||
{
|
||||
g_free (result);
|
||||
return NULL;
|
||||
}
|
||||
in += 2;
|
||||
}
|
||||
*out++ = character;
|
||||
}
|
||||
|
||||
*out = '\0';
|
||||
|
||||
g_assert (out - result <= strlen (escaped));
|
||||
|
||||
if (!g_utf8_validate (result, -1, NULL))
|
||||
{
|
||||
g_free (result);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* g_filename_from_uri:
|
||||
* @uri: a uri describing a filename (escaped, encoded in UTF-8)
|
||||
* @hostname: Location to store hostname for the URI, or %NULL.
|
||||
* If there is no hostname in the URI, %NULL will be
|
||||
* stored in this location.
|
||||
* @error: location to store the error occuring, or %NULL to ignore
|
||||
* errors. Any of the errors in #GConvertError may occur.
|
||||
*
|
||||
* Converts an escaped UTF-8 encoded URI to a local filename in the
|
||||
* encoding used for filenames.
|
||||
*
|
||||
* Return value: a newly allocated string holding the resulting
|
||||
* filename, or %NULL on an error.
|
||||
**/
|
||||
gchar *
|
||||
g_filename_from_uri (const char *uri,
|
||||
char **hostname,
|
||||
GError **error)
|
||||
{
|
||||
const char *path_part;
|
||||
const char *host_part;
|
||||
char *unescaped_hostname;
|
||||
char *result;
|
||||
char *filename;
|
||||
int offs;
|
||||
|
||||
if (hostname)
|
||||
*hostname = NULL;
|
||||
|
||||
if (!has_case_prefix (uri, "file:/"))
|
||||
{
|
||||
g_set_error (error, G_CONVERT_ERROR, G_CONVERT_ERROR_NOT_LOCAL_FILE,
|
||||
_("The URI `%s' does not specify a local file"),
|
||||
uri);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
path_part = uri + strlen ("file:");
|
||||
|
||||
if (strchr (path_part, '#') != NULL)
|
||||
{
|
||||
g_set_error (error, G_CONVERT_ERROR, G_CONVERT_ERROR_INVALID_URI,
|
||||
_("The local file URI `%s' may not include a `#'"),
|
||||
uri);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (has_case_prefix (path_part, "///"))
|
||||
path_part += 2;
|
||||
else if (has_case_prefix (path_part, "//"))
|
||||
{
|
||||
path_part += 2;
|
||||
host_part = path_part;
|
||||
|
||||
path_part = strchr (path_part, '/');
|
||||
|
||||
if (path_part == NULL)
|
||||
{
|
||||
g_set_error (error, G_CONVERT_ERROR, G_CONVERT_ERROR_INVALID_URI,
|
||||
_("The URI `%s' is invalid"),
|
||||
uri);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
unescaped_hostname = g_unescape_uri_string (host_part, "", path_part - host_part);
|
||||
if (unescaped_hostname == NULL)
|
||||
{
|
||||
g_set_error (error, G_CONVERT_ERROR, G_CONVERT_ERROR_INVALID_URI,
|
||||
_("The hostname of the URI `%s' is contains invalidly escaped characters"),
|
||||
uri);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (hostname)
|
||||
*hostname = unescaped_hostname;
|
||||
else
|
||||
g_free (unescaped_hostname);
|
||||
}
|
||||
|
||||
filename = g_unescape_uri_string (path_part, "/", -1);
|
||||
|
||||
if (filename == NULL)
|
||||
{
|
||||
g_set_error (error, G_CONVERT_ERROR, G_CONVERT_ERROR_INVALID_URI,
|
||||
_("The URI `%s' is contains invalidly escaped characters"),
|
||||
uri);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* DOS uri's are like "file://host/c:\foo", so we need to check if we need to
|
||||
* drop the initial slash */
|
||||
offs = 0;
|
||||
if (g_path_is_absolute (filename+1))
|
||||
offs = 1;
|
||||
|
||||
result = g_filename_from_utf8 (filename + offs, -1, NULL, NULL, error);
|
||||
g_free (filename);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* g_filename_to_uri:
|
||||
* @filename: an absolute filename specified in the encoding
|
||||
* used for filenames by the operating system.
|
||||
* @hostname: A UTF-8 encoded hostname, or %NULL for none.
|
||||
* @error: location to store the error occuring, or %NULL to ignore
|
||||
* errors. Any of the errors in #GConvertError may occur.
|
||||
*
|
||||
* Converts an absolute filename to an escaped UTF-8 encoded URI.
|
||||
*
|
||||
* Return value: a newly allocated string holding the resulting
|
||||
* URI, or %NULL on an error.
|
||||
**/
|
||||
gchar *
|
||||
g_filename_to_uri (const char *filename,
|
||||
char *hostname,
|
||||
GError **error)
|
||||
{
|
||||
char *escaped_uri;
|
||||
char *utf8_filename;
|
||||
|
||||
g_return_val_if_fail (filename != NULL, NULL);
|
||||
|
||||
if (!g_path_is_absolute (filename))
|
||||
{
|
||||
g_set_error (error, G_CONVERT_ERROR, G_CONVERT_ERROR_NOT_ABSOLUTE_PATH,
|
||||
_("The pathname '%s' is not an absolute path"),
|
||||
filename);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
utf8_filename = g_filename_to_utf8 (filename, -1, NULL, NULL, error);
|
||||
if (utf8_filename == NULL)
|
||||
return NULL;
|
||||
|
||||
if (hostname &&
|
||||
!g_utf8_validate (hostname, -1, NULL))
|
||||
{
|
||||
g_free (utf8_filename);
|
||||
g_set_error (error, G_CONVERT_ERROR, G_CONVERT_ERROR_ILLEGAL_SEQUENCE,
|
||||
_("Invalid byte sequence in hostname"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
escaped_uri = g_escape_file_uri (hostname,
|
||||
utf8_filename);
|
||||
g_free (utf8_filename);
|
||||
|
||||
return escaped_uri;
|
||||
}
|
||||
|
||||
|
@ -37,7 +37,10 @@ typedef enum
|
||||
G_CONVERT_ERROR_NO_CONVERSION,
|
||||
G_CONVERT_ERROR_ILLEGAL_SEQUENCE,
|
||||
G_CONVERT_ERROR_FAILED,
|
||||
G_CONVERT_ERROR_PARTIAL_INPUT
|
||||
G_CONVERT_ERROR_PARTIAL_INPUT,
|
||||
G_CONVERT_ERROR_NOT_LOCAL_FILE,
|
||||
G_CONVERT_ERROR_INVALID_URI,
|
||||
G_CONVERT_ERROR_NOT_ABSOLUTE_PATH
|
||||
} GConvertError;
|
||||
|
||||
#define G_CONVERT_ERROR g_convert_error_quark()
|
||||
@ -107,6 +110,15 @@ gchar* g_filename_from_utf8 (const gchar *utf8string,
|
||||
gsize *bytes_written,
|
||||
GError **error);
|
||||
|
||||
gchar *g_filename_from_uri (const char *uri,
|
||||
char **hostname,
|
||||
GError **error);
|
||||
|
||||
gchar *g_filename_to_uri (const char *filename,
|
||||
char *hostname,
|
||||
GError **error);
|
||||
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __G_CONVERT_H__ */
|
||||
|
@ -75,7 +75,8 @@ test_programs = \
|
||||
tree-test \
|
||||
type-test \
|
||||
unicode-caseconv \
|
||||
unicode-encoding
|
||||
unicode-encoding \
|
||||
uri-test
|
||||
|
||||
test_scripts = run-markup-tests.sh
|
||||
|
||||
@ -117,6 +118,7 @@ tree_test_LDADD = $(progs_LDADD)
|
||||
type_test_LDADD = $(progs_LDADD)
|
||||
unicode_encoding_LDADD = $(progs_LDADD)
|
||||
unicode_caseconv_LDADD = $(progs_LDADD)
|
||||
uri_test_LDADD = $(progs_LDADD)
|
||||
|
||||
lib_LTLIBRARIES = libmoduletestplugin_a.la libmoduletestplugin_b.la
|
||||
|
||||
|
224
tests/uri-test.c
Normal file
224
tests/uri-test.c
Normal file
@ -0,0 +1,224 @@
|
||||
/* GLIB - Library of useful routines for C programming
|
||||
* Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Modified by the GLib Team and others 1997-2000. See the AUTHORS
|
||||
* file for a list of people on the GLib Team. See the ChangeLog
|
||||
* files for a list of changes. These files are distributed with
|
||||
* GLib at ftp://ftp.gtk.org/pub/gtk/.
|
||||
*/
|
||||
|
||||
#undef G_DISABLE_ASSERT
|
||||
#undef G_LOG_DOMAIN
|
||||
|
||||
#include <glib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
typedef struct
|
||||
{
|
||||
char *filename;
|
||||
char *hostname;
|
||||
char *expected_result;
|
||||
GConvertError expected_error; /* If failed */
|
||||
} ToUriTest;
|
||||
|
||||
ToUriTest
|
||||
to_uri_tests[] = {
|
||||
{ "/etc", NULL, "file:///etc"},
|
||||
{ "/etc", "", "file:///etc"},
|
||||
{ "/etc", "localhost", "file://localhost/etc"},
|
||||
#ifdef G_OS_WIN32
|
||||
{ "c:\\windows", NULL, "file:///c:\\windows"},
|
||||
{ "c:\\windows", "localhost", "file://localhost/c:\\windows"},
|
||||
#endif
|
||||
{ "etc", "localhost", NULL, G_CONVERT_ERROR_NOT_ABSOLUTE_PATH},
|
||||
{ "/etc/öäå", NULL, NULL, G_CONVERT_ERROR_ILLEGAL_SEQUENCE},
|
||||
{ "/etc/öäå", NULL, "file:///etc/%C3%B6%C3%A4%C3%A5"},
|
||||
{ "/etc", "öäå", "file://%C3%B6%C3%A4%C3%A5/etc"},
|
||||
{ "/etc", "åäö", NULL, G_CONVERT_ERROR_ILLEGAL_SEQUENCE},
|
||||
{ "/etc/file with #%", NULL, "file:///etc/file%20with%20%23%25"},
|
||||
};
|
||||
|
||||
|
||||
typedef struct
|
||||
{
|
||||
char *uri;
|
||||
char *expected_filename;
|
||||
char *expected_hostname;
|
||||
GConvertError expected_error; /* If failed */
|
||||
} FromUriTest;
|
||||
|
||||
FromUriTest
|
||||
from_uri_tests[] = {
|
||||
{ "file:///etc", "/etc", NULL},
|
||||
{ "file:/etc", "/etc", NULL},
|
||||
{ "file://localhost/etc", "/etc", "localhost", },
|
||||
{ "file://localhost/etc/%23%25%20file", "/etc/#% file", "localhost", },
|
||||
{ "file://%C3%B6%C3%A4%C3%A5/etc", "/etc", "öäå", },
|
||||
{ "file:////etc/%C3%B6%C3%C3%C3%A5", NULL, NULL, G_CONVERT_ERROR_INVALID_URI},
|
||||
{ "file://localhost/åäö", NULL, NULL, G_CONVERT_ERROR_INVALID_URI},
|
||||
{ "file://åäö/etc", NULL, NULL, G_CONVERT_ERROR_INVALID_URI},
|
||||
{ "file:///some/file#bad", NULL, NULL, G_CONVERT_ERROR_INVALID_URI},
|
||||
{ "file://some", NULL, NULL, G_CONVERT_ERROR_INVALID_URI},
|
||||
};
|
||||
|
||||
|
||||
static gboolean any_failed = FALSE;
|
||||
|
||||
static void
|
||||
run_to_uri_tests (void)
|
||||
{
|
||||
int i;
|
||||
gchar *res;
|
||||
GError *error;
|
||||
|
||||
for (i = 0; i < G_N_ELEMENTS (to_uri_tests); i++)
|
||||
{
|
||||
error = NULL;
|
||||
res = g_filename_to_uri (to_uri_tests[i].filename,
|
||||
to_uri_tests[i].hostname,
|
||||
&error);
|
||||
|
||||
if (to_uri_tests[i].expected_result == NULL)
|
||||
{
|
||||
if (res != NULL)
|
||||
{
|
||||
g_print ("\ng_filename_to_uri() test %d failed, expected to return NULL, actual result: %s\n", i, res);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (error == NULL)
|
||||
{
|
||||
g_print ("\ng_filename_to_uri() test %d failed, returned NULL, but didn't set error\n", i);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
else if (error->domain != G_CONVERT_ERROR)
|
||||
{
|
||||
g_print ("\ng_filename_to_uri() test %d failed, returned NULL, set non G_CONVERT_ERROR error\n", i);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
else if (error->code != to_uri_tests[i].expected_error)
|
||||
{
|
||||
g_print ("\ng_filename_to_uri() test %d failed as expected, but set wrong errorcode %d instead of expected %d \n",
|
||||
i, error->code, to_uri_tests[i].expected_error);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (res == NULL || strcmp (res, to_uri_tests[i].expected_result) != 0)
|
||||
{
|
||||
g_print ("\ng_filename_to_uri() test %d failed, expected result: %s, actual result: %s\n",
|
||||
i, to_uri_tests[i].expected_result, (res) ? res : "NULL");
|
||||
if (error)
|
||||
g_print ("Error message: %s\n", error->message);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
|
||||
/* Give some output */
|
||||
g_print (".");
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
run_from_uri_tests (void)
|
||||
{
|
||||
int i;
|
||||
gchar *res;
|
||||
gchar *hostname;
|
||||
GError *error;
|
||||
|
||||
for (i = 0; i < G_N_ELEMENTS (from_uri_tests); i++)
|
||||
{
|
||||
error = NULL;
|
||||
res = g_filename_from_uri (from_uri_tests[i].uri,
|
||||
&hostname,
|
||||
&error);
|
||||
|
||||
if (from_uri_tests[i].expected_filename == NULL)
|
||||
{
|
||||
if (res != NULL)
|
||||
{
|
||||
g_print ("\ng_filename_from_uri() test %d failed, expected to return NULL, actual result: %s\n", i, res);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (error == NULL)
|
||||
{
|
||||
g_print ("\ng_filename_from_uri() test %d failed, returned NULL, but didn't set error\n", i);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
else if (error->domain != G_CONVERT_ERROR)
|
||||
{
|
||||
g_print ("\ng_filename_from_uri() test %d failed, returned NULL, set non G_CONVERT_ERROR error\n", i);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
else if (error->code != from_uri_tests[i].expected_error)
|
||||
{
|
||||
g_print ("\ng_filename_from_uri() test %d failed as expected, but set wrong errorcode %d instead of expected %d \n",
|
||||
i, error->code, from_uri_tests[i].expected_error);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (res == NULL || strcmp (res, from_uri_tests[i].expected_filename) != 0)
|
||||
{
|
||||
g_print ("\ng_filename_from_uri() test %d failed, expected result: %s, actual result: %s\n",
|
||||
i, from_uri_tests[i].expected_filename, (res) ? res : "NULL");
|
||||
any_failed = TRUE;
|
||||
}
|
||||
|
||||
if (from_uri_tests[i].expected_hostname == NULL)
|
||||
{
|
||||
if (hostname != NULL)
|
||||
{
|
||||
g_print ("\ng_filename_from_uri() test %d failed, expected no hostname, got: %s\n",
|
||||
i, hostname);
|
||||
any_failed = TRUE;
|
||||
}
|
||||
}
|
||||
else if (hostname == NULL ||
|
||||
strcmp (hostname, from_uri_tests[i].expected_hostname) != 0)
|
||||
{
|
||||
g_print ("\ng_filename_from_uri() test %d failed, expected hostname: %s, actual result: %s\n",
|
||||
i, from_uri_tests[i].expected_hostname, (hostname) ? hostname : "NULL");
|
||||
any_failed = TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
/* Give some output */
|
||||
g_print (".");
|
||||
}
|
||||
g_print ("\n");
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc,
|
||||
char *argv[])
|
||||
{
|
||||
run_to_uri_tests ();
|
||||
run_from_uri_tests ();
|
||||
|
||||
return any_failed ? 1 : 0;
|
||||
}
|
Loading…
Reference in New Issue
Block a user