Mercurial > hg > index.fcgi > gift-gnutella > gift-gnutella-0.0.11-1pba
diff src/encoding/url.c @ 0:d39e1d0d75b6
initial add
author | paulo@hit-nxdomain.opendns.com |
---|---|
date | Sat, 20 Feb 2010 21:18:28 -0800 |
parents | |
children |
line diff
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/src/encoding/url.c Sat Feb 20 21:18:28 2010 -0800 1.3 @@ -0,0 +1,169 @@ 1.4 +/* 1.5 + * $Id: url.c,v 1.1 2004/03/24 06:34:36 hipnod Exp $ 1.6 + * 1.7 + * Copyright (C) 2001-2003 giFT project (gift.sourceforge.net) 1.8 + * 1.9 + * This program is free software; you can redistribute it and/or modify it 1.10 + * under the terms of the GNU General Public License as published by the 1.11 + * Free Software Foundation; either version 2, or (at your option) any 1.12 + * later version. 1.13 + * 1.14 + * This program is distributed in the hope that it will be useful, but 1.15 + * WITHOUT ANY WARRANTY; without even the implied warranty of 1.16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 1.17 + * General Public License for more details. 1.18 + */ 1.19 + 1.20 +#include "gt_gnutella.h" 1.21 +#include "encoding/url.h" 1.22 + 1.23 +#include <ctype.h> 1.24 + 1.25 +/*****************************************************************************/ 1.26 +/* url decode/encode helpers */ 1.27 + 1.28 +static int oct_value_from_hex (char hex_char) 1.29 +{ 1.30 + if (!isxdigit (hex_char)) 1.31 + return 0; 1.32 + 1.33 + if (hex_char >= '0' && hex_char <= '9') 1.34 + return (hex_char - '0'); 1.35 + 1.36 + hex_char = toupper (hex_char); 1.37 + 1.38 + return ((hex_char - 'A') + 10); 1.39 +} 1.40 + 1.41 +char *gt_url_decode (const char *encoded) 1.42 +{ 1.43 + char *decoded, *ptr; 1.44 + 1.45 + if (!encoded) 1.46 + return NULL; 1.47 + 1.48 + /* make sure we are using our own memory here ... */ 1.49 + ptr = strdup (encoded); 1.50 + 1.51 + /* save the head */ 1.52 + decoded = ptr; 1.53 + 1.54 + /* convert '+' -> ' ' and %2x -> char value */ 1.55 + while (*ptr) 1.56 + { 1.57 + switch (*ptr) 1.58 + { 1.59 + case '+': 1.60 + *ptr = ' '; 1.61 + break; 1.62 + case '%': 1.63 + if (isxdigit (ptr[1]) && isxdigit (ptr[2])) 1.64 + { 1.65 + int oct_val; 1.66 + 1.67 + oct_val = oct_value_from_hex (ptr[1]) * 16; 1.68 + oct_val += oct_value_from_hex (ptr[2]); 1.69 + 1.70 + *ptr = (char) oct_val; 1.71 + 1.72 + string_move (ptr + 1, ptr + 3); 1.73 + } 1.74 + break; 1.75 + default: 1.76 + break; 1.77 + } 1.78 + 1.79 + ptr++; 1.80 + } 1.81 + 1.82 + return decoded; 1.83 +} 1.84 + 1.85 +static char *gt_url_encode_char (char *stream, unsigned char c) 1.86 +{ 1.87 + const char hex_alpha[] = "0123456789abcdef"; 1.88 + 1.89 + *stream++ = '%'; 1.90 + 1.91 + *stream++ = hex_alpha[(c & 0xf0) >> 4]; 1.92 + *stream++ = hex_alpha[(c & 0x0f)]; 1.93 + 1.94 + return stream; 1.95 +} 1.96 + 1.97 +/* 1.98 + * This is a bit overzealous about what to encode..hopefully that's ok. This 1.99 + * escapes path components ('/'). 1.100 + */ 1.101 +static BOOL is_safe_char (unsigned char c) 1.102 +{ 1.103 + if (c >= 'A' && c <= 'Z') 1.104 + return TRUE; 1.105 + 1.106 + if (c >= 'a' && c <= 'z') 1.107 + return TRUE; 1.108 + 1.109 + if (c >= '0' && c <= '9') 1.110 + return TRUE; 1.111 + 1.112 + switch (c) 1.113 + { 1.114 + case '-': 1.115 + case '.': 1.116 + case '_': 1.117 + return TRUE; 1.118 + default: 1.119 + return FALSE; 1.120 + } 1.121 + 1.122 + return FALSE; 1.123 +} 1.124 + 1.125 +char *gt_url_encode (const char *decoded) 1.126 +{ 1.127 + char *encoded, *ptr; 1.128 + unsigned char chr; 1.129 + 1.130 + if (!decoded) 1.131 + return NULL; 1.132 + 1.133 + /* allocate a large enough buffer for all cases */ 1.134 + encoded = ptr = malloc ((strlen (decoded) * 3) + 1); 1.135 + 1.136 + while ((chr = *decoded) != 0) 1.137 + { 1.138 + if (is_safe_char (chr)) 1.139 + *ptr++ = chr; 1.140 + else 1.141 + ptr = gt_url_encode_char (ptr, chr); 1.142 + 1.143 + decoded++; 1.144 + } 1.145 + 1.146 + *ptr = 0; 1.147 + 1.148 + return encoded; 1.149 +} 1.150 + 1.151 +/*****************************************************************************/ 1.152 + 1.153 +#if 0 1.154 +int main (int argc, char **argv) 1.155 +{ 1.156 + int i; 1.157 + 1.158 + for (i = 1; i < argc; i++) 1.159 + { 1.160 + char *enc, *dec; 1.161 + 1.162 + enc = gt_url_encode (argv[i]); 1.163 + dec = gt_url_decode (enc); 1.164 + 1.165 + printf ("%s\n%s\n%s\n", argv[i], enc, dec); 1.166 + 1.167 + assert (strcmp (argv[i], dec) == 0); 1.168 + } 1.169 + 1.170 + return 0; 1.171 +} 1.172 +#endif