# # # patch "ChangeLog" # from [59db5fcab0f06ebaac0b4b1176272b3a568532ce] # to [ad12888403b0f47c1c60ec773118196a185fd73f] # # patch "schema_migration.cc" # from [e1ea1f91c0830784152e630beb42a16a601d2a52] # to [d45098178370d1ddfc169c00853c714a695fd5c1] # ============================================================ --- ChangeLog 59db5fcab0f06ebaac0b4b1176272b3a568532ce +++ ChangeLog ad12888403b0f47c1c60ec773118196a185fd73f @@ -1,5 +1,16 @@ 2007-01-13 Zack Weinberg + * schema_migration.cc: Further prune includes and using-declarations. + (lowercase_facet, calculate_id): Delete. + (is_ws): Convert from class to predicate function. + (sqlite3_value_cstr): New, type-adjustment wrapper around _value_text. + (sqlite_sha1_fn): Clarify logic by using remove_copy_if, + sqlite3_value_cstr, and a simpler loop in the args>1 case. + Use transforms.hh's calculate_ident instead of calculate_id. + (massage_sql_tokens): Move to directly above sole user. + (calculate_schema_id): Use calculate_ident. + (sqlite_unbase64_fn): Use sqlite_value_cstr. + * transforms.cc (encode_hexenc_inner, encode_hexenc, decode_hex_char) (decode_hexenc_inner, decode_hexenc): Delete. (xform): Request lowercase output. ============================================================ --- schema_migration.cc e1ea1f91c0830784152e630beb42a16a601d2a52 +++ schema_migration.cc d45098178370d1ddfc169c00853c714a695fd5c1 @@ -9,7 +9,6 @@ #include #include -#include "botan/botan.h" #include "sanity.hh" #include "schema_migration.hh" @@ -18,12 +17,8 @@ #include "transforms.hh" #include "ui.hh" -using std::ctype; -using std::locale; using std::map; -using std::use_facet; using std::vector; -using boost::char_separator; // this file knows how to migrate schema databases. the general strategy is // to hash each schema we ever use, and make a list of the SQL commands @@ -33,12 +28,10 @@ using boost::char_separator; // of the migration. // you will notice a little bit of duplicated code between here and -// transforms.cc / database.cc; this was originally to facilitate inclusion of -// migration capability into the depot code, which did not link against those -// objects. the depot code is gone, but this isn't the sort of code that -// should ever be touched after being written, so the duplication currently -// remains. if it becomes a maintainence burden, however, consider -// refactoring. +// database.cc; this was originally to facilitate inclusion of migration +// capability into the depot code, but is now preserved because the code +// in this file is easier to write and understand if it speaks directly +// to sqlite. static int logged_sqlite3_exec(sqlite3* db, const char* sql, @@ -54,90 +47,73 @@ static int logged_sqlite3_exec(sqlite3* return res; } -typedef boost::tokenizer > tokenizer; - -static string -lowercase_facet(string const & in) +// sqlite3_value_text returns unsigned char const *, which is inconvenient +inline char const * +sqlite3_value_cstr(sqlite3_value * arg) { - I(40==in.size()); - const int sz=40; - char buf[sz]; - in.copy(buf, sz); - locale loc; - use_facet< ctype >(loc).tolower(buf, buf+sz); - return string(buf,sz); + return reinterpret_cast(sqlite3_value_text(arg)); } -static void -massage_sql_tokens(string const & in, - string & out) +inline bool is_ws(char c) { - char_separator sep(" \r\n\t", "(),;"); - tokenizer tokens(in, sep); - out.clear(); - for (tokenizer::iterator i = tokens.begin(); - i != tokens.end(); ++i) - { - if (i != tokens.begin()) - out += " "; - out += *i; - } + return c == '\r' || c == '\n' || c == '\t' || c == ' '; } static void -calculate_id(string const & in, - string & ident) -{ - Botan::Pipe p(new Botan::Hash_Filter("SHA-1"), new Botan::Hex_Encoder()); - p.process_msg(in); - - ident = lowercase_facet(p.read_all_as_string()); -} - -namespace { -struct -is_ws -{ - bool operator()(char c) const - { - return c == '\r' || c == '\n' || c == '\t' || c == ' '; - } -}; -} - -static void sqlite_sha1_fn(sqlite3_context *f, int nargs, sqlite3_value ** args) { - string tmp, sha; if (nargs <= 1) { sqlite3_result_error(f, "need at least 1 arg to sha1()", -1); return; } + string tmp; if (nargs == 1) { - string s = reinterpret_cast(sqlite3_value_text(args[0])); - s.erase(remove_if(s.begin(), s.end(), is_ws()),s.end()); - tmp = s; + char const * s = sqlite3_value_cstr(args[0]); + char const * end = s + sqlite3_value_bytes(args[0]) - 1; + remove_copy_if(s, end, back_inserter(tmp), is_ws); } else { - string sep = string(reinterpret_cast(sqlite3_value_text(args[0]))); - string s = reinterpret_cast(sqlite3_value_text(args[1])); - s.erase(remove_if(s.begin(), s.end(), is_ws()),s.end()); - tmp = s; - for (int i = 2; i < nargs; ++i) + char const * sep = sqlite3_value_cstr(args[0]); + + for (int i = 1; i < nargs; ++i) { - s = string(reinterpret_cast(sqlite3_value_text(args[i]))); - s.erase(remove_if(s.begin(), s.end(), is_ws()),s.end()); - tmp += sep + s; + if (i > 1) + tmp += sep; + char const * s = sqlite3_value_cstr(args[i]); + char const * end = s + sqlite3_value_bytes(args[i]) - 1; + remove_copy_if(s, end, back_inserter(tmp), is_ws); } } - calculate_id(tmp, sha); - sqlite3_result_text(f,sha.c_str(),sha.size(),SQLITE_TRANSIENT); + + hexenc sha; + calculate_ident(data(tmp), sha); + sqlite3_result_text(f, sha().c_str(), sha().size(), SQLITE_TRANSIENT); } + +static void +massage_sql_tokens(string const & in, + string & out) +{ + using boost::char_separator; + typedef boost::tokenizer > tokenizer; + + char_separator sep(" \r\n\t", "(),;"); + tokenizer tokens(in, sep); + out.clear(); + for (tokenizer::iterator i = tokens.begin(); + i != tokens.end(); ++i) + { + if (i != tokens.begin()) + out += " "; + out += *i; + } +} + static int append_sql_stmt(void * vp, int ncols, @@ -163,9 +139,9 @@ void } void -calculate_schema_id(sqlite3 *sql, string & id) +calculate_schema_id(sqlite3 *sql, string & ident) { - id.clear(); + ident.clear(); string tmp, tmp2; int res = logged_sqlite3_exec(sql, "SELECT sql FROM sqlite_master " @@ -194,7 +170,10 @@ calculate_schema_id(sqlite3 *sql, string E(false, F("sqlite error: %s\n%s") % errmsg % auxiliary_message); } massage_sql_tokens(tmp, tmp2); - calculate_id(tmp2, id); + + hexenc tid; + calculate_ident(data(tmp2), tid); + ident = tid(); } // these must be listed in order so that ones listed earlier override ones @@ -845,7 +824,7 @@ sqlite3_unbase64_fn(sqlite3_context *f, return; } data decoded; - decode_base64(base64(string(reinterpret_cast(sqlite3_value_text(args[0])))), decoded); + decode_base64(base64(string(sqlite3_value_cstr(args[0]))), decoded); sqlite3_result_blob(f, decoded().c_str(), decoded().size(), SQLITE_TRANSIENT); }