// charset_names.cc // This file is part of libpbe; see http://anyterm.org/ // (C) 2008 Philip Endecott // Distributed under the Boost Software License, Version 1.0: // // Permission is hereby granted, free of charge, to any person or organization // obtaining a copy of the software and accompanying documentation covered by // this license (the "Software") to use, reproduce, display, distribute, // execute, and transmit the Software, and to prepare derivative works of the // Software, and to permit third-parties to whom the Software is furnished to // do so, all subject to the following: // // The copyright notices in the Software and this entire statement, including // the above license grant, this restriction and the following disclaimer, // must be included in all copies of the Software, in whole or in part, and // all derivative works of the Software, unless such copies or derivative // works are solely in the form of machine-executable object code generated by // a source language processor. // // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, // FITNESS FOR A PARTICULAR PURPOSE, TITLE AND NON-INFRINGEMENT. IN NO EVENT // SHALL THE COPYRIGHT HOLDERS OR ANYONE DISTRIBUTING THE SOFTWARE BE LIABLE // FOR ANY DAMAGES OR OTHER LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE, // ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER // DEALINGS IN THE SOFTWARE. #include "charset/charset_names.hh" #include #include #include #include #include using namespace std; namespace pbe { #include "generated/charset_iana_names_body.cc" #include "generated/charset_mime_names_body.cc" struct charset_lookup { const char* name; charset_t cs; }; static const charset_lookup lookup_table[] = { #include "generated/charset_lookup_body.cc" // {NULL, 0} }; static bool charset_name_less_than(const charset_lookup& a, string b) { return ::strcmp(a.name,b.c_str())<0; } charset_t lookup_charset(const char* name) { string stripped_lc_name; bool was_digit=false; bool uscore_pending=false; for (const char* p = name; *p; ++p) { if (isalnum(*p)) { if (uscore_pending && isdigit(*p)) { stripped_lc_name += '_'; } stripped_lc_name += tolower(*p); was_digit = isdigit(*p); uscore_pending = false; } else if (was_digit) { uscore_pending=true; } } const charset_lookup* lookup_table_end = lookup_table+sizeof(lookup_table)/sizeof(charset_lookup); const charset_lookup* l = lower_bound(&lookup_table[0], lookup_table_end, stripped_lc_name, charset_name_less_than); if (l==lookup_table_end || string(l->name)!=stripped_lc_name) { throw NoSuchCharacterSet(); } return l->cs; } charset_t lookup_charset(string name) { return lookup_charset(name.c_str()); } };