1/* Licensed to the Apache Software Foundation (ASF) under one or more 2 * contributor license agreements. See the NOTICE file distributed with 3 * this work for additional information regarding copyright ownership. 4 * The ASF licenses this file to You under the Apache License, Version 2.0 5 * (the "License"); you may not use this file except in compliance with 6 * the License. You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16/** 17 * @file apr_escape.h 18 * @brief APR-UTIL Escaping 19 */ 20#ifndef APR_ESCAPE_H 21#define APR_ESCAPE_H 22#include "apr.h" 23#include "apr_general.h" 24#ifdef __cplusplus 25extern "C" { 26#endif 27 28/** 29 * @defgroup APR_Util_Escaping Escape functions 30 * @ingroup APR 31 * @{ 32 */ 33 34/* Simple escape/unescape functions. 35 * 36 * The design goal of these functions are: 37 * 38 * - Avoid unnecessary work. 39 * 40 * In most cases the strings passed in do not need to be escaped at all. In 41 * these cases the original string will be returned. 42 * 43 * - Lowest possible memory footprint. 44 * 45 * The amount of memory allocated for a given encoding is calculated based 46 * on the exact amount of memory needed, and not the theoretical worst case 47 * scenario. 48 * 49 */ 50 51/** 52 * When passing a string to one of the escape functions, this value can be 53 * passed to indicate a string-valued key, and have the length computed 54 * automatically. 55 */ 56#define APR_ESCAPE_STRING (-1) 57 58/** 59 * Apply LDAP distinguished name escaping as per RFC4514. 60 */ 61#define APR_ESCAPE_LDAP_DN (0x01) 62 63/** 64 * Apply LDAP filter escaping as per RFC4515. 65 */ 66#define APR_ESCAPE_LDAP_FILTER (0x02) 67 68/** 69 * Apply both RFC4514 and RFC4515 LDAP escaping. 70 */ 71#define APR_ESCAPE_LDAP_ALL (0x03) 72 73/** 74 * Perform shell escaping on the provided string. 75 * 76 * Shell escaping causes characters to be prefixed with a '\' character. 77 * @param escaped Optional buffer to write the encoded string, can be 78 * NULL 79 * @param str The original string 80 * @param slen The length of the original string, or APR_ESCAPE_STRING 81 * @param len If present, returns the length of the string 82 * @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were 83 * detected or the string was NULL 84 */ 85APR_DECLARE(apr_status_t) apr_escape_shell(char *escaped, const char *str, 86 apr_ssize_t slen, apr_size_t *len); 87 88/** 89 * Perform shell escaping on the provided string, returning the result 90 * from the pool. 91 * 92 * Shell escaping causes characters to be prefixed with a '\' character. 93 * 94 * If no characters were escaped, the original string is returned. 95 * @param p Pool to allocate from 96 * @param str The original string 97 * @return the encoded string, allocated from the pool, or the original 98 * string if no escaping took place or the string was NULL. 99 */ 100APR_DECLARE(const char *) apr_pescape_shell(apr_pool_t *p, const char *str) 101 __attribute__((nonnull(1))); 102 103/** 104 * Unescapes a URL, leaving reserved characters intact. 105 * @param escaped Optional buffer to write the encoded string, can be 106 * NULL 107 * @param url String to be unescaped 108 * @param slen The length of the original url, or APR_ESCAPE_STRING 109 * @param forbid Optional list of forbidden characters, in addition to 110 * 0x00 111 * @param reserved Optional list of reserved characters that will be 112 * left unescaped 113 * @param plus If non zero, '+' is converted to ' ' as per 114 * application/x-www-form-urlencoded encoding 115 * @param len If set, the length of the escaped string will be returned 116 * @return APR_SUCCESS on success, APR_NOTFOUND if no characters are 117 * decoded or the string is NULL, APR_EINVAL if a bad escape sequence is 118 * found, APR_BADCH if a character on the forbid list is found. 119 */ 120APR_DECLARE(apr_status_t) apr_unescape_url(char *escaped, const char *url, 121 apr_ssize_t slen, const char *forbid, const char *reserved, int plus, 122 apr_size_t *len); 123 124/** 125 * Unescapes a URL, leaving reserved characters intact, returning the 126 * result from a pool. 127 * @param p Pool to allocate from 128 * @param url String to be unescaped in place 129 * @param forbid Optional list of forbidden characters, in addition to 130 * 0x00 131 * @param reserved Optional list of reserved characters that will be 132 * left unescaped 133 * @param plus If non zero, '+' is converted to ' ' as per 134 * application/x-www-form-urlencoded encoding 135 * @return A string allocated from the pool on success, the original string 136 * if no characters are decoded, or NULL if a bad escape sequence is found 137 * or if a character on the forbid list is found, or if the original string 138 * was NULL. 139 */ 140APR_DECLARE(const char *) apr_punescape_url(apr_pool_t *p, const char *url, 141 const char *forbid, const char *reserved, int plus) 142 __attribute__((nonnull(1))); 143 144/** 145 * Escape a path segment, as defined in RFC1808. 146 * @param escaped Optional buffer to write the encoded string, can be 147 * NULL 148 * @param str The original string 149 * @param slen The length of the original string, or APR_ESCAPE_STRING 150 * @param len If present, returns the length of the string 151 * @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were 152 * detected or the string was NULL 153 */ 154APR_DECLARE(apr_status_t) apr_escape_path_segment(char *escaped, 155 const char *str, apr_ssize_t slen, apr_size_t *len); 156 157/** 158 * Escape a path segment, as defined in RFC1808, returning the result from a 159 * pool. 160 * @param p Pool to allocate from 161 * @param str String to be escaped 162 * @return A string allocated from the pool on success, the original string 163 * if no characters are encoded or the string is NULL. 164 */ 165APR_DECLARE(const char *) apr_pescape_path_segment(apr_pool_t *p, 166 const char *str) __attribute__((nonnull(1))); 167 168/** 169 * Converts an OS path to a URL, in an OS dependent way, as defined in RFC1808. 170 * In all cases if a ':' occurs before the first '/' in the URL, the URL should 171 * be prefixed with "./" (or the ':' escaped). In the case of Unix, this means 172 * leaving '/' alone, but otherwise doing what escape_path_segment() does. For 173 * efficiency reasons, we don't use escape_path_segment(), which is provided for 174 * reference. Again, RFC 1808 is where this stuff is defined. 175 * 176 * If partial is set, os_escape_path() assumes that the path will be appended to 177 * something with a '/' in it (and thus does not prefix "./"). 178 * @param escaped Optional buffer to write the encoded string, can be 179 * NULL 180 * @param path The original string 181 * @param slen The length of the original string, or APR_ESCAPE_STRING 182 * @param partial If non zero, suppresses the prepending of "./" 183 * @param len If present, returns the length of the string 184 * @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were 185 * detected or if the string was NULL 186 */ 187APR_DECLARE(apr_status_t) apr_escape_path(char *escaped, const char *path, 188 apr_ssize_t slen, int partial, apr_size_t *len); 189 190/** 191 * Converts an OS path to a URL, in an OS dependent way, as defined in RFC1808, 192 * returning the result from a pool. 193 * 194 * In all cases if a ':' occurs before the first '/' in the URL, the URL should 195 * be prefixed with "./" (or the ':' escaped). In the case of Unix, this means 196 * leaving '/' alone, but otherwise doing what escape_path_segment() does. For 197 * efficiency reasons, we don't use escape_path_segment(), which is provided for 198 * reference. Again, RFC 1808 is where this stuff is defined. 199 * 200 * If partial is set, os_escape_path() assumes that the path will be appended to 201 * something with a '/' in it (and thus does not prefix "./"). 202 * @param p Pool to allocate from 203 * @param str The original string 204 * @param partial If non zero, suppresses the prepending of "./" 205 * @return A string allocated from the pool on success, the original string 206 * if no characters are encoded or if the string was NULL. 207 */ 208APR_DECLARE(const char *) apr_pescape_path(apr_pool_t *p, const char *str, 209 int partial) __attribute__((nonnull(1))); 210 211/** 212 * Urlencode a string, as defined in 213 * http://www.w3.org/TR/html401/interact/forms.html#h-17.13.4.1. 214 * @param escaped Optional buffer to write the encoded string, can be 215 * NULL 216 * @param str The original string 217 * @param slen The length of the original string, or APR_ESCAPE_STRING 218 * @param len If present, returns the length of the string 219 * @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were 220 * detected or if the stirng was NULL 221 */ 222APR_DECLARE(apr_status_t) apr_escape_urlencoded(char *escaped, const char *str, 223 apr_ssize_t slen, apr_size_t *len); 224 225/** 226 * Urlencode a string, as defined in 227 * http://www.w3.org/TR/html401/interact/forms.html#h-17.13.4.1, returning 228 * the result from a pool. 229 * @param p Pool to allocate from 230 * @param str String to be escaped 231 * @return A string allocated from the pool on success, the original string 232 * if no characters are encoded or if the string was NULL. 233 */ 234APR_DECLARE(const char *) apr_pescape_urlencoded(apr_pool_t *p, 235 const char *str) __attribute__((nonnull(1))); 236 237/** 238 * Apply entity encoding to a string. Characters are replaced as follows: 239 * '<' becomes '\<', '>' becomes '\>', '&' becomes '\&', the 240 * double quote becomes '\"" and the single quote becomes '\''. 241 * 242 * If toasc is not zero, any non ascii character will be encoded as 243 * '%\#ddd;', where ddd is the decimal code of the character. 244 * @param escaped Optional buffer to write the encoded string, can be 245 * NULL 246 * @param str The original string 247 * @param slen The length of the original string, or APR_ESCAPE_STRING 248 * @param toasc If non zero, encode non ascii characters 249 * @param len If present, returns the length of the string 250 * @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were 251 * detected or the string was NULL 252 */ 253APR_DECLARE(apr_status_t) apr_escape_entity(char *escaped, const char *str, 254 apr_ssize_t slen, int toasc, apr_size_t *len); 255 256/** 257 * Apply entity encoding to a string, returning the result from a pool. 258 * Characters are replaced as follows: '<' becomes '\<', '>' becomes 259 * '\>', '&' becomes '\&', the double quote becomes '\"" and the 260 * single quote becomes '\''. 261 * @param p Pool to allocate from 262 * @param str The original string 263 * @param toasc If non zero, encode non ascii characters 264 * @return A string allocated from the pool on success, the original string 265 * if no characters are encoded or the string is NULL. 266 */ 267APR_DECLARE(const char *) apr_pescape_entity(apr_pool_t *p, const char *str, 268 int toasc) __attribute__((nonnull(1))); 269 270/** 271 * Decodes html entities or numeric character references in a string. If 272 * the string to be unescaped is syntactically incorrect, then the 273 * following fixups will be made: 274 * unknown entities will be left undecoded; 275 * references to unused numeric characters will be deleted. 276 * In particular, � will not be decoded, but will be deleted. 277 * @param unescaped Optional buffer to write the encoded string, can be 278 * NULL 279 * @param str The original string 280 * @param slen The length of the original string, or APR_ESCAPE_STRING 281 * @param len If present, returns the length of the string 282 * @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were 283 * detected or the string was NULL 284 */ 285APR_DECLARE(apr_status_t) apr_unescape_entity(char *unescaped, const char *str, 286 apr_ssize_t slen, apr_size_t *len); 287 288/** 289 * Decodes html entities or numeric character references in a string. If 290 * the string to be unescaped is syntactically incorrect, then the 291 * following fixups will be made: 292 * unknown entities will be left undecoded; 293 * references to unused numeric characters will be deleted. 294 * In particular, � will not be decoded, but will be deleted. 295 * @param p Pool to allocate from 296 * @param str The original string 297 * @return A string allocated from the pool on success, the original string 298 * if no characters are encoded or the string is NULL. 299 */ 300APR_DECLARE(const char *) apr_punescape_entity(apr_pool_t *p, const char *str) 301 __attribute__((nonnull(1))); 302 303/** 304 * Escape control characters in a string, as performed by the shell's 305 * 'echo' command. Characters are replaced as follows: 306 * \\a alert (bell), \\b backspace, \\f form feed, \\n new line, \\r carriage 307 * return, \\t horizontal tab, \\v vertical tab, \\ backslash. 308 * 309 * Any non ascii character will be encoded as '\\xHH', where HH is the hex 310 * code of the character. 311 * 312 * If quote is not zero, the double quote character will also be escaped. 313 * @param escaped Optional buffer to write the encoded string, can be 314 * NULL 315 * @param str The original string 316 * @param slen The length of the original string, or APR_ESCAPE_STRING 317 * @param quote If non zero, encode double quotes 318 * @param len If present, returns the length of the string 319 * @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were 320 * detected or the string was NULL 321 */ 322APR_DECLARE(apr_status_t) apr_escape_echo(char *escaped, const char *str, 323 apr_ssize_t slen, int quote, apr_size_t *len); 324 325/** 326 * Escape control characters in a string, as performed by the shell's 327 * 'echo' command, and return the results from a pool. Characters are 328 * replaced as follows: \\a alert (bell), \\b backspace, \\f form feed, 329 * \\n new line, \\r carriage return, \\t horizontal tab, \\v vertical tab, 330 * \\ backslash. 331 * 332 * Any non ascii character will be encoded as '\\xHH', where HH is the hex 333 * code of the character. 334 * 335 * If quote is not zero, the double quote character will also be escaped. 336 * @param p Pool to allocate from 337 * @param str The original string 338 * @param quote If non zero, encode double quotes 339 * @return A string allocated from the pool on success, the original string 340 * if no characters are encoded or the string is NULL. 341 */ 342APR_DECLARE(const char *) apr_pescape_echo(apr_pool_t *p, const char *str, 343 int quote); 344 345/** 346 * Convert binary data to a hex encoding. 347 * @param dest The destination buffer, can be NULL 348 * @param src The original buffer 349 * @param srclen The length of the original buffer 350 * @param colon If not zero, insert colon characters between hex digits. 351 * @param len If present, returns the length of the string 352 * @return APR_SUCCESS, or APR_NOTFOUND if the string was NULL 353 */ 354APR_DECLARE(apr_status_t) apr_escape_hex(char *dest, const void *src, 355 apr_size_t srclen, int colon, apr_size_t *len); 356 357/** 358 * Convert binary data to a hex encoding, and return the results from a 359 * pool. 360 * @param p Pool to allocate from 361 * @param src The original buffer 362 * @param slen The length of the original buffer 363 * @param colon If not zero, insert colon characters between hex digits. 364 * @return A zero padded buffer allocated from the pool on success, or 365 * NULL if src was NULL. 366 */ 367APR_DECLARE(const char *) apr_pescape_hex(apr_pool_t *p, const void *src, 368 apr_size_t slen, int colon) __attribute__((nonnull(1))); 369 370/** 371 * Convert hex encoded string to binary data. 372 * @param dest The destination buffer, can be NULL 373 * @param str The original buffer 374 * @param slen The length of the original buffer 375 * @param colon If not zero, ignore colon characters between hex digits. 376 * @param len If present, returns the length of the string 377 * @return APR_SUCCESS, or APR_NOTFOUND if the string was NULL, or APR_BADCH 378 * if a non hex character is present. 379 */ 380APR_DECLARE(apr_status_t) apr_unescape_hex(void *dest, const char *str, 381 apr_ssize_t slen, int colon, apr_size_t *len); 382 383/** 384 * Convert hex encoding to binary data, and return the results from a pool. 385 * If the colon character appears between pairs of hex digits, it will be 386 * ignored. 387 * @param p Pool to allocate from 388 * @param str The original string 389 * @param colon If not zero, ignore colon characters between hex digits. 390 * @param len If present, returns the length of the final buffer 391 * @return A buffer allocated from the pool on success, or NULL if src was 392 * NULL, or a bad character was present. 393 */ 394APR_DECLARE(const void *) apr_punescape_hex(apr_pool_t *p, const char *str, 395 int colon, apr_size_t *len); 396 397/** 398 * Apply LDAP escaping to binary data. Characters from RFC4514 and RFC4515 399 * are escaped with their hex equivalents. 400 * @param dest The destination buffer, can be NULL 401 * @param src The original buffer 402 * @param srclen The length of the original buffer 403 * @param flags APR_ESCAPE_LDAP_DN for RFC4514, APR_ESCAPE_LDAP_FILTER for 404 * RFC4515, APR_ESCAPE_LDAP_ALL for both 405 * @param len If present, returns the length of the string 406 * @return APR_SUCCESS, or APR_NOTFOUND if the string was NULL 407 */ 408APR_DECLARE(apr_status_t) apr_escape_ldap(char *dest, const void *src, 409 apr_ssize_t srclen, int flags, apr_size_t *len); 410 411/** 412 * Apply LDAP escaping to binary data, and return the results from a 413 * pool. Characters from RFC4514 and RFC4515 are escaped with their hex 414 * equivalents. 415 * @param p Pool to allocate from 416 * @param src The original buffer 417 * @param slen The length of the original buffer 418 * @param flags APR_ESCAPE_LDAP_DN for RFC4514, APR_ESCAPE_LDAP_FILTER for 419 * RFC4515, APR_ESCAPE_LDAP_ALL for both 420 * @return A zero padded buffer allocated from the pool on success, or 421 * NULL if src was NULL. 422 */ 423APR_DECLARE(const char *) apr_pescape_ldap(apr_pool_t *p, const void *src, 424 apr_ssize_t slen, int flags) __attribute__((nonnull(1))); 425 426/** @} */ 427#ifdef __cplusplus 428} 429#endif 430 431#endif /* !APR_ESCAPE_H */ 432