1ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * uri.c: set of generic URI related routines 3ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Reference: RFCs 3986, 2732 and 2373 5ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 6ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * See Copyright for the status of this software. 7ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 8ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * daniel@veillard.com 9ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 10ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 11ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#define IN_LIBXML 12ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#include "libxml.h" 13ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 14ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#include <string.h> 15ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 16ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#include <libxml/xmlmemory.h> 17ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#include <libxml/uri.h> 18ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#include <libxml/globals.h> 19ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#include <libxml/xmlerror.h> 20ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun/** 2294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * MAX_URI_LENGTH: 2394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * 2494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * The definition of the URI regexp in the above RFC has no size limit 2594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * In practice they are usually relativey short except for the 2694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * data URI scheme as defined in RFC 2397. Even for data URI the usual 2794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * maximum size before hitting random practical limits is around 64 KB 2894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * and 4KB is usually a maximum admitted limit for proper operations. 2994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * The value below is more a security limit than anything else and 3094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * really should never be hit by 'normal' operations 3194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * Set to 1 MByte in 2012, this is only enforced on output 3294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun */ 3394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun#define MAX_URI_LENGTH 1024 * 1024 3494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun 3594442ad4107000e6d49f9b85a46a591495a57632Selim Gurunstatic void 3694442ad4107000e6d49f9b85a46a591495a57632Selim GurunxmlURIErrMemory(const char *extra) 3794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun{ 3894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (extra) 3994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun __xmlRaiseError(NULL, NULL, NULL, 4094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun NULL, NULL, XML_FROM_URI, 4194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun XML_ERR_NO_MEMORY, XML_ERR_FATAL, NULL, 0, 4294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun extra, NULL, NULL, 0, 0, 4394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun "Memory allocation failed : %s\n", extra); 4494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun else 4594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun __xmlRaiseError(NULL, NULL, NULL, 4694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun NULL, NULL, XML_FROM_URI, 4794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun XML_ERR_NO_MEMORY, XML_ERR_FATAL, NULL, 0, 4894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun NULL, NULL, NULL, 0, 0, 4994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun "Memory allocation failed\n"); 5094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun} 5194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun 5260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic void xmlCleanURI(xmlURIPtr uri); 53ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 54ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 5560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Old rule from 2396 used in legacy handling code 56ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * alpha = lowalpha | upalpha 57ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 58ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#define IS_ALPHA(x) (IS_LOWALPHA(x) || IS_UPALPHA(x)) 59ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 60ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 61ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 62ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * lowalpha = "a" | "b" | "c" | "d" | "e" | "f" | "g" | "h" | "i" | "j" | 63ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * "k" | "l" | "m" | "n" | "o" | "p" | "q" | "r" | "s" | "t" | 64ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * "u" | "v" | "w" | "x" | "y" | "z" 65ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 66ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 67ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#define IS_LOWALPHA(x) (((x) >= 'a') && ((x) <= 'z')) 68ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 69ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 70ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * upalpha = "A" | "B" | "C" | "D" | "E" | "F" | "G" | "H" | "I" | "J" | 71ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * "K" | "L" | "M" | "N" | "O" | "P" | "Q" | "R" | "S" | "T" | 72ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * "U" | "V" | "W" | "X" | "Y" | "Z" 73ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 74ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#define IS_UPALPHA(x) (((x) >= 'A') && ((x) <= 'Z')) 75ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 76ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#ifdef IS_DIGIT 77ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#undef IS_DIGIT 78ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#endif 79ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 80ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * digit = "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9" 81ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 82ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#define IS_DIGIT(x) (((x) >= '0') && ((x) <= '9')) 83ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 84ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 85ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * alphanum = alpha | digit 86ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 87ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 88ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#define IS_ALPHANUM(x) (IS_ALPHA(x) || IS_DIGIT(x)) 89ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 90ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 91ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * mark = "-" | "_" | "." | "!" | "~" | "*" | "'" | "(" | ")" 92ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 93ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 9460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define IS_MARK(x) (((x) == '-') || ((x) == '_') || ((x) == '.') || \ 9560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((x) == '!') || ((x) == '~') || ((x) == '*') || ((x) == '\'') || \ 96ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ((x) == '(') || ((x) == ')')) 97ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 9860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/* 9960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * unwise = "{" | "}" | "|" | "\" | "^" | "`" 10060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 101ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 10260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define IS_UNWISE(p) \ 10360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (((*(p) == '{')) || ((*(p) == '}')) || ((*(p) == '|')) || \ 10460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '\\')) || ((*(p) == '^')) || ((*(p) == '[')) || \ 10560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == ']')) || ((*(p) == '`'))) 106ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 107ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * reserved = ";" | "/" | "?" | ":" | "@" | "&" | "=" | "+" | "$" | "," | 10860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * "[" | "]" 109ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 110ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 11160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define IS_RESERVED(x) (((x) == ';') || ((x) == '/') || ((x) == '?') || \ 11260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((x) == ':') || ((x) == '@') || ((x) == '&') || ((x) == '=') || \ 11360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((x) == '+') || ((x) == '$') || ((x) == ',') || ((x) == '[') || \ 11460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((x) == ']')) 115ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 116ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 117ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * unreserved = alphanum | mark 118ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 119ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 120ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#define IS_UNRESERVED(x) (IS_ALPHANUM(x) || IS_MARK(x)) 121ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 122ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 12360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Skip to next pointer char, handle escaped sequences 124ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 125ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 12660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define NEXT(p) ((*p == '%')? p += 3 : p++) 127ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 128ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 12960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Productions from the spec. 13060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 13160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * authority = server | reg_name 13260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * reg_name = 1*( unreserved | escaped | "$" | "," | 13360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * ";" | ":" | "@" | "&" | "=" | "+" ) 13460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 13560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * path = [ abs_path | opaque_part ] 136ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 13760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 13860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define STRNDUP(s, n) (char *) xmlStrndup((const xmlChar *)(s), (n)) 13960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 14060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/************************************************************************ 14160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * * 14260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * RFC 3986 parser * 14360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * * 14460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ************************************************************************/ 14560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 14660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_DIGIT(p) ((*(p) >= '0') && (*(p) <= '9')) 14760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_ALPHA(p) (((*(p) >= 'a') && (*(p) <= 'z')) || \ 14860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) >= 'A') && (*(p) <= 'Z'))) 14960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_HEXDIG(p) \ 15060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (ISA_DIGIT(p) || ((*(p) >= 'a') && (*(p) <= 'f')) || \ 15160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) >= 'A') && (*(p) <= 'F'))) 152ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 153ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 15460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * sub-delims = "!" / "$" / "&" / "'" / "(" / ")" 15560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / "*" / "+" / "," / ";" / "=" 156ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 15760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_SUB_DELIM(p) \ 15860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (((*(p) == '!')) || ((*(p) == '$')) || ((*(p) == '&')) || \ 15960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '(')) || ((*(p) == ')')) || ((*(p) == '*')) || \ 16060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '+')) || ((*(p) == ',')) || ((*(p) == ';')) || \ 161df143a5041f03a22808b59c76698770b74692815Selim Gurun ((*(p) == '=')) || ((*(p) == '\''))) 162ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 163ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 16460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * gen-delims = ":" / "/" / "?" / "#" / "[" / "]" / "@" 165ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 16660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_GEN_DELIM(p) \ 16760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (((*(p) == ':')) || ((*(p) == '/')) || ((*(p) == '?')) || \ 16860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '#')) || ((*(p) == '[')) || ((*(p) == ']')) || \ 16960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '@'))) 170ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 171ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 17260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * reserved = gen-delims / sub-delims 173ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 17460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_RESERVED(p) (ISA_GEN_DELIM(p) || (ISA_SUB_DELIM(p))) 175ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 176ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 17760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~" 178ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 17960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_UNRESERVED(p) \ 18060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((ISA_ALPHA(p)) || (ISA_DIGIT(p)) || ((*(p) == '-')) || \ 18160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '.')) || ((*(p) == '_')) || ((*(p) == '~'))) 182ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 183ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 18460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * pct-encoded = "%" HEXDIG HEXDIG 185ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 18660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_PCT_ENCODED(p) \ 18760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '%') && (ISA_HEXDIG(p + 1)) && (ISA_HEXDIG(p + 2))) 188ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 189ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 19060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * pchar = unreserved / pct-encoded / sub-delims / ":" / "@" 191ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 19260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define ISA_PCHAR(p) \ 19360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (ISA_UNRESERVED(p) || ISA_PCT_ENCODED(p) || ISA_SUB_DELIM(p) || \ 19460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == ':')) || ((*(p) == '@'))) 195ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 19660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 19760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986Scheme: 19860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 19960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: pointer to the string to analyze 20060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 20160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an URI scheme 20260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 20360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * ALPHA *( ALPHA / DIGIT / "+" / "-" / "." ) 20460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 20560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 20660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 20760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 20860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986Scheme(xmlURIPtr uri, const char **str) { 20960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 210ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 21160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (str == NULL) 21260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(-1); 213ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 21460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 21560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (!ISA_ALPHA(cur)) 21660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(2); 21760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 21860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (ISA_ALPHA(cur) || ISA_DIGIT(cur) || 21960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (*cur == '+') || (*cur == '-') || (*cur == '.')) cur++; 22060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 22160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->scheme != NULL) xmlFree(uri->scheme); 22260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->scheme = STRNDUP(*str, cur - *str); 22360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 22460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 22560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 22660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 227ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 22860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 22960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986Fragment: 23060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 23160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: pointer to the string to analyze 23260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 23360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse the query part of an URI 23460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 23560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * fragment = *( pchar / "/" / "?" ) 23660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * NOTE: the strict syntax as defined by 3986 does not allow '[' and ']' 23760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * in the fragment identifier but this is used very broadly for 23860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xpointer scheme selection, so we are allowing it here to not break 23960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * for example all the DocBook processing chains. 24060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 24160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 242ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 24360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 24460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986Fragment(xmlURIPtr uri, const char **str) 24560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 24660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 247ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 24860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (str == NULL) 24960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (-1); 250ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 25160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 25260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 25360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while ((ISA_PCHAR(cur)) || (*cur == '/') || (*cur == '?') || 25460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (*cur == '[') || (*cur == ']') || 25560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((uri != NULL) && (uri->cleanup & 1) && (IS_UNWISE(cur)))) 25660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NEXT(cur); 25760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 25860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->fragment != NULL) 25960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(uri->fragment); 26060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->cleanup & 2) 26160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->fragment = STRNDUP(*str, cur - *str); 26260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else 26360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->fragment = xmlURIUnescapeString(*str, cur - *str, NULL); 26460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 26560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 26660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (0); 26760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 26860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 26960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 27060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986Query: 27160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 27260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: pointer to the string to analyze 273ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 27460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse the query part of an URI 275ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 27660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * query = *uric 27760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 27860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 279ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 28060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 28160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986Query(xmlURIPtr uri, const char **str) 28260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 28360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 284ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 28560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (str == NULL) 28660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (-1); 287ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 28860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 28960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 29060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while ((ISA_PCHAR(cur)) || (*cur == '/') || (*cur == '?') || 29160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((uri != NULL) && (uri->cleanup & 1) && (IS_UNWISE(cur)))) 29260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NEXT(cur); 29360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 29460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->query != NULL) 29560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(uri->query); 29660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->cleanup & 2) 29760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->query = STRNDUP(*str, cur - *str); 29860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else 29960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->query = xmlURIUnescapeString(*str, cur - *str, NULL); 30060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 30160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* Save the raw bytes of the query as well. 30260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * See: http://mail.gnome.org/archives/xml/2007-April/thread.html#00114 30360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 30460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->query_raw != NULL) 30560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree (uri->query_raw); 30660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->query_raw = STRNDUP (*str, cur - *str); 30760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 30860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 30960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (0); 31060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 311ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 312ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 31360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986Port: 31460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 31560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 316ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 31760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse a port part and fills in the appropriate fields 31860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 319ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 32060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * port = *DIGIT 32160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 32260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 323ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 32460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 32560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986Port(xmlURIPtr uri, const char **str) 32660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 32760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur = *str; 328ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 32960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ISA_DIGIT(cur)) { 33060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) 33160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->port = 0; 33260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (ISA_DIGIT(cur)) { 33360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) 33460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->port = uri->port * 10 + (*cur - '0'); 33560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 33660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 33760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 33860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 339ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 34060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 341ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 342ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 343ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 34460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986Userinfo: 34560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 34660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 347ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 34860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an user informations part and fills in the appropriate fields 34960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 350ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 35160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * userinfo = *( unreserved / pct-encoded / sub-delims / ":" ) 35260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 35360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 354ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 35560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 35660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986Userinfo(xmlURIPtr uri, const char **str) 35760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 35860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 359ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 36060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 36160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (ISA_UNRESERVED(cur) || ISA_PCT_ENCODED(cur) || 36260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ISA_SUB_DELIM(cur) || (*cur == ':')) 36360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NEXT(cur); 36460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*cur == '@') { 36560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 36660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->user != NULL) xmlFree(uri->user); 36760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->cleanup & 2) 36860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->user = STRNDUP(*str, cur - *str); 36960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else 37060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->user = xmlURIUnescapeString(*str, cur - *str, NULL); 37160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 37260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 37360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 37460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 37560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 37660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 377ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 37860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 37960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986DecOctet: 38060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 38160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 38260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * dec-octet = DIGIT ; 0-9 38360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / %x31-39 DIGIT ; 10-99 38460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / "1" 2DIGIT ; 100-199 38560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / "2" %x30-34 DIGIT ; 200-249 38660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / "25" %x30-35 ; 250-255 38760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 38860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Skip a dec-octet. 38960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 39060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 if found and skipped, 1 otherwise 39160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 39260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 39360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986DecOctet(const char **str) { 39460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur = *str; 395ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 39660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (!(ISA_DIGIT(cur))) 39760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 39860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (!ISA_DIGIT(cur+1)) 39960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 40060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if ((*cur != '0') && (ISA_DIGIT(cur + 1)) && (!ISA_DIGIT(cur+2))) 40160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur += 2; 40260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if ((*cur == '1') && (ISA_DIGIT(cur + 1)) && (ISA_DIGIT(cur + 2))) 40360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur += 3; 40460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if ((*cur == '2') && (*(cur + 1) >= '0') && 40560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (*(cur + 1) <= '4') && (ISA_DIGIT(cur + 2))) 40660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur += 3; 40760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if ((*cur == '2') && (*(cur + 1) == '5') && 40860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (*(cur + 2) >= '0') && (*(cur + 1) <= '5')) 40960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur += 3; 41060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else 41160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 41260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 41360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 41460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 41560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 41660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986Host: 41760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 41860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 41960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 42060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an host part and fills in the appropriate fields 42160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 42260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 42360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * host = IP-literal / IPv4address / reg-name 42460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * IP-literal = "[" ( IPv6address / IPvFuture ) "]" 42560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * IPv4address = dec-octet "." dec-octet "." dec-octet "." dec-octet 42660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * reg-name = *( unreserved / pct-encoded / sub-delims ) 42760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 42860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 42960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 43060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 43160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986Host(xmlURIPtr uri, const char **str) 43260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 43360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur = *str; 43460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *host; 435ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 43660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott host = cur; 43760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 43860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * IPv6 and future adressing scheme are enclosed between brackets 43960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 44060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*cur == '[') { 44160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 44260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while ((*cur != ']') && (*cur != 0)) 44360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 44460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*cur != ']') 44560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 44660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 44760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto found; 448ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 44960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 45060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * try to parse an IPv4 45160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 45260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ISA_DIGIT(cur)) { 45360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (xmlParse3986DecOctet(&cur) != 0) 45460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto not_ipv4; 45560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*cur != '.') 45660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto not_ipv4; 45760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 45860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (xmlParse3986DecOctet(&cur) != 0) 45960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto not_ipv4; 46060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*cur != '.') 46160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto not_ipv4; 46260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (xmlParse3986DecOctet(&cur) != 0) 46360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto not_ipv4; 46460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*cur != '.') 46560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto not_ipv4; 46660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (xmlParse3986DecOctet(&cur) != 0) 46760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto not_ipv4; 46860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto found; 46960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottnot_ipv4: 47060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 471ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 47260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 47360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * then this should be a hostname which can be empty 47460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 47560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (ISA_UNRESERVED(cur) || ISA_PCT_ENCODED(cur) || ISA_SUB_DELIM(cur)) 47660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NEXT(cur); 47760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottfound: 47860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 47960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->authority != NULL) xmlFree(uri->authority); 48060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->authority = NULL; 48160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->server != NULL) xmlFree(uri->server); 48260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (cur != host) { 48360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->cleanup & 2) 48460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->server = STRNDUP(host, cur - host); 48560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else 48660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->server = xmlURIUnescapeString(host, cur - host, NULL); 48760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else 48860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->server = NULL; 489ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 49060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 49160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 492ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 493ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 494ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 49560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986Authority: 49660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 49760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 498ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 49960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an authority part and fills in the appropriate fields 50060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 50160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 50260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * authority = [ userinfo "@" ] host [ ":" port ] 50360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 50460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 505ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 50660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 50760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986Authority(xmlURIPtr uri, const char **str) 50860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 50960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 51060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 511ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 51260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 51360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 51460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * try to parse an userinfo and check for the trailing @ 51560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 51660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Userinfo(uri, &cur); 51760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((ret != 0) || (*cur != '@')) 51860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 51960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else 52060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 52160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Host(uri, &cur); 52260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 52360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*cur == ':') { 52460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 52560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Port(uri, &cur); 52660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 527ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 52860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 52960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 530ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 531ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 532ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 53360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986Segment: 53460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 53560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @forbid: an optional forbidden character 53660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @empty: allow an empty segment 537ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 53860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse a segment and fills in the appropriate fields 53960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 54060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 54160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * segment = *pchar 54260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * segment-nz = 1*pchar 54360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * segment-nz-nc = 1*( unreserved / pct-encoded / sub-delims / "@" ) 54460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * ; non-zero-length segment without any colon ":" 54560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 54660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 547ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 54860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 54960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986Segment(const char **str, char forbid, int empty) 55060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 55160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 552ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 55360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 55460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (!ISA_PCHAR(cur)) { 55560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (empty) 55660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 55760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 55860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 55960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (ISA_PCHAR(cur) && (*cur != forbid)) 56060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NEXT(cur); 56160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 56260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (0); 563ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 564ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 565ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 56660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986PathAbEmpty: 56760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 56860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 569ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 57060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an path absolute or empty and fills in the appropriate fields 57160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 57260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 57360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * path-abempty = *( "/" segment ) 57460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 57560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 576ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 57760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 57860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986PathAbEmpty(xmlURIPtr uri, const char **str) 57960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 58060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 58160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 582ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 58360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 584ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 58560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*cur == '/') { 58660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 58760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Segment(&cur, 0, 1); 58860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 58960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 59060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 59160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) xmlFree(uri->path); 592df143a5041f03a22808b59c76698770b74692815Selim Gurun if (*str != cur) { 593df143a5041f03a22808b59c76698770b74692815Selim Gurun if (uri->cleanup & 2) 594df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = STRNDUP(*str, cur - *str); 595df143a5041f03a22808b59c76698770b74692815Selim Gurun else 596df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = xmlURIUnescapeString(*str, cur - *str, NULL); 597df143a5041f03a22808b59c76698770b74692815Selim Gurun } else { 598df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = NULL; 599df143a5041f03a22808b59c76698770b74692815Selim Gurun } 60060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 60160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 60260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (0); 60360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 604ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 605ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 60660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986PathAbsolute: 60760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 60860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 609ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 61060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an path absolute and fills in the appropriate fields 61160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 612ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 61360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * path-absolute = "/" [ segment-nz *( "/" segment ) ] 614ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 61560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 616ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 61760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 61860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986PathAbsolute(xmlURIPtr uri, const char **str) 61960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 62060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 62160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 622ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 62360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 624ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 62560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*cur != '/') 62660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 62760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 62860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Segment(&cur, 0, 0); 62960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret == 0) { 63060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*cur == '/') { 631ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project cur++; 63260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Segment(&cur, 0, 1); 63360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 63460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 635ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 63660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 63760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) xmlFree(uri->path); 638df143a5041f03a22808b59c76698770b74692815Selim Gurun if (cur != *str) { 639df143a5041f03a22808b59c76698770b74692815Selim Gurun if (uri->cleanup & 2) 640df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = STRNDUP(*str, cur - *str); 641df143a5041f03a22808b59c76698770b74692815Selim Gurun else 642df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = xmlURIUnescapeString(*str, cur - *str, NULL); 643df143a5041f03a22808b59c76698770b74692815Selim Gurun } else { 644df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = NULL; 645df143a5041f03a22808b59c76698770b74692815Selim Gurun } 64660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 64760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 64860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (0); 64960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 650ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 65160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 65260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986PathRootless: 65360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 65460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 65560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 65660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an path without root and fills in the appropriate fields 65760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 65860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 65960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * path-rootless = segment-nz *( "/" segment ) 66060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 66160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 66260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 66360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 66460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986PathRootless(xmlURIPtr uri, const char **str) 66560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 66660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 66760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 668ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 66960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 670ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 67160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Segment(&cur, 0, 0); 67260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 67360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*cur == '/') { 67460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 67560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Segment(&cur, 0, 1); 67660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 67760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 67860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 67960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) xmlFree(uri->path); 680df143a5041f03a22808b59c76698770b74692815Selim Gurun if (cur != *str) { 681df143a5041f03a22808b59c76698770b74692815Selim Gurun if (uri->cleanup & 2) 682df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = STRNDUP(*str, cur - *str); 683df143a5041f03a22808b59c76698770b74692815Selim Gurun else 684df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = xmlURIUnescapeString(*str, cur - *str, NULL); 685df143a5041f03a22808b59c76698770b74692815Selim Gurun } else { 686df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = NULL; 687df143a5041f03a22808b59c76698770b74692815Selim Gurun } 68860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 68960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 69060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (0); 69160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 692ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 69360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 69460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986PathNoScheme: 69560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 69660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 69760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 69860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an path which is not a scheme and fills in the appropriate fields 69960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 70060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 70160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * path-noscheme = segment-nz-nc *( "/" segment ) 70260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 70360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 70460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 70560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 70660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986PathNoScheme(xmlURIPtr uri, const char **str) 70760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 70860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 70960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 710ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 71160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 712ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 71360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Segment(&cur, ':', 0); 71460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 71560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*cur == '/') { 71660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 71760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Segment(&cur, 0, 1); 71860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 71960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 72060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 72160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) xmlFree(uri->path); 722df143a5041f03a22808b59c76698770b74692815Selim Gurun if (cur != *str) { 723df143a5041f03a22808b59c76698770b74692815Selim Gurun if (uri->cleanup & 2) 724df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = STRNDUP(*str, cur - *str); 725df143a5041f03a22808b59c76698770b74692815Selim Gurun else 726df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = xmlURIUnescapeString(*str, cur - *str, NULL); 727df143a5041f03a22808b59c76698770b74692815Selim Gurun } else { 728df143a5041f03a22808b59c76698770b74692815Selim Gurun uri->path = NULL; 729df143a5041f03a22808b59c76698770b74692815Selim Gurun } 73060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 73160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 73260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (0); 73360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 734ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 73560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 73660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986HierPart: 73760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 73860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 73960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 74060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an hierarchical part and fills in the appropriate fields 74160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 74260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 74360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * hier-part = "//" authority path-abempty 74460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / path-absolute 74560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / path-rootless 74660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / path-empty 74760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 74860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 74960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 75060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 75160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986HierPart(xmlURIPtr uri, const char **str) 75260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 75360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *cur; 75460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 755ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 75660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = *str; 757ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 75860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((*cur == '/') && (*(cur + 1) == '/')) { 75960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur += 2; 76060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Authority(uri, &cur); 76160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 76260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986PathAbEmpty(uri, &cur); 76360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 76460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 76560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 76660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else if (*cur == '/') { 76760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986PathAbsolute(uri, &cur); 76860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 76960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else if (ISA_PCHAR(cur)) { 77060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986PathRootless(uri, &cur); 77160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 77260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else { 77360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* path-empty is effectively empty */ 77460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 77560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) xmlFree(uri->path); 77660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->path = NULL; 77760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 778ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 77960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *str = cur; 78060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (0); 78160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 782ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 78360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 78460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986RelativeRef: 78560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 78660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 78760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 78860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an URI string and fills in the appropriate fields 78960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 79060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 79160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * relative-ref = relative-part [ "?" query ] [ "#" fragment ] 79260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * relative-part = "//" authority path-abempty 79360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / path-absolute 79460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / path-noscheme 79560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * / path-empty 79660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 79760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 79860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 79960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 80060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986RelativeRef(xmlURIPtr uri, const char *str) { 80160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 802ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 80360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((*str == '/') && (*(str + 1) == '/')) { 80460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott str += 2; 80560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Authority(uri, &str); 80660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 80760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986PathAbEmpty(uri, &str); 80860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 80960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else if (*str == '/') { 81060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986PathAbsolute(uri, &str); 81160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 81260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else if (ISA_PCHAR(str)) { 81360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986PathNoScheme(uri, &str); 81460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 81560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else { 81660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* path-empty is effectively empty */ 81760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 81860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) xmlFree(uri->path); 81960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->path = NULL; 82060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 821ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 822ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 82360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*str == '?') { 82460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott str++; 82560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Query(uri, &str); 82660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 82760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 82860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*str == '#') { 82960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott str++; 83060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Fragment(uri, &str); 83160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 83260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 83360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*str != 0) { 83460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlCleanURI(uri); 83560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 83660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 837ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(0); 838ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 839ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 84060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 84160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 84260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986URI: 84360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 84460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 84560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 84660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an URI string and fills in the appropriate fields 84760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 84860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 84960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * scheme ":" hier-part [ "?" query ] [ "#" fragment ] 85060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 85160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 85260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 85360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 85460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986URI(xmlURIPtr uri, const char *str) { 85560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 85660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 85760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Scheme(uri, &str); 85860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 85960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*str != ':') { 86060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(1); 86160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 86260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott str++; 86360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986HierPart(uri, &str); 86460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 86560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*str == '?') { 86660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott str++; 86760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Query(uri, &str); 86860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 86960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 87060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*str == '#') { 87160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott str++; 87260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986Fragment(uri, &str); 87360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) return(ret); 87460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 87560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (*str != 0) { 87660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlCleanURI(uri); 877ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(1); 87860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 879ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(0); 880ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 881ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 882ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 88360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParse3986URIReference: 88460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 88560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 886ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 88760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an URI reference string and fills in the appropriate fields 88860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of the @uri structure 889ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 89060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * URI-reference = URI / relative-ref 89160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 89260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 893ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 89460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int 89560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParse3986URIReference(xmlURIPtr uri, const char *str) { 89660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 897ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 898ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (str == NULL) 89960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(-1); 90060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlCleanURI(uri); 901ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 90260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 90360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Try first to parse absolute refs, then fallback to relative if 90460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * it fails. 90560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 90660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986URI(uri, str); 90760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) { 90860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlCleanURI(uri); 90960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986RelativeRef(uri, str); 91060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret != 0) { 91160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlCleanURI(uri); 91260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(ret); 91360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 91460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 91560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 91660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 91760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 91860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 91960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParseURI: 92060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the URI string to analyze 92160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 92260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an URI based on RFC 3986 92360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 92460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * URI-reference = [ absoluteURI | relativeURI ] [ "#" fragment ] 92560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 92660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns a newly built xmlURIPtr or NULL in case of error 92760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 92860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlURIPtr 92960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParseURI(const char *str) { 93060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlURIPtr uri; 93160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 93260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 93360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (str == NULL) 93460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 93560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri = xmlCreateURI(); 93660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 93760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParse3986URIReference(uri, str); 93860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret) { 93960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFreeURI(uri); 940ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(NULL); 941ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 94260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 94360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(uri); 94460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 94560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 94660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 94760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParseURIReference: 94860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an URI structure 94960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to analyze 95060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 95160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an URI reference string based on RFC 3986 and fills in the 95260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * appropriate fields of the @uri structure 95360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 95460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * URI-reference = URI / relative-ref 95560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 95660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or the error code 95760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 95860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottint 95960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParseURIReference(xmlURIPtr uri, const char *str) { 96060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(xmlParse3986URIReference(uri, str)); 96160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 96260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 96360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 96460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlParseURIRaw: 96560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the URI string to analyze 96660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @raw: if 1 unescaping of URI pieces are disabled 96760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 96860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Parse an URI but allows to keep intact the original fragments. 96960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 97060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * URI-reference = URI / relative-ref 97160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 97260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns a newly built xmlURIPtr or NULL in case of error 97360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 97460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlURIPtr 97560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlParseURIRaw(const char *str, int raw) { 97660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlURIPtr uri; 97760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret; 97860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 97960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (str == NULL) 98060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 98160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri = xmlCreateURI(); 98260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri != NULL) { 98360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (raw) { 98460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->cleanup |= 2; 98560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 98660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlParseURIReference(uri, str); 98760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret) { 98860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFreeURI(uri); 98960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 990ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 991ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 99260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(uri); 99360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 99460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 99560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/************************************************************************ 99660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * * 99760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Generic URI structure functions * 99860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * * 99960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ************************************************************************/ 100060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 100160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 100260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlCreateURI: 100360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 100460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Simply creates an empty xmlURI 100560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 100660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns the new structure or NULL in case of error 100760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 100860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlURIPtr 100960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlCreateURI(void) { 101060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlURIPtr ret; 101160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 101260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = (xmlURIPtr) xmlMalloc(sizeof(xmlURI)); 101360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret == NULL) { 101494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("creating URI structure\n"); 101560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 101660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 101760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott memset(ret, 0, sizeof(xmlURI)); 1018ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(ret); 1019ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1020ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1021ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 102294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * xmlSaveUriRealloc: 102394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * 102494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * Function to handle properly a reallocation when saving an URI 102594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * Also imposes some limit on the length of an URI string output 102694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun */ 102794442ad4107000e6d49f9b85a46a591495a57632Selim Gurunstatic xmlChar * 102894442ad4107000e6d49f9b85a46a591495a57632Selim GurunxmlSaveUriRealloc(xmlChar *ret, int *max) { 102994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlChar *temp; 103094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun int tmp; 103194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun 103294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (*max > MAX_URI_LENGTH) { 103394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("reaching arbitrary MAX_URI_LENGTH limit\n"); 103494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun return(NULL); 103594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun } 103694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun tmp = *max * 2; 103794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = (xmlChar *) xmlRealloc(ret, (tmp + 1)); 103894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) { 103994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("saving URI\n"); 104094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun return(NULL); 104194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun } 104294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun *max = tmp; 104394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun return(temp); 104494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun} 104594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun 104694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun/** 104760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlSaveUri: 104860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an xmlURI 1049ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 105060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Save the URI as an escaped string 1051ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 105260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns a new string (to be deallocated by caller) 1053ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 1054ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlChar * 105560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlSaveUri(xmlURIPtr uri) { 105660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlChar *ret = NULL; 105760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlChar *temp; 105860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *p; 105960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int len; 106060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int max; 1061ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 106260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri == NULL) return(NULL); 1063ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1064ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 106560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott max = 80; 106660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = (xmlChar *) xmlMallocAtomic((max + 1) * sizeof(xmlChar)); 1067ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ret == NULL) { 106894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("saving URI\n"); 1069ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(NULL); 1070ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 107160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott len = 0; 107260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 107360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->scheme != NULL) { 107460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->scheme; 107560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 107660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len >= max) { 107794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 107894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 107960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = temp; 108060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 108160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 108260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 108360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len >= max) { 108494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 108594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 108694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 1087ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 108860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = ':'; 108960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 109060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->opaque != NULL) { 109160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->opaque; 109260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 109360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 109494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 109594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 109694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 109760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 109860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (IS_RESERVED(*(p)) || IS_UNRESERVED(*(p))) 109960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 110060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else { 110160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int val = *(unsigned char *)p++; 110260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int hi = val / 0x10, lo = val % 0x10; 110360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '%'; 110460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = hi + (hi > 9? 'A'-10 : '0'); 110560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = lo + (lo > 9? 'A'-10 : '0'); 110660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 110760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 110860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else { 110960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->server != NULL) { 111060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 111194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 111294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 111394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 111460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 111560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '/'; 111660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '/'; 111760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->user != NULL) { 111860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->user; 111960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 112060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 112194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 112294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 112394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 112460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 112560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((IS_UNRESERVED(*(p))) || 112660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == ';')) || ((*(p) == ':')) || 112760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '&')) || ((*(p) == '=')) || 112860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '+')) || ((*(p) == '$')) || 112960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == ','))) 113060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 113160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else { 113260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int val = *(unsigned char *)p++; 113360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int hi = val / 0x10, lo = val % 0x10; 113460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '%'; 113560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = hi + (hi > 9? 'A'-10 : '0'); 113660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = lo + (lo > 9? 'A'-10 : '0'); 113760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 113860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 113960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 114094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 114194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 114294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 114360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 114460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '@'; 114560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 114660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->server; 114760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 114860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len >= max) { 114994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 115094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 115194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 115260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 115360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 115460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 115560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->port > 0) { 115660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 10 >= max) { 115794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 115894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 115994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 116060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 116160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott len += snprintf((char *) &ret[len], max - len, ":%d", uri->port); 116260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 116360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else if (uri->authority != NULL) { 116460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 116594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 116694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 116794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 116860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 116960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '/'; 117060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '/'; 117160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->authority; 117260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 117360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 117494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 117594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 117694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 117760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 117860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((IS_UNRESERVED(*(p))) || 117960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '$')) || ((*(p) == ',')) || ((*(p) == ';')) || 118060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == ':')) || ((*(p) == '@')) || ((*(p) == '&')) || 118160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '=')) || ((*(p) == '+'))) 118260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 118360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else { 118460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int val = *(unsigned char *)p++; 118560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int hi = val / 0x10, lo = val % 0x10; 118660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '%'; 118760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = hi + (hi > 9? 'A'-10 : '0'); 118860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = lo + (lo > 9? 'A'-10 : '0'); 118960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 119060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 119160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else if (uri->scheme != NULL) { 119260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 119394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 119494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 119594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 119660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 119760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '/'; 119860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '/'; 119960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 120060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) { 120160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->path; 120260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 120360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * the colon in file:///d: should not be escaped or 120460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Windows accesses fail later. 120560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 120660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((uri->scheme != NULL) && 120760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (p[0] == '/') && 120860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (((p[1] >= 'a') && (p[1] <= 'z')) || 120960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((p[1] >= 'A') && (p[1] <= 'Z'))) && 121060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (p[2] == ':') && 121160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (xmlStrEqual(BAD_CAST uri->scheme, BAD_CAST "file"))) { 121260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 121394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 121494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 121594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 121660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 121760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 121860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 121960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 122060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 122160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 122260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 122394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 122494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 122594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 122660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 122760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((IS_UNRESERVED(*(p))) || ((*(p) == '/')) || 122860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == ';')) || ((*(p) == '@')) || ((*(p) == '&')) || 122960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == '=')) || ((*(p) == '+')) || ((*(p) == '$')) || 123060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((*(p) == ','))) 123160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 123260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else { 123360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int val = *(unsigned char *)p++; 123460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int hi = val / 0x10, lo = val % 0x10; 123560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '%'; 123660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = hi + (hi > 9? 'A'-10 : '0'); 123760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = lo + (lo > 9? 'A'-10 : '0'); 123860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 123960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 124060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 124160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->query_raw != NULL) { 124260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 1 >= max) { 124394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 124494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 124594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 124660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 124760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '?'; 124860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->query_raw; 124960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 125060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 1 >= max) { 125194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 125294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 125394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 125460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 125560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 125660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 125760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else if (uri->query != NULL) { 125860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 125994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 126094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 126194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 126260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 126360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '?'; 126460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->query; 126560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 126660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 126794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 126894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 126994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 127060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 127194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if ((IS_UNRESERVED(*(p))) || (IS_RESERVED(*(p)))) 127260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 127360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else { 127460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int val = *(unsigned char *)p++; 127560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int hi = val / 0x10, lo = val % 0x10; 127660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '%'; 127760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = hi + (hi > 9? 'A'-10 : '0'); 127860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = lo + (lo > 9? 'A'-10 : '0'); 127960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 128060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 1281ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1282ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 128360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->fragment != NULL) { 128460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 128594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 128694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 128794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 128860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 128960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '#'; 129060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott p = uri->fragment; 129160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (*p != 0) { 129260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len + 3 >= max) { 129394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 129494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 129594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 129660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 129794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if ((IS_UNRESERVED(*(p))) || (IS_RESERVED(*(p)))) 129860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = *p++; 129960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else { 130060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int val = *(unsigned char *)p++; 130160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int hi = val / 0x10, lo = val % 0x10; 130260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = '%'; 130360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = hi + (hi > 9? 'A'-10 : '0'); 130460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[len++] = lo + (lo > 9? 'A'-10 : '0'); 130560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 130660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 1307ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 130860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len >= max) { 130994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &max); 131094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (temp == NULL) goto mem_error; 131194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = temp; 1312ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1313df143a5041f03a22808b59c76698770b74692815Selim Gurun ret[len] = 0; 131460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(ret); 131594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun 131694442ad4107000e6d49f9b85a46a591495a57632Selim Gurunmem_error: 131794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlFree(ret); 131894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun return(NULL); 1319ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1320ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1321ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 132260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlPrintURI: 132360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @stream: a FILE* for the output 132460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an xmlURI 1325ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 132660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Prints the URI in the stream @stream. 1327ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 132860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottvoid 132960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlPrintURI(FILE *stream, xmlURIPtr uri) { 133060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlChar *out; 1331ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 133260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out = xmlSaveUri(uri); 133360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (out != NULL) { 133460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott fprintf(stream, "%s", (char *) out); 133560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(out); 1336ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1337ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1338ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1339ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 134060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlCleanURI: 134160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an xmlURI 1342ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 134360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Make sure the xmlURI struct is free of content 1344ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 134560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic void 134660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlCleanURI(xmlURIPtr uri) { 134760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri == NULL) return; 1348ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 134960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->scheme != NULL) xmlFree(uri->scheme); 135060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->scheme = NULL; 135160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->server != NULL) xmlFree(uri->server); 135260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->server = NULL; 135360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->user != NULL) xmlFree(uri->user); 135460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->user = NULL; 135560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) xmlFree(uri->path); 135660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->path = NULL; 135760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->fragment != NULL) xmlFree(uri->fragment); 135860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->fragment = NULL; 135960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->opaque != NULL) xmlFree(uri->opaque); 136060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->opaque = NULL; 136160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->authority != NULL) xmlFree(uri->authority); 136260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->authority = NULL; 136360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->query != NULL) xmlFree(uri->query); 136460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->query = NULL; 136560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->query_raw != NULL) xmlFree(uri->query_raw); 136660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->query_raw = NULL; 136760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott} 1368ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 136960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/** 137060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlFreeURI: 137160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @uri: pointer to an xmlURI 137260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 137360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Free up the xmlURI struct 137460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 137560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottvoid 137660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlFreeURI(xmlURIPtr uri) { 137760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri == NULL) return; 137860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 137960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->scheme != NULL) xmlFree(uri->scheme); 138060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->server != NULL) xmlFree(uri->server); 138160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->user != NULL) xmlFree(uri->user); 138260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path != NULL) xmlFree(uri->path); 138360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->fragment != NULL) xmlFree(uri->fragment); 138460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->opaque != NULL) xmlFree(uri->opaque); 138560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->authority != NULL) xmlFree(uri->authority); 138660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->query != NULL) xmlFree(uri->query); 138760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->query_raw != NULL) xmlFree(uri->query_raw); 138860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(uri); 1389ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1390ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 139160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott/************************************************************************ 139260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * * 139360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Helper functions * 139460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * * 139560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ************************************************************************/ 139660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 1397ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 139860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlNormalizeURIPath: 139960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @path: pointer to the path string 1400ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 140160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Applies the 5 normalization steps to a path string--that is, RFC 2396 140260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Section 5.2, steps 6.c through 6.g. 1403ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 140460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Normalization occurs directly on the string, no new allocation is done 140560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 140660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns 0 or an error code 1407ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 140860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottint 140960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlNormalizeURIPath(char *path) { 141060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott char *cur, *out; 1411ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 141260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (path == NULL) 1413ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(-1); 1414ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 141560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* Skip all initial "/" chars. We want to get to the beginning of the 141660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * first non-empty segment. 1417ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 141860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = path; 141960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (cur[0] == '/') 142060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ++cur; 142160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (cur[0] == '\0') 142260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 142360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 142460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* Keep everything we've seen so far. */ 142560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out = cur; 142660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 1427ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 142860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Analyze each segment in sequence for cases (c) and (d). 1429ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 143060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (cur[0] != '\0') { 1431ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 143260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * c) All occurrences of "./", where "." is a complete path segment, 143360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * are removed from the buffer string. 1434ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 143560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((cur[0] == '.') && (cur[1] == '/')) { 143660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur += 2; 143760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* '//' normalization should be done at this point too */ 143860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (cur[0] == '/') 1439ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project cur++; 144060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott continue; 1441ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1442ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 144360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 144460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * d) If the buffer string ends with "." as a complete path segment, 144560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * that "." is removed. 144660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 144760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((cur[0] == '.') && (cur[1] == '\0')) 144860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott break; 1449ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 145060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* Otherwise keep the segment. */ 145160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (cur[0] != '/') { 145260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (cur[0] == '\0') 145360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott goto done_cd; 145460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (out++)[0] = (cur++)[0]; 145560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 145660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* nomalize // */ 145760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while ((cur[0] == '/') && (cur[1] == '/')) 145860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur++; 1459ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 146060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (out++)[0] = (cur++)[0]; 1461ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 146260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott done_cd: 146360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out[0] = '\0'; 146460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 146560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* Reset to the beginning of the first segment for the next sequence. */ 146660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = path; 146760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (cur[0] == '/') 146860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ++cur; 146960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (cur[0] == '\0') 147060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 147160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 147260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 147360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Analyze each segment in sequence for cases (e) and (f). 147460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 147560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * e) All occurrences of "<segment>/../", where <segment> is a 147660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * complete path segment not equal to "..", are removed from the 147760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * buffer string. Removal of these path segments is performed 147860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * iteratively, removing the leftmost matching pattern on each 147960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * iteration, until no matching pattern remains. 148060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 148160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * f) If the buffer string ends with "<segment>/..", where <segment> 148260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * is a complete path segment not equal to "..", that 148360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * "<segment>/.." is removed. 148460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 148560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * To satisfy the "iterative" clause in (e), we need to collapse the 148660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * string every time we find something that needs to be removed. Thus, 148760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * we don't need to keep two pointers into the string: we only need a 148860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * "current position" pointer. 148960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 149060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (1) { 149160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott char *segp, *tmp; 1492ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 149360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* At the beginning of each iteration of this loop, "cur" points to 149460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * the first character of the segment we want to examine. 149560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 1496ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 149760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* Find the end of the current segment. */ 149860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segp = cur; 149960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while ((segp[0] != '/') && (segp[0] != '\0')) 150060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ++segp; 1501ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 150260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* If this is the last segment, we're done (we need at least two 150360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * segments to meet the criteria for the (e) and (f) cases). 150460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 150560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (segp[0] == '\0') 150660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott break; 1507ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 150860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* If the first segment is "..", or if the next segment _isn't_ "..", 150960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * keep this segment and try the next one. 151060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 151160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ++segp; 151260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (((cur[0] == '.') && (cur[1] == '.') && (segp == cur+3)) 151360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott || ((segp[0] != '.') || (segp[1] != '.') 151460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott || ((segp[2] != '/') && (segp[2] != '\0')))) { 151560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = segp; 151660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott continue; 1517ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1518ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 151960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* If we get here, remove this segment and the next one and back up 152060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * to the previous segment (if there is one), to implement the 152160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * "iteratively" clause. It's pretty much impossible to back up 152260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * while maintaining two pointers into the buffer, so just compact 152360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * the whole buffer now. 1524ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 1525ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 152660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* If this is the end of the buffer, we're done. */ 152760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (segp[2] == '\0') { 152860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur[0] = '\0'; 152960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott break; 1530ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 153160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* Valgrind complained, strcpy(cur, segp + 3); */ 153294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun /* string will overlap, do not use strcpy */ 153394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun tmp = cur; 153494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun segp += 3; 153594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun while ((*tmp++ = *segp++) != 0) 153694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ; 1537ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 153860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* If there are no previous segments, then keep going from here. */ 153960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segp = cur; 154060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while ((segp > path) && ((--segp)[0] == '/')) 154160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ; 154260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (segp == path) 154360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott continue; 1544ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 154560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* "segp" is pointing to the end of a previous segment; find it's 154660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * start. We need to back up to the previous segment and start 154760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * over with that to handle things like "foo/bar/../..". If we 154860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * don't do this, then on the first pass we'll remove the "bar/..", 154960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * but be pointing at the second ".." so we won't realize we can also 155060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * remove the "foo/..". 155160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 155260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = segp; 155360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while ((cur > path) && (cur[-1] != '/')) 155460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott --cur; 155560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 155660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out[0] = '\0'; 1557ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1558ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 155960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * g) If the resulting buffer string still begins with one or more 156060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * complete path segments of "..", then the reference is 156160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * considered to be in error. Implementations may handle this 156260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * error by retaining these components in the resolved path (i.e., 156360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * treating them as part of the final URI), by removing them from 156460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * the resolved path (i.e., discarding relative levels above the 156560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * root), or by avoiding traversal of the reference. 156660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 156760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * We discard them from the final path. 1568ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 156960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (path[0] == '/') { 157060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur = path; 157160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while ((cur[0] == '/') && (cur[1] == '.') && (cur[2] == '.') 157260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott && ((cur[3] == '/') || (cur[3] == '\0'))) 157360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott cur += 3; 1574ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 157560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (cur != path) { 157660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out = path; 157760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while (cur[0] != '\0') 157860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott (out++)[0] = (cur++)[0]; 157960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out[0] = 0; 158060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 1581ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1582ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1583ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(0); 1584ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1585ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 158660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottstatic int is_hex(char c) { 158760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (((c >= '0') && (c <= '9')) || 158860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((c >= 'a') && (c <= 'f')) || 158960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ((c >= 'A') && (c <= 'F'))) 1590ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(1); 159160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(0); 1592ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1593ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1594ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 159560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlURIUnescapeString: 159660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string to unescape 159760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @len: the length in bytes to unescape (or <= 0 to indicate full string) 159860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @target: optional destination buffer 1599ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 160060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Unescaping routine, but does not check that the string is an URI. The 160160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * output is a direct unsigned char translation of %XX values (no encoding) 160260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Note that the length of the result can only be smaller or same size as 160360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * the input string. 1604ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 160560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns a copy of the string, but unescaped, will return NULL only in case 160660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * of error 1607ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 160860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scottchar * 160960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlURIUnescapeString(const char *str, int len, char *target) { 161060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott char *ret, *out; 161160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const char *in; 1612ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1613ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (str == NULL) 161460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 161560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len <= 0) len = strlen(str); 161660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len < 0) return(NULL); 161760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 161860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (target == NULL) { 161960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = (char *) xmlMallocAtomic(len + 1); 162060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret == NULL) { 162194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("unescaping URI value\n"); 162260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 1623ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 162460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else 162560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = target; 162660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott in = str; 162760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out = ret; 162860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while(len > 0) { 162960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((len > 2) && (*in == '%') && (is_hex(in[1])) && (is_hex(in[2]))) { 163060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott in++; 163194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if ((*in >= '0') && (*in <= '9')) 163260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *out = (*in - '0'); 163360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if ((*in >= 'a') && (*in <= 'f')) 163460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *out = (*in - 'a') + 10; 163560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if ((*in >= 'A') && (*in <= 'F')) 163660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *out = (*in - 'A') + 10; 163760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott in++; 163894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if ((*in >= '0') && (*in <= '9')) 163960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *out = *out * 16 + (*in - '0'); 164060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if ((*in >= 'a') && (*in <= 'f')) 164160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *out = *out * 16 + (*in - 'a') + 10; 164260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if ((*in >= 'A') && (*in <= 'F')) 164360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *out = *out * 16 + (*in - 'A') + 10; 164460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott in++; 164560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott len -= 3; 164660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out++; 164760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else { 164860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *out++ = *in++; 164960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott len--; 1650ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1651ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 165260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott *out = 0; 1653ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(ret); 1654ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1655ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1656ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 165760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlURIEscapeStr: 165860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: string to escape 165960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @list: exception list string of chars not to escape 1660ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 166160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * This routine escapes a string to hex, ignoring reserved characters (a-z) 166260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * and the characters in the exception list. 1663ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 166460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns a new escaped string or NULL in case of error. 1665ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 166660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlChar * 166760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlURIEscapeStr(const xmlChar *str, const xmlChar *list) { 166860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlChar *ret, ch; 166960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlChar *temp; 167060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott const xmlChar *in; 167194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun int len, out; 1672ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1673ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (str == NULL) 167460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 167560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (str[0] == 0) 167660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(xmlStrdup(str)); 167760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott len = xmlStrlen(str); 167860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (!(len > 0)) return(NULL); 1679ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 168060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott len += 20; 168160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = (xmlChar *) xmlMallocAtomic(len); 168260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret == NULL) { 168394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("escaping URI value\n"); 168460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 1685ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 168660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott in = (const xmlChar *) str; 168760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott out = 0; 168860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott while(*in != 0) { 168960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (len - out <= 3) { 169094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun temp = xmlSaveUriRealloc(ret, &len); 169160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (temp == NULL) { 169294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("escaping URI value\n"); 169360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(ret); 169460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(NULL); 169560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 169660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = temp; 169760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 169860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 169960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ch = *in; 170060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 170160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((ch != '@') && (!IS_UNRESERVED(ch)) && (!xmlStrchr(list, ch))) { 170260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott unsigned char val; 170360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[out++] = '%'; 170460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott val = ch >> 4; 170560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (val <= 9) 170660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[out++] = '0' + val; 170760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else 170860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[out++] = 'A' + val - 0xA; 170960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott val = ch & 0xF; 171060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (val <= 9) 171160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[out++] = '0' + val; 171260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else 171360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[out++] = 'A' + val - 0xA; 171460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott in++; 171560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } else { 171660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[out++] = *in++; 171760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 1718ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1719ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 172060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret[out] = 0; 172160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return(ret); 1722ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1723ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1724ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 172560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * xmlURIEscape: 172660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * @str: the string of the URI to escape 1727ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 172860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Escaping routine, does not do validity checks ! 172960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * It will try to escape the chars needing this, but this is heuristic 173060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * based it's impossible to be sure. 1731ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 173260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Returns an copy of the string, but escaped 173360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 173460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * 25 May 2001 173560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Uses xmlParseURI and xmlURIEscapeStr to try to escape correctly 173660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * according to RFC2396. 173760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * - Carl Douglas 1738ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 173960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlChar * 174060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick ScottxmlURIEscape(const xmlChar * str) 174160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott{ 174260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlChar *ret, *segment = NULL; 1743ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURIPtr uri; 174460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott int ret2; 174560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 174660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#define NULLCHK(p) if(!p) { \ 174794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("escaping URI value\n"); \ 174894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlFreeURI(uri); \ 174994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun return NULL; } \ 1750ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1751ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (str == NULL) 175260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (NULL); 175360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 1754ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uri = xmlCreateURI(); 1755ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (uri != NULL) { 175660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott /* 175760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott * Allow escaping errors in the unescaped form 175860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott */ 175960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott uri->cleanup = 1; 176060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret2 = xmlParseURIReference(uri, (const char *)str); 176160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (ret2) { 176260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFreeURI(uri); 176360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (NULL); 176460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 1765ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1766ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 176760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (!uri) 176860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return NULL; 1769ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 177060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = NULL; 177160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 177260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->scheme) { 177360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segment = xmlURIEscapeStr(BAD_CAST uri->scheme, BAD_CAST "+-."); 177460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NULLCHK(segment) 177560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, segment); 177660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST ":"); 177760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(segment); 1778ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 177960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 178060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->authority) { 178160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segment = 178260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlURIEscapeStr(BAD_CAST uri->authority, BAD_CAST "/?;:@"); 178360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NULLCHK(segment) 178460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST "//"); 178560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, segment); 178660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(segment); 178760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 178860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 178960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->user) { 179060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segment = xmlURIEscapeStr(BAD_CAST uri->user, BAD_CAST ";:&=+$,"); 179160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NULLCHK(segment) 179294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun ret = xmlStrcat(ret,BAD_CAST "//"); 179360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, segment); 179460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST "@"); 179560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(segment); 179660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 179760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 179860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->server) { 179960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segment = xmlURIEscapeStr(BAD_CAST uri->server, BAD_CAST "/?;:@"); 180060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NULLCHK(segment) 180160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->user == NULL) 180260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST "//"); 180360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, segment); 180460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(segment); 180560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 180660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 180760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->port) { 180860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlChar port[10]; 180960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 181060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott snprintf((char *) port, 10, "%d", uri->port); 181160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST ":"); 181260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, port); 181360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 181460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 181560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->path) { 181660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segment = 181760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlURIEscapeStr(BAD_CAST uri->path, BAD_CAST ":@&=+$,/?;"); 181860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NULLCHK(segment) 181960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, segment); 182060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(segment); 182160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 182260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 182360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->query_raw) { 182460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST "?"); 182560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST uri->query_raw); 182660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 182760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott else if (uri->query) { 182860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segment = 182960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlURIEscapeStr(BAD_CAST uri->query, BAD_CAST ";/?:@&=+,$"); 183060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NULLCHK(segment) 183160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST "?"); 183260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, segment); 183360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(segment); 183460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 183560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 183660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->opaque) { 183760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segment = xmlURIEscapeStr(BAD_CAST uri->opaque, BAD_CAST ""); 183860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NULLCHK(segment) 183960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, segment); 184060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(segment); 184160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 184260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 184360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if (uri->fragment) { 184460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott segment = xmlURIEscapeStr(BAD_CAST uri->fragment, BAD_CAST "#"); 184560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott NULLCHK(segment) 184660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, BAD_CAST "#"); 184760a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott ret = xmlStrcat(ret, segment); 184860a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFree(segment); 184960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott } 185060a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 185160a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott xmlFreeURI(uri); 185260a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott#undef NULLCHK 185360a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 185460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott return (ret); 1855ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 1856ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1857ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/************************************************************************ 1858ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * * 1859ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Public functions * 1860ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * * 1861ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ************************************************************************/ 1862ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1863ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 1864ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * xmlBuildURI: 1865ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * @URI: the URI instance found in the document 1866ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * @base: the base value 1867ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 1868ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Computes he final URI of the reference done by checking that 1869ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * the given URI is valid, and building the final URI using the 187094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * base URI. This is processed according to section 5.2 of the 1871ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * RFC 2396 1872ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 1873ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 5.2. Resolving Relative References to Absolute Form 1874ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 1875ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Returns a new URI string (to be freed by the caller) or NULL in case 1876ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * of error. 1877ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 1878ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlChar * 1879ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlBuildURI(const xmlChar *URI, const xmlChar *base) { 1880ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlChar *val = NULL; 1881ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int ret, len, indx, cur, out; 1882ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURIPtr ref = NULL; 1883ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURIPtr bas = NULL; 1884ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURIPtr res = NULL; 1885ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1886ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 1887ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 1) The URI reference is parsed into the potential four components and 1888ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * fragment identifier, as described in Section 4.3. 1889ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 1890ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * NOTE that a completely empty URI is treated by modern browsers 1891ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * as a reference to "." rather than as a synonym for the current 1892ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * URI. Should we do that here? 1893ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 189494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if (URI == NULL) 1895ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = -1; 1896ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else { 1897ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (*URI) { 1898ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ref = xmlCreateURI(); 1899ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref == NULL) 1900ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 1901ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = xmlParseURIReference(ref, (const char *) URI); 1902ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1903ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else 1904ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = 0; 1905ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1906ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ret != 0) 1907ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 1908ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((ref != NULL) && (ref->scheme != NULL)) { 1909ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 1910ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * The URI is absolute don't modify. 1911ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 1912ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlStrdup(URI); 1913ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 1914ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1915ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (base == NULL) 1916ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = -1; 1917ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else { 1918ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project bas = xmlCreateURI(); 1919ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas == NULL) 1920ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 1921ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = xmlParseURIReference(bas, (const char *) base); 1922ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1923ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ret != 0) { 1924ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref) 1925ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlSaveUri(ref); 1926ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 1927ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1928ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref == NULL) { 1929ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 1930ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * the base fragment must be ignored 1931ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 1932ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->fragment != NULL) { 1933ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFree(bas->fragment); 1934ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project bas->fragment = NULL; 1935ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1936ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlSaveUri(bas); 1937ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 1938ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1939ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1940ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 1941ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2) If the path component is empty and the scheme, authority, and 1942ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * query components are undefined, then it is a reference to the 1943ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * current document and we are done. Otherwise, the reference URI's 1944ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * query and fragment components are defined as found (or not found) 1945ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * within the URI reference and not inherited from the base URI. 1946ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 1947ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * NOTE that in modern browsers, the parsing differs from the above 1948ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * in the following aspect: the query component is allowed to be 1949ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * defined while still treating this as a reference to the current 1950ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * document. 1951ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 1952ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res = xmlCreateURI(); 1953ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (res == NULL) 1954ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 1955ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((ref->scheme == NULL) && (ref->path == NULL) && 1956ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ((ref->authority == NULL) && (ref->server == NULL))) { 1957ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->scheme != NULL) 1958ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->scheme = xmlMemStrdup(bas->scheme); 1959ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->authority != NULL) 1960ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->authority = xmlMemStrdup(bas->authority); 1961ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else if (bas->server != NULL) { 1962ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->server = xmlMemStrdup(bas->server); 1963ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->user != NULL) 1964ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->user = xmlMemStrdup(bas->user); 196594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun res->port = bas->port; 1966ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1967ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->path != NULL) 1968ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path = xmlMemStrdup(bas->path); 1969ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->query_raw != NULL) 1970ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->query_raw = xmlMemStrdup (ref->query_raw); 1971ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else if (ref->query != NULL) 1972ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->query = xmlMemStrdup(ref->query); 1973ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else if (bas->query_raw != NULL) 1974ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->query_raw = xmlMemStrdup(bas->query_raw); 1975ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else if (bas->query != NULL) 1976ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->query = xmlMemStrdup(bas->query); 1977ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->fragment != NULL) 1978ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->fragment = xmlMemStrdup(ref->fragment); 1979ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto step_7; 1980ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1981ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 1982ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 1983ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 3) If the scheme component is defined, indicating that the reference 1984ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * starts with a scheme name, then the reference is interpreted as an 1985ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * absolute URI and we are done. Otherwise, the reference URI's 1986ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * scheme is inherited from the base URI's scheme component. 1987ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 1988ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->scheme != NULL) { 1989ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlSaveUri(ref); 1990ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 1991ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 1992ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->scheme != NULL) 1993ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->scheme = xmlMemStrdup(bas->scheme); 199494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun 1995ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->query_raw != NULL) 1996ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->query_raw = xmlMemStrdup(ref->query_raw); 1997ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else if (ref->query != NULL) 1998ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->query = xmlMemStrdup(ref->query); 1999ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->fragment != NULL) 2000ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->fragment = xmlMemStrdup(ref->fragment); 2001ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2002ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2003ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 4) If the authority component is defined, then the reference is a 2004ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * network-path and we skip to step 7. Otherwise, the reference 2005ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * URI's authority is inherited from the base URI's authority 2006ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * component, which will also be undefined if the URI scheme does not 2007ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * use an authority component. 2008ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2009ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((ref->authority != NULL) || (ref->server != NULL)) { 2010ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->authority != NULL) 2011ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->authority = xmlMemStrdup(ref->authority); 2012ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else { 2013ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->server = xmlMemStrdup(ref->server); 2014ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->user != NULL) 2015ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->user = xmlMemStrdup(ref->user); 201694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun res->port = ref->port; 2017ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2018ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->path != NULL) 2019ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path = xmlMemStrdup(ref->path); 2020ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto step_7; 2021ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2022ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->authority != NULL) 2023ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->authority = xmlMemStrdup(bas->authority); 2024ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else if (bas->server != NULL) { 2025ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->server = xmlMemStrdup(bas->server); 2026ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->user != NULL) 2027ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->user = xmlMemStrdup(bas->user); 202894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun res->port = bas->port; 2029ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2030ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2031ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2032ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 5) If the path component begins with a slash character ("/"), then 2033ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * the reference is an absolute-path and we skip to step 7. 2034ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2035ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((ref->path != NULL) && (ref->path[0] == '/')) { 2036ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path = xmlMemStrdup(ref->path); 2037ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto step_7; 2038ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2039ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2040ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2041ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2042ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 6) If this step is reached, then we are resolving a relative-path 2043ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * reference. The relative path needs to be merged with the base 2044ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * URI's path. Although there are many ways to do this, we will 2045ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * describe a simple method using a separate string buffer. 2046ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2047ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Allocate a buffer large enough for the result string. 2048ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2049ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project len = 2; /* extra / and 0 */ 2050ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->path != NULL) 2051ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project len += strlen(ref->path); 2052ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->path != NULL) 2053ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project len += strlen(bas->path); 2054ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path = (char *) xmlMallocAtomic(len); 2055ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (res->path == NULL) { 205694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("resolving URI against base\n"); 2057ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2058ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2059ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path[0] = 0; 2060ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2061ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2062ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * a) All but the last segment of the base URI's path component is 2063ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * copied to the buffer. In other words, any characters after the 2064ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * last (right-most) slash character, if any, are excluded. 2065ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2066ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project cur = 0; 2067ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project out = 0; 2068ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->path != NULL) { 2069ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project while (bas->path[cur] != 0) { 2070ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project while ((bas->path[cur] != 0) && (bas->path[cur] != '/')) 2071ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project cur++; 2072ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->path[cur] == 0) 2073ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project break; 2074ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2075ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project cur++; 2076ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project while (out < cur) { 2077ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path[out] = bas->path[out]; 2078ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project out++; 2079ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2080ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2081ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2082ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path[out] = 0; 2083ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2084ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2085ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * b) The reference's path component is appended to the buffer 2086ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * string. 2087ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2088ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->path != NULL && ref->path[0] != 0) { 2089ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project indx = 0; 2090ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2091ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Ensure the path includes a '/' 2092ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2093ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((out == 0) && (bas->server != NULL)) 2094ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path[out++] = '/'; 2095ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project while (ref->path[indx] != 0) { 2096ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path[out++] = ref->path[indx++]; 2097ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2098ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2099ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project res->path[out] = 0; 2100ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2101ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2102ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Steps c) to h) are really path normalization steps 2103ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2104ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlNormalizeURIPath(res->path); 2105ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2106ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Projectstep_7: 2107ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2108ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2109ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 7) The resulting URI components, including any inherited from the 2110ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * base URI, are recombined to give the absolute form of the URI 2111ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * reference. 2112ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2113ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlSaveUri(res); 2114ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2115ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Projectdone: 2116ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref != NULL) 2117ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(ref); 2118ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas != NULL) 2119ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(bas); 2120ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (res != NULL) 2121ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(res); 2122ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(val); 2123ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 2124ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2125ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 2126ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * xmlBuildRelativeURI: 2127ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * @URI: the URI reference under consideration 2128ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * @base: the base value 2129ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2130ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Expresses the URI of the reference in terms relative to the 2131ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * base. Some examples of this operation include: 2132ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * base = "http://site1.com/docs/book1.html" 2133ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * URI input URI returned 2134ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * docs/pic1.gif pic1.gif 2135ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * docs/img/pic1.gif img/pic1.gif 2136ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * img/pic1.gif ../img/pic1.gif 2137ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * http://site1.com/docs/pic1.gif pic1.gif 2138ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * http://site2.com/docs/pic1.gif http://site2.com/docs/pic1.gif 2139ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2140ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * base = "docs/book1.html" 2141ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * URI input URI returned 2142ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * docs/pic1.gif pic1.gif 2143ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * docs/img/pic1.gif img/pic1.gif 2144ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * img/pic1.gif ../img/pic1.gif 2145ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * http://site1.com/docs/pic1.gif http://site1.com/docs/pic1.gif 2146ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2147ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2148ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Note: if the URI reference is really wierd or complicated, it may be 2149ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * worthwhile to first convert it into a "nice" one by calling 2150ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * xmlBuildURI (using 'base') before calling this routine, 2151ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * since this routine (for reasonable efficiency) assumes URI has 2152ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * already been through some validation. 2153ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2154ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Returns a new URI string (to be freed by the caller) or NULL in case 2155ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * error. 2156ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2157ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlChar * 2158ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlBuildRelativeURI (const xmlChar * URI, const xmlChar * base) 2159ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project{ 2160ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlChar *val = NULL; 2161ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int ret; 2162ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int ix; 2163ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int pos = 0; 2164ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int nbslash = 0; 2165ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int len; 2166ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURIPtr ref = NULL; 2167ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURIPtr bas = NULL; 2168ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlChar *bptr, *uptr, *vptr; 2169ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int remove_path = 0; 2170ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2171ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((URI == NULL) || (*URI == 0)) 2172ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return NULL; 2173ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2174ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2175ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * First parse URI into a standard form 2176ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2177ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ref = xmlCreateURI (); 2178ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref == NULL) 2179ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return NULL; 2180ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* If URI not already in "relative" form */ 2181ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (URI[0] != '.') { 2182ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = xmlParseURIReference (ref, (const char *) URI); 2183ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ret != 0) 2184ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; /* Error in URI, return NULL */ 2185ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } else 2186ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ref->path = (char *)xmlStrdup(URI); 2187ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2188ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2189ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Next parse base into the same standard form 2190ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2191ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((base == NULL) || (*base == 0)) { 2192ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlStrdup (URI); 2193ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2194ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2195ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project bas = xmlCreateURI (); 2196ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas == NULL) 2197ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2198ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (base[0] != '.') { 2199ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = xmlParseURIReference (bas, (const char *) base); 2200ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ret != 0) 2201ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; /* Error in base, return NULL */ 2202ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } else 2203ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project bas->path = (char *)xmlStrdup(base); 2204ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2205ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2206ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * If the scheme / server on the URI differs from the base, 2207ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * just return the URI 2208ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2209ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((ref->scheme != NULL) && 2210ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ((bas->scheme == NULL) || 2211ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project (xmlStrcmp ((xmlChar *)bas->scheme, (xmlChar *)ref->scheme)) || 2212ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project (xmlStrcmp ((xmlChar *)bas->server, (xmlChar *)ref->server)))) { 2213ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlStrdup (URI); 2214ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2215ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2216ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (xmlStrEqual((xmlChar *)bas->path, (xmlChar *)ref->path)) { 2217ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlStrdup(BAD_CAST ""); 2218ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2219ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2220ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->path == NULL) { 2221ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlStrdup((xmlChar *)ref->path); 2222ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2223ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2224ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->path == NULL) { 2225ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ref->path = (char *) "/"; 2226ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project remove_path = 1; 2227ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2228ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2229ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2230ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * At this point (at last!) we can compare the two paths 2231ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2232ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * First we take care of the special case where either of the 2233ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * two path components may be missing (bug 316224) 2234ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2235ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas->path == NULL) { 2236ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->path != NULL) { 2237ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uptr = (xmlChar *) ref->path; 2238ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (*uptr == '/') 2239ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uptr++; 2240ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* exception characters from xmlSaveUri */ 2241ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlURIEscapeStr(uptr, BAD_CAST "/;&=+$,"); 2242ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2243ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2244ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2245ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project bptr = (xmlChar *)bas->path; 2246ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->path == NULL) { 2247ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project for (ix = 0; bptr[ix] != 0; ix++) { 2248ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bptr[ix] == '/') 2249ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project nbslash++; 2250ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2251ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uptr = NULL; 2252ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project len = 1; /* this is for a string terminator only */ 2253ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } else { 2254ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2255ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Next we compare the two strings and find where they first differ 2256ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2257ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((ref->path[pos] == '.') && (ref->path[pos+1] == '/')) 2258ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project pos += 2; 2259ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((*bptr == '.') && (bptr[1] == '/')) 2260ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project bptr += 2; 2261ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else if ((*bptr == '/') && (ref->path[pos] != '/')) 2262ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project bptr++; 2263ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project while ((bptr[pos] == ref->path[pos]) && (bptr[pos] != 0)) 2264ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project pos++; 2265ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2266ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bptr[pos] == ref->path[pos]) { 2267ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlStrdup(BAD_CAST ""); 2268ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; /* (I can't imagine why anyone would do this) */ 2269ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2270ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2271ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2272ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * In URI, "back up" to the last '/' encountered. This will be the 2273ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * beginning of the "unique" suffix of URI 2274ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2275ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ix = pos; 2276ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((ref->path[ix] == '/') && (ix > 0)) 2277ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ix--; 2278ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project else if ((ref->path[ix] == 0) && (ix > 1) && (ref->path[ix - 1] == '/')) 2279ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ix -= 2; 2280ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project for (; ix > 0; ix--) { 2281ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref->path[ix] == '/') 2282ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project break; 2283ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2284ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ix == 0) { 2285ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uptr = (xmlChar *)ref->path; 2286ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } else { 2287ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ix++; 2288ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uptr = (xmlChar *)&ref->path[ix]; 2289ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2290ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2291ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2292ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * In base, count the number of '/' from the differing point 2293ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2294ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bptr[pos] != ref->path[pos]) {/* check for trivial URI == base */ 2295ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project for (; bptr[ix] != 0; ix++) { 2296ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bptr[ix] == '/') 2297ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project nbslash++; 2298ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2299ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2300ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project len = xmlStrlen (uptr) + 1; 2301ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 230294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun 2303ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (nbslash == 0) { 2304ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (uptr != NULL) 2305ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* exception characters from xmlSaveUri */ 2306ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlURIEscapeStr(uptr, BAD_CAST "/;&=+$,"); 2307ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2308ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2309ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2310ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2311ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Allocate just enough space for the returned string - 2312ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * length of the remainder of the URI, plus enough space 2313ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * for the "../" groups, plus one for the terminator 2314ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2315ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = (xmlChar *) xmlMalloc (len + 3 * nbslash); 2316ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (val == NULL) { 231794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun xmlURIErrMemory("building relative URI\n"); 2318ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto done; 2319ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2320ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project vptr = val; 2321ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2322ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Put in as many "../" as needed 2323ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2324ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project for (; nbslash>0; nbslash--) { 2325ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project *vptr++ = '.'; 2326ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project *vptr++ = '.'; 2327ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project *vptr++ = '/'; 2328ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2329ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2330ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Finish up with the end of the URI 2331ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2332ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (uptr != NULL) { 2333ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((vptr > val) && (len > 0) && 2334ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project (uptr[0] == '/') && (vptr[-1] == '/')) { 2335ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project memcpy (vptr, uptr + 1, len - 1); 2336ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project vptr[len - 2] = 0; 2337ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } else { 2338ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project memcpy (vptr, uptr, len); 2339ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project vptr[len - 1] = 0; 2340ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2341ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } else { 2342ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project vptr[len - 1] = 0; 2343ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2344ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2345ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* escape the freshly-built path */ 2346ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project vptr = val; 2347ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* exception characters from xmlSaveUri */ 2348ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project val = xmlURIEscapeStr(vptr, BAD_CAST "/;&=+$,"); 2349ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFree(vptr); 2350ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2351ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Projectdone: 2352ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2353ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Free the working variables 2354ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2355ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (remove_path != 0) 2356ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ref->path = NULL; 2357ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (ref != NULL) 2358ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI (ref); 2359ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (bas != NULL) 2360ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI (bas); 2361ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2362ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return val; 2363ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 2364ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2365ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 2366ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * xmlCanonicPath: 2367ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * @path: the resource locator in a filesystem notation 2368ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 236994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * Constructs a canonic path from the specified path. 2370ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 237194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * Returns a new canonic path, or a duplicate of the path parameter if the 2372ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * construction fails. The caller is responsible for freeing the memory occupied 237394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * by the returned string. If there is insufficient memory available, or the 2374ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * argument is NULL, the function returns NULL. 2375ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 237694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun#define IS_WINDOWS_PATH(p) \ 2377ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ((p != NULL) && \ 2378ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project (((p[0] >= 'a') && (p[0] <= 'z')) || \ 2379ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ((p[0] >= 'A') && (p[0] <= 'Z'))) && \ 2380ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project (p[1] == ':') && ((p[2] == '/') || (p[2] == '\\'))) 2381ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlChar * 2382ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlCanonicPath(const xmlChar *path) 2383ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project{ 2384ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* 2385ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * For Windows implementations, additional work needs to be done to 2386ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * replace backslashes in pathnames with "forward slashes" 2387ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 238894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun#if defined(_WIN32) && !defined(__CYGWIN__) 2389ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int len = 0; 2390ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int i = 0; 2391ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlChar *p = NULL; 2392ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#endif 2393ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURIPtr uri; 2394ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlChar *ret; 2395ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project const xmlChar *absuri; 2396ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2397ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (path == NULL) 2398ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(NULL); 239960a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 240094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun#if defined(_WIN32) 240194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun /* 240294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * We must not change the backslashes to slashes if the the path 240394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * starts with \\?\ 240494442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * Those paths can be up to 32k characters long. 240594442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * Was added specifically for OpenOffice, those paths can't be converted 240694442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * to URIs anyway. 240794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun */ 240894442ad4107000e6d49f9b85a46a591495a57632Selim Gurun if ((path[0] == '\\') && (path[1] == '\\') && (path[2] == '?') && 240994442ad4107000e6d49f9b85a46a591495a57632Selim Gurun (path[3] == '\\') ) 241094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun return xmlStrdup((const xmlChar *) path); 241194442ad4107000e6d49f9b85a46a591495a57632Selim Gurun#endif 241294442ad4107000e6d49f9b85a46a591495a57632Selim Gurun 241394442ad4107000e6d49f9b85a46a591495a57632Selim Gurun /* sanitize filename starting with // so it can be used as URI */ 241460a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott if ((path[0] == '/') && (path[1] == '/') && (path[2] != '/')) 241560a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott path++; 241660a4c356ee9ce5e9ccb23347c0381f0436192691Patrick Scott 2417ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((uri = xmlParseURI((const char *) path)) != NULL) { 2418ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(uri); 2419ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return xmlStrdup(path); 2420ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2421ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2422ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* Check if this is an "absolute uri" */ 2423ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project absuri = xmlStrstr(path, BAD_CAST "://"); 2424ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (absuri != NULL) { 2425ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project int l, j; 2426ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project unsigned char c; 2427ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlChar *escURI; 2428ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2429ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2430ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * this looks like an URI where some parts have not been 2431ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * escaped leading to a parsing problem. Check that the first 2432ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * part matches a protocol. 2433ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2434ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project l = absuri - path; 2435ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* Bypass if first part (part before the '://') is > 20 chars */ 2436ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((l <= 0) || (l > 20)) 2437ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto path_processing; 2438ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* Bypass if any non-alpha characters are present in first part */ 2439ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project for (j = 0;j < l;j++) { 2440ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project c = path[j]; 2441ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (!(((c >= 'a') && (c <= 'z')) || ((c >= 'A') && (c <= 'Z')))) 2442ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project goto path_processing; 2443ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2444ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2445ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* Escape all except the characters specified in the supplied path */ 2446ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project escURI = xmlURIEscapeStr(path, BAD_CAST ":/?_.#&;="); 2447ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (escURI != NULL) { 2448ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* Try parsing the escaped path */ 2449ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uri = xmlParseURI((const char *) escURI); 2450ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* If successful, return the escaped string */ 2451ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (uri != NULL) { 2452ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(uri); 2453ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return escURI; 2454ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2455ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2456ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2457ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2458ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Projectpath_processing: 2459ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/* For Windows implementations, replace backslashes with 'forward slashes' */ 246094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun#if defined(_WIN32) && !defined(__CYGWIN__) 2461ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 2462ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Create a URI structure 2463ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2464ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uri = xmlCreateURI(); 2465ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (uri == NULL) { /* Guard against 'out of memory' */ 2466ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(NULL); 2467ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2468ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2469ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project len = xmlStrlen(path); 2470ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((len > 2) && IS_WINDOWS_PATH(path)) { 2471ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* make the scheme 'file' */ 2472ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uri->scheme = xmlStrdup(BAD_CAST "file"); 2473ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* allocate space for leading '/' + path + string terminator */ 2474ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uri->path = xmlMallocAtomic(len + 2); 2475ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (uri->path == NULL) { 2476ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(uri); /* Guard agains 'out of memory' */ 2477ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(NULL); 2478ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2479ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* Put in leading '/' plus path */ 2480ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uri->path[0] = '/'; 2481ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project p = uri->path + 1; 2482ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project strncpy(p, path, len + 1); 2483ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } else { 2484ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project uri->path = xmlStrdup(path); 2485ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (uri->path == NULL) { 2486ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(uri); 2487ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(NULL); 2488ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2489ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project p = uri->path; 2490ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2491ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* Now change all occurences of '\' to '/' */ 2492ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project while (*p != '\0') { 2493ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (*p == '\\') 2494ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project *p = '/'; 2495ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project p++; 2496ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2497ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2498ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (uri->scheme == NULL) { 2499ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = xmlStrdup((const xmlChar *) uri->path); 2500ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } else { 2501ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = xmlSaveUri(uri); 2502ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2503ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2504ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(uri); 2505ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#else 2506ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = xmlStrdup((const xmlChar *) path); 2507ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#endif 2508ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(ret); 2509ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 2510ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2511ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project/** 2512ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * xmlPathToURI: 2513ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * @path: the resource locator in a filesystem notation 2514ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 2515ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * Constructs an URI expressing the existing path 2516ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * 251794442ad4107000e6d49f9b85a46a591495a57632Selim Gurun * Returns a new URI, or a duplicate of the path parameter if the 2518ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * construction fails. The caller is responsible for freeing the memory 2519ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * occupied by the returned string. If there is insufficient memory available, 2520ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project * or the argument is NULL, the function returns NULL. 2521ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project */ 2522ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlChar * 2523ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source ProjectxmlPathToURI(const xmlChar *path) 2524ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project{ 2525ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURIPtr uri; 2526ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlURI temp; 2527ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlChar *ret, *cal; 2528ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2529ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (path == NULL) 2530ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(NULL); 2531ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project 2532ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((uri = xmlParseURI((const char *) path)) != NULL) { 2533ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(uri); 2534ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return xmlStrdup(path); 2535ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2536ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project cal = xmlCanonicPath(path); 2537ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (cal == NULL) 2538ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(NULL); 2539ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#if defined(_WIN32) && !defined(__CYGWIN__) 254094442ad4107000e6d49f9b85a46a591495a57632Selim Gurun /* xmlCanonicPath can return an URI on Windows (is that the intended behaviour?) 2541ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project If 'cal' is a valid URI allready then we are done here, as continuing would make 2542ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project it invalid. */ 2543ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if ((uri = xmlParseURI((const char *) cal)) != NULL) { 2544ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFreeURI(uri); 2545ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return cal; 2546ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2547ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project /* 'cal' can contain a relative path with backslashes. If that is processed 2548ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project by xmlSaveURI, they will be escaped and the external entity loader machinery 2549ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project will fail. So convert them to slashes. Misuse 'ret' for walking. */ 2550ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = cal; 2551ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project while (*ret != '\0') { 2552ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project if (*ret == '\\') 2553ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project *ret = '/'; 2554ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret++; 2555ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project } 2556ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#endif 2557ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project memset(&temp, 0, sizeof(temp)); 2558ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project temp.path = (char *) cal; 2559ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project ret = xmlSaveUri(&temp); 2560ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project xmlFree(cal); 2561ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project return(ret); 2562ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project} 2563ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#define bottom_uri 2564ab4e2e90f63db6b1cd8bb2e453cac899ef43d42bThe Android Open Source Project#include "elfgcchack.h" 2565