--- parser3/src/main/untaint.C 2001/03/19 17:42:16 1.8 +++ parser3/src/main/untaint.C 2001/03/21 14:06:46 1.11 @@ -5,7 +5,7 @@ Author: Alexander Petrosyan (http://design.ru/paf) - $Id: untaint.C,v 1.8 2001/03/19 17:42:16 paf Exp $ + $Id: untaint.C,v 1.11 2001/03/21 14:06:46 paf Exp $ */ #include @@ -30,11 +30,11 @@ strncpy(copy_here, b, bsize); \ copy_here+=bsize; \ break -#define escape_encode(need_encode_func) \ +#define escape_encode(need_encode_func, prefix) \ default: \ if(need_encode_func(*ptr)) { \ static const char *hex="0123456789ABCDEF"; \ - char chunk[3]={'%'}; \ + char chunk[3]={prefix}; \ chunk[1]=hex[((unsigned char)*ptr)/0x10]; \ chunk[2]=hex[((unsigned char)*ptr)%0x10]; \ strncpy(copy_here, chunk, 3); copy_here+=3; \ @@ -42,6 +42,12 @@ *copy_here++=*ptr; \ break +inline bool need_file_encode(unsigned char c){ + if ((c>='0') && (c<='9') || (c>='A') && (c<='Z') || (c>='a') && (c<='z')) + return false; + + return !strchr("./\\", c); +} inline bool need_uri_encode(unsigned char c){ if ((c>='0') && (c<='9') || (c>='A') && (c<='Z') || (c>='a') && (c<='z')) return false; @@ -57,7 +63,7 @@ inline bool need_header_encode(unsigned // String -/// \todo optimize whitespaces for all but 'html' +/// @todo optimize whitespaces for all but 'html' char *String::cstr() const { char *result=(char *)malloc(size()*UNTAINT_TIMES_BIGGER+1); @@ -72,44 +78,51 @@ char *String::cstr() const { // WARNING: // string can grow only UNTAINT_TIMES_BIGGER switch(row->item.lang) { - case NO: + case UL_NO: // clean piece - case YES: + case UL_YES: // tainted piece, but undefined untaint language // for VString.get_double of tainted values // for ^process{body} evaluation - case AS_IS: + case UL_AS_IS: // tainted, untaint language: as-is memcpy(copy_here, row->item.ptr, row->item.size); copy_here+=row->item.size; break; - case URI: + case UL_FILE_NAME: + // tainted, untaint language: file [name] + escape( + escape_value(' ', '_'); + escape_encode(need_file_encode, '-'); + ); + break; + case UL_URI: // tainted, untaint language: uri escape( escape_value(' ', '+'); - escape_encode(need_uri_encode); + escape_encode(need_uri_encode, '%'); ); break; - case HEADER: + case UL_HEADER: // tainted, untaint language: header escape( - escape_encode(need_header_encode); + escape_encode(need_header_encode, '%'); ); break; - case TABLE: + case UL_TABLE: escape( escape_value('\t', ' '); escape_value('\n', ' '); escape_default; ); break; - case SQL: + case UL_SQL: // tainted, untaint language: sql // TODO: зависимость от sql сервера memset(copy_here, '?', row->item.size); copy_here+=row->item.size; break; - case JS: + case UL_JS: escape( escape_subst('"', "\\\"", 2); escape_subst('\'', "\\'", 2); @@ -120,7 +133,7 @@ char *String::cstr() const { escape_default; ); break; - case HTML: + case UL_HTML: escape( escape_subst('&', "&", 5); // BEFORE consequent relpaces yelding '&' escape_subst('>', ">", 4); @@ -131,7 +144,7 @@ char *String::cstr() const { escape_default; ); break; - case HTML_TYPO: + case UL_HTML_TYPO: // tainted, untaint language: html-typo escape( escape_subst('&', "&", 5); // BEFORE consequent relpaces yelding '&'