void ValidateMapSize(const Image16Bpp& image, bool affine) { if ((image.width != 256 && image.width != 512) || (image.height != 256 && image.height != 512)) FatalLog("Invalid map size for image %s, (%d %d). Please fix. Use --force to override.", image.name.c_str(), image.width, image.height); else if (affine) { if (!((image.width == 128 && image.height == 128) || (image.width == 256 && image.height == 256) || (image.width == 512 && image.height == 512) || (image.width == 1024 && image.height == 1024))) FatalLog("Invalid affine map size for image %s, (%d %d). Please fix. Use --force to override.", image.name.c_str(), image.width, image.height); } }
int test_outputfunc() { LOG *g = NULL ; g = CreateLogHandle() ; if( g == NULL ) { printf( "创建日志句柄失败errno[%d]\n" , errno ); return -1; } else { printf( "创建日志句柄成功\n" ); } SetLogOutput( g , LOG_OUTPUT_CALLBACK , "127.0.0.1:514" , & MyOpenLogFirst , NULL , & MyWriteLog , NULL , NULL , & MyCloseLogFinally ); SetLogLevel( g , LOG_LEVEL_INFO ); SetLogStyles( g , LOG_STYLES_LOG , LOG_NO_STYLEFUNC ); DebugLog( g , __FILE__ , __LINE__ , "hello iLOG3\n" ); InfoLog( g , __FILE__ , __LINE__ , "hello iLOG3\n" ); WarnLog( g , __FILE__ , __LINE__ , "hello iLOG3\n" ); ErrorLog( g , __FILE__ , __LINE__ , "hello iLOG3\n" ); FatalLog( g , __FILE__ , __LINE__ , "hello iLOG3\n" ); DestroyLogHandle( g ); printf( "销毁日志句柄\n" ); return 0; }
const Map& MapScene::GetMap(int index) const { const Image* image = images[index].get(); const Map* map = dynamic_cast<const Map*>(image); if (!map) FatalLog("Internal Error could not cast Image to Map. This shouldn't happen"); return *map; }
Tileset::Tileset(const std::vector<Image16Bpp>& images, const std::string& name, int _bpp, bool _affine, const std::shared_ptr<Palette>& global_palette) : Exportable(name), bpp(_bpp), affine(_affine), palette(global_palette), paletteBanks(name), export_shared_data(global_palette == nullptr) { switch(bpp) { case 4: if (affine) { FatalLog("Affine can not be used with a 4 bpp tileset"); } else if (palette) { paletteBanks.Copy(*global_palette); } else { for (unsigned int i = 0; i < paletteBanks.Size(); i++) paletteBanks[i].Add(Color16(params.transparent_color)); } Init4bpp(images); break; case 8: Init8bpp(images); break; case 16: Init16bpp(images); break; } }
bool CmdLineParserHelper::GetSwitch(const std::string& param, bool def_value) { std::string no_param = "no_" + param; auto found_switch = parser.FoundSwitch(param); auto no_found_switch = parser.FoundSwitch(no_param); if (found_switch != wxCMD_SWITCH_NOT_FOUND && no_found_switch != wxCMD_SWITCH_NOT_FOUND) FatalLog("--%s and --no_%s provided at the same time, only one of these switches can be given", param.c_str(), param.c_str()); if (found_switch == wxCMD_SWITCH_NOT_FOUND && no_found_switch == wxCMD_SWITCH_NOT_FOUND) return def_value; return found_switch == wxCMD_SWITCH_ON || no_found_switch == wxCMD_SWITCH_OFF; }
void DoMapExport(const std::vector<Image16Bpp>& images, const std::vector<Image16Bpp>& tilesets) { if (tilesets.empty()) FatalLog("Map export specified however --tileset not given"); // Form the tileset from the images given this is a dummy std::shared_ptr<Tileset> tileset(new Tileset(tilesets, "", params.bpp, params.affine)); for (const auto& image : images) { std::shared_ptr<Exportable> map_ptr(new Map(image, tileset, params.affine)); header.Add(map_ptr); implementation.Add(map_ptr); } }
std::vector<int> CmdLineParserHelper::GetListInt(const std::string& param, const std::vector<int>& def_value) { wxString list; if (!parser.Found(param, &list)) return def_value; std::vector<int> ret; Scanner scan(list.ToStdString(), ","); while (scan.HasMoreTokens()) { int var; if (!scan.Next(var)) FatalLog("Error parsing flag %s", param.c_str()); ret.push_back(var); } return ret; }
std::string CmdLineParserHelper::GetChoice(const std::string& param, const std::set<std::string>& choices, const std::string& def_value) { std::string ret = GetString(param, def_value); if (choices.find(ret) == choices.end()) { std::stringstream choices_str; unsigned int i = 0; for (const auto& choice : choices) { choices_str << choice; if (i != choices.size() - 1) choices_str << ","; i++; } FatalLog("Invalid choice given for %s. Valid choices are [%s].", param.c_str(), choices_str.str().c_str()); } return ret; }
void DoGBAExport(const std::vector<Image32Bpp>& images32, const std::vector<Image32Bpp>& tilesets32, const std::vector<Image32Bpp>& palettes32) { std::vector<Image16Bpp> images; for (const auto& image : images32) images.push_back(Image16Bpp(image)); std::vector<Image16Bpp> tilesets; for (const auto& image : tilesets32) tilesets.push_back(Image16Bpp(image)); std::shared_ptr<Palette> palette; if (!palettes32.empty()) { std::vector<Image16Bpp> palettes; for (const auto& image : palettes32) palettes.push_back(Image16Bpp(image)); Image8BppScene scene(palettes, params.symbol_base_name); palette = scene.palette; } if (params.affine && params.bpp == 4 && (params.mode == "0" || params.mode == "MAP" || params.mode == "TILES" || params.mode == "TILEMAP")) FatalLog("GBA Affine Maps are 8 bpp only."); if (params.mode == "0" || params.mode == "TILEMAP") DoMode0Export(images); else if (params.mode == "3" || params.mode == "BITMAP") DoMode3Export(images); else if (params.mode == "4" || params.mode == "INDEXED") DoMode4Export(images, palette); else if (params.mode == "SPRITES") DoSpriteExport(images, palette); else if (params.mode == "TILES") DoTilesetExport(images, palette); else if (params.mode == "MAP") DoMapExport(images, tilesets); else if (params.mode == "PALETTE") DoPaletteExport(images); }
void Tileset::Init8bpp(const std::vector<Image16Bpp>& images16) { int tile_width = 8 + params.border; // Reduce all and get the global palette and reduced images. Image8BppScene scene(images16, name, palette); palette = scene.palette; const Tile& nullTile = Tile::GetNullTile8(); const ImageTile& nullImageTile = ImageTile::GetNullTile(); tiles.insert(nullTile); tilesExport.push_back(nullTile); matcher.insert(std::pair<ImageTile, Tile>(nullImageTile, nullTile)); for (unsigned int k = 0; k < images16.size(); k++) { const Image8Bpp& image = scene.GetImage(k); const Image16Bpp& image16 = images16[k]; unsigned int tilesX = image.width / tile_width; unsigned int tilesY = image.height / tile_width; unsigned int totalTiles = tilesX * tilesY; // Perform reduce. for (unsigned int i = 0; i < totalTiles; i++) { int tilex = i % tilesX; int tiley = i / tilesX; Tile tile(image, tilex, tiley, params.border); std::set<Tile>::iterator foundTile = tiles.find(tile); if (foundTile == tiles.end()) { tile.id = tiles.size(); tiles.insert(tile); tilesExport.push_back(tile); // Add matcher data ImageTile imageTile(image16, tilex, tiley, params.border); matcher.insert(std::pair<ImageTile, Tile>(imageTile, tile)); } } } // Checks int tile_size = TILE_SIZE_BYTES_8BPP; int memory_b = tiles.size() * tile_size; if (params.force) { if (!affine && tiles.size() >= 1024) WarnLog("Too many tiles. Found %d tiles. Maximum is 1024. Associated maps exported against this tileset may be incorrect.", tiles.size()); else if (affine && tiles.size() >= 256) WarnLog("Too many tiles found for affine. Found %d tiles. Maximum is 256. Associated maps exported against this tileset may be incorrect.", tiles.size()); } else { if (!affine && tiles.size() >= 1024) FatalLog("Too many tiles. Found %d tiles. Maximum is 1024. Please make the map/tileset simpler. Use --force to override this.", tiles.size()); else if (affine && tiles.size() >= 256) FatalLog("Too many tiles found for affine. Found %d tiles. Maximum is 256. Please make the map/tileset simpler. Use --force to override this.", tiles.size()); } // Delicious infos int cbbs = tiles.size() * tile_size / SIZE_CBB_BYTES; int sbbs = (int) ceil(tiles.size() * tile_size % SIZE_CBB_BYTES / ((double)SIZE_SBB_BYTES)); InfoLog("Tiles found %zu.", tiles.size()); InfoLog("Tiles uses %d charblocks and %d screenblocks.", cbbs, sbbs); InfoLog("Total utilization %.2f/4 charblocks or %d/32 screenblocks, %d/65536 bytes.", memory_b / ((double)SIZE_CBB_BYTES), (int) ceil(memory_b / ((double)SIZE_SBB_BYTES)), memory_b); }
void Tileset::Init4bpp(const std::vector<Image16Bpp>& images) { // Tile image into 16 bit tiles Tileset tileset16bpp(images, name, 16, affine); std::set<ImageTile> imageTiles = tileset16bpp.itiles; const Tile& nullTile = Tile::GetNullTile4(); const ImageTile& nullImageTile = ImageTile::GetNullTile(); tiles.insert(nullTile); tilesExport.push_back(nullTile); matcher.insert(std::pair<ImageTile, Tile>(nullImageTile, nullTile)); // Reduce each tile to 4bpp std::vector<Tile> gbaTiles; for (const auto& imageTile : imageTiles) gbaTiles.emplace_back(imageTile, 4); // Ensure image contains < 256 colors std::set<Color16> bigPalette; for (const auto& tile : gbaTiles) { const std::vector<Color16>& tile_palette = tile.palette.GetColors(); bigPalette.insert(tile_palette.begin(), tile_palette.end()); } if (bigPalette.size() > 256 && !params.force) FatalLog("Image after reducing tiles to 4 bpp still contains more than 256 distinct colors. Found %d colors. Please fix. Use --force to override.", bigPalette.size()); else if (bigPalette.size() > 256 && params.force) WarnLog("Image after reducing tiles to 4 bpp still contains more than 256 distinct colors. Found %d colors. Potential for image color quality loss."); // Greedy approach deal with tiles with largest palettes first. std::sort(gbaTiles.begin(), gbaTiles.end(), TilesPaletteSizeComp); // Construct palette banks, assign bank id to tile, remap tile to palette bank given, assign tile ids for (auto& tile : gbaTiles) { int pbank = -1; // Fully contains checks for (unsigned int i = 0; i < paletteBanks.Size(); i++) { PaletteBank& bank = paletteBanks[i]; if (bank.Contains(tile.palette)) pbank = i; } // Ok then find least affected bank if (pbank == -1) { int min_delta = 0x7FFFFFFF; for (unsigned int i = 0; i < paletteBanks.Size(); i++) { PaletteBank& bank = paletteBanks[i]; int colors_left; int delta; bank.CanMerge(tile.palette, colors_left, delta); if (colors_left >= 0 && delta < min_delta) { min_delta = delta; pbank = i; } } } // Cry and die for now. Unless you tell me to keep going. if (pbank == -1 && !params.force) FatalLog("More than 16 distinct palettes found, please use 8bpp mode. Use --force to override."); else if (pbank == -1 && params.force) WarnLog("More than 16 distinct palettes found. Huge potential for image color quality loss."); // Alright... if (pbank == -1) { pbank = paletteBanks.FindBestMatch(tile.palette); paletteBanks[pbank].BestMerge(tile.palette); } else { // Merge step and assign palette bank paletteBanks[pbank].Merge(tile.palette); } tile.palette_bank = pbank; tile.UsePalette(paletteBanks[pbank]); // Assign tile id const auto& it = tiles.find(tile); if (it == tiles.end()) { tile.id = tiles.size(); tiles.insert(tile); tilesExport.push_back(tile); } else { tile.id = it->id; } // Form mapping from ImageTile to Tile matcher.insert(std::pair<ImageTile, Tile>(*tile.sourceTile, tile)); } int tile_size = TILE_SIZE_BYTES_4BPP; int memory_b = tiles.size() * tile_size; // 4bpp mode so !affine can be assumed here. Affine maps have a max of 256 tiles. if (tiles.size() >= 1024 && !params.force) FatalLog("Too many tiles. Found %d tiles. Maximum is 1024. Please make the image simpler. Use --force to override.", tiles.size()); else if (tiles.size() >= 1024 && params.force) WarnLog("Too many tiles. Found %d tiles. Maximum is 1024. Associated maps exported against this tileset may be incorrect.", tiles.size()); // Delicious infos int cbbs = tiles.size() * tile_size / SIZE_CBB_BYTES; int sbbs = (int) ceil(tiles.size() * tile_size % SIZE_CBB_BYTES / ((double)SIZE_SBB_BYTES)); InfoLog("Tiles found %zu.", tiles.size()); InfoLog("Tiles uses %d charblocks and %d screenblocks.", cbbs, sbbs); InfoLog("Total utilization %.2f/4 charblocks or %d/32 screenblocks, %d/65536 bytes.", memory_b / ((double)SIZE_CBB_BYTES), (int) ceil(memory_b / ((double)SIZE_SBB_BYTES)), memory_b); }
int server( struct ServerEnv *penv ) { time_t now ; long epoll_timeout ; struct epoll_event events[ WAIT_EVENTS_COUNT ] ; int epoll_ready_count ; int epoll_ready_index ; struct epoll_event *pevent ; struct SocketSession *psession = NULL ; int accepted_session_index ; int nret = 0 ; signal( SIGTERM , & server_signal_proc ); SetLogFile( "%s/log/dc4c_rserver_1_%s:%d.log" , getenv("HOME") , penv->param.rserver_ip , penv->param.rserver_port ); if( penv->param.loglevel_debug == 1 ) SetLogLevel( LOGLEVEL_DEBUG ); else SetLogLevel( LOGLEVEL_INFO ); penv->epoll_socks = epoll_create( EPOLL_FDS_COUNT ) ; if( penv->epoll_socks < 0 ) { ErrorLog( __FILE__ , __LINE__ , "epoll_create failed[%d]errno[%d]" , penv->epoll_socks , errno ); return -1; } else { InfoLog( __FILE__ , __LINE__ , "epoll_create ok , sock[%d]" , penv->epoll_socks ); } nret = InitSocketSession( & (penv->listen_session) ) ; if( nret ) { ErrorLog( __FILE__ , __LINE__ , "InitSocketSession failed[%d]errno[%d]" , nret , errno ); return -1; } nret = BindListenSocket( penv->param.rserver_ip , penv->param.rserver_port , & (penv->listen_session) ) ; if( nret ) { ErrorLog( __FILE__ , __LINE__ , "BindListenSocket[%s:%d] failed[%d]errno[%d]" , penv->param.rserver_ip , penv->param.rserver_port , nret , errno ); return -1; } else { InfoLog( __FILE__ , __LINE__ , "BindListenSocket[%s:%d] ok" , penv->param.rserver_ip , penv->param.rserver_port ); } AddInputSockToEpoll( penv->epoll_socks , & (penv->listen_session) ); penv->accepted_session_array = (struct SocketSession *)malloc( sizeof(struct SocketSession) * MAXCOUNT_ACCEPTED_SESSION ) ; if( penv->accepted_session_array == NULL ) { FatalLog( __FILE__ , __LINE__ , "malloc failed[%d]errno[%d]" , nret , errno ); return -1; } memset( penv->accepted_session_array , 0x00 , sizeof(struct SocketSession) * MAXCOUNT_ACCEPTED_SESSION ); epoll_timeout = 1 ; while( ! g_server_exit_flag ) { memset( events , 0x00 , sizeof(events) ); if( g_server_exit_flag || getppid() == 1 ) break; epoll_ready_count = epoll_wait( penv->epoll_socks , events , WAIT_EVENTS_COUNT , epoll_timeout * 1000 ) ; if( g_server_exit_flag || getppid() == 1 ) break; DebugLog( __FILE__ , __LINE__ , "epoll_wait [%d]events reached" , epoll_ready_count ); time( & now ); for( epoll_ready_index = 0 , pevent = & (events[0]) ; epoll_ready_index < epoll_ready_count ; epoll_ready_index++ , pevent++ ) { psession = pevent->data.ptr ; DebugLog( __FILE__ , __LINE__ , "psession[%p] pevent->events[%d]" , psession , pevent->events ); if( psession == & (penv->listen_session) ) { if( pevent->events & EPOLLERR ) { DebugLog( __FILE__ , __LINE__ , "EPOLLERR on listen sock[%d]" , psession->sock ); g_server_exit_flag = 1 ; break; } else if( pevent->events & EPOLLIN || pevent->events & EPOLLHUP ) { DebugLog( __FILE__ , __LINE__ , "EPOLLIN on listen sock[%d]" , psession->sock ); nret = comm_OnListenSocketInput( penv , psession ) ; if( nret < 0 ) return nret; } else if( pevent->events & EPOLLOUT ) { DebugLog( __FILE__ , __LINE__ , "EPOLLOUT on listen sock[%d]" , psession->sock ); g_server_exit_flag = 1 ; break; } } else { if( pevent->events & EPOLLERR ) { DebugLog( __FILE__ , __LINE__ , "EPOLLERR on accepted sock[%d]" , psession->sock ); nret = comm_OnAcceptedSocketError( penv , psession ) ; if( nret < 0 ) return nret; } else if( pevent->events & EPOLLIN || pevent->events & EPOLLHUP ) { DebugLog( __FILE__ , __LINE__ , "EPOLLIN on accepted sock[%d]" , psession->sock ); nret = comm_OnAcceptedSocketInput( penv , psession ) ; if( nret < 0 ) return nret; } else if( pevent->events & EPOLLOUT ) { DebugLog( __FILE__ , __LINE__ , "EPOLLOUT on accepted sock[%d]" , psession->sock ); nret = comm_OnAcceptedSocketOutput( penv , psession ) ; if( nret < 0 ) return nret; } } } app_HeartBeatRequest( penv , & now , & epoll_timeout ); } sleep( penv->param.delay ); for( accepted_session_index = 0 ; accepted_session_index < MAXCOUNT_ACCEPTED_SESSION ; accepted_session_index++ ) { CleanSocketSession( penv->accepted_session_array+accepted_session_index ); } free( penv->accepted_session_array ); DeleteSockFromEpoll( penv->epoll_socks , & (penv->listen_session) ); CloseSocket( & (penv->listen_session) ); CleanSocketSession( & (penv->listen_session) ); close( penv->epoll_socks ); InfoLog( __FILE__ , __LINE__ , "close all socks and epoll_socks" ); InfoLog( __FILE__ , __LINE__ , "--- rserver [%s:%d] - [1] --- end" , penv->param.rserver_ip , penv->param.rserver_port ); return 0; }