cfg_enum_t* cfg_enum_open(cfg_t *cfg, cfg_dir_where_t where, char *subdir) { char buf[4096]; cfg_enum_t *e=0; do { if( where == CFG_DIR_NONE ) { e = cfg_enum_open(cfg, CFG_DIR_USER, subdir); if( e ) return e; e = cfg_enum_open(cfg, CFG_DIR_GLOBAL, subdir); if( e ) return e; return 0; } e = (cfg_enum_t*)calloc(1, sizeof(*e)); assertb(e); snprintf(e->path, sizeof(e->path), "%s/%s", cfg_dir(cfg, where, buf, sizeof(buf)), subdir); e->dir = opendir(e->path); } while(0); if( e && !e->dir ) { free(e); e = 0; } return e; }
/*! * \brief メッセージカタログのロード * \param[in] dir *.po ファイルが存在するディレクトリ * \retval true 成功 * \retval false 失敗 * * 実装を簡便化するため、.poファイルの記述方法には以下の制約がある。 * - msgid, msgstr は必ず行の先頭に記述する。 * - msgid, msgstr の直後には、必ず空白類文字一文字とし、その直後に文字列を記述する。 * - 文字列のみを記述する行は必ず " で始める。 * - .poファイルはの文字コードは必ず UTF-8N とする。 */ bool load_msgcat( std::string const& dir ) { namespace fs = boost::filesystem; char const* env = std::getenv( "TOPPERS_CFG_LANG" ); // env = "ja"; if ( env == 0 ) { return false; } std::string lang( env ); // fs::path cfg_dir( dir, fs::native ); fs::path cfg_dir( dir ); // filesystem3対応 // fs::path po_file( cfg_dir/fs::path( lang + ".po", fs::native ) ); fs::path po_file( cfg_dir/fs::path( lang + ".po" ) ); // filesystem3対応 // std::ifstream ifs( po_file.native_file_string().c_str() ); std::ifstream ifs( po_file.string().c_str() ); // filesystem3対応 std::string msgid; std::string msgstr; while ( ifs ) { std::string str; std::getline( ifs, str ); // 改行文字の違いを吸収 std::string::size_type pos = str.find_last_not_of( " \t\r\n" ); // ついでに行末の空白類も除去 if ( pos != std::string::npos && pos < str.size() - 1 ) { char c = str[pos]; str.erase( pos + 1, std::string::npos ); } if ( str.empty() || str[ 0 ] == '#' || str == "" ) { ; // 空行またはコメント行 } else { try { if ( std::strncmp( str.c_str(), "msgid", sizeof( "msgid" )-1 ) == 0 ) { str.erase( 0, sizeof( "msgid" )-1+1 ); msgid = expand_quote( str ); } else if ( std::strncmp( str.c_str(), "msgstr", sizeof( "msgstr" )-1 ) == 0 ) { str.erase( 0, sizeof( "msgstr" )-1+1 ); msgstr = expand_quote( str ); } else { msgstr += expand_quote( str ); } if ( !msgid.empty() && !msgstr.empty() ) // 直前の msgid / msgstr を登録 { register_msgcat( msgid, msgstr ); msgid.clear(); msgstr.clear(); } } catch ( std::invalid_argument& ) { return false; } } } msgcat_loaded = true; return true; }