bool PluginLoader::ParsePlugin(FileSpecifier& file_name) { OpenedFile file; if (file_name.Open(file)) { int32 data_size; file.GetLength(data_size); m_data.resize(data_size); if (file.Read(data_size, &m_data[0])) { file_name.ToDirectory(current_plugin_directory); char name[256]; current_plugin_directory.GetName(name); m_name = name; if (!DoParse()) { logError1("There were parsing errors in %s Plugin.xml\n", m_name.c_str()); } } m_data.clear(); return true; } return false; }
void stop_recording( void) { if (replay.game_is_being_recorded) { replay.game_is_being_recorded = false; short player_index; int32 total_length; assert(replay.valid); for (player_index= 0; player_index<dynamic_world->player_count; player_index++) { save_recording_queue_chunk(player_index); } /* Rewrite the header, since it has the new length */ FilmFile.SetPosition(0); byte Header[SIZEOF_recording_header]; pack_recording_header(Header,&replay.header,1); // ZZZ: removing code that does stuff from assert() argument. BUT... // should we really be asserting on this anyway? I mean, the write could fail // in 'normal operation' too, not just when we screwed something up in writing the program? bool successfulWrite = FilmFile.Write(SIZEOF_recording_header,Header); assert(successfulWrite); FilmFile.GetLength(total_length); assert(total_length==replay.header.length); FilmFile.Close(); } replay.valid= false; }
// For reading the face-data chunk static bool ReadFaceData(OpenedFile& OFile, int32 ParentChunkEnd) { uint8 NFBuffer[2]; uint16 NumFaces; if (!OFile.Read(2,NFBuffer)) { logError1("ERROR reading number of faces in %s",Path); return false; } uint8 *S = NFBuffer; StreamToValue(S,NumFaces); int32 DataSize = 4*sizeof(uint16)*int(NumFaces); SetChunkBufferSize(DataSize); if (!OFile.Read(DataSize,ChunkBufferBase())) { logError1("ERROR reading face-chunk contents in %s",Path); return false; } S = ChunkBufferBase(); ModelPtr->VertIndices.resize(3*NumFaces); for (int k=0; k<NumFaces; k++) { uint16 *CurrPoly = ModelPtr->VIBase() + 3*k; uint16 Flags; StreamToList(S,CurrPoly,3); StreamToValue(S,Flags); } int32 Location = 0; OFile.GetPosition(Location); while(Location < ParentChunkEnd) { ChunkHeaderData ChunkHeader; if (!ReadChunkHeader(OFile,ChunkHeader)) return false; switch(ChunkHeader.ID) { /* case OBJECT: if (!ReadContainer(OFile,ChunkHeader,ReadObject)) return false; break; */ default: if (!SkipChunk(OFile,ChunkHeader)) return false; } // Where are we now? OFile.GetPosition(Location); } if (Location > ParentChunkEnd) { logError3("ERROR: Overran parent chunk: %d > %d in %s",Location,ParentChunkEnd,Path); return false; } return true; }
// For reading the editor-data chunk static bool ReadEditor(OpenedFile& OFile, int32 ParentChunkEnd) { int32 Location = 0; OFile.GetPosition(Location); while(Location < ParentChunkEnd) { ChunkHeaderData ChunkHeader; if (!ReadChunkHeader(OFile,ChunkHeader)) return false; switch(ChunkHeader.ID) { case OBJECT: if (!ReadContainer(OFile,ChunkHeader,ReadObject)) return false; break; default: if (!SkipChunk(OFile,ChunkHeader)) return false; } // Where are we now? OFile.GetPosition(Location); } if (Location > ParentChunkEnd) { logError3("ERROR: Overran parent chunk: %d > %d in %s",Location,ParentChunkEnd,Path); return false; } return true; }
void rewind_recording( void) { if(replay.game_is_being_recorded) { /* This is unnecessary, because it is called from reset_player_queues, */ /* which is always called from revert_game */ /* FilmFile.SetLength(sizeof(recording_header)); FilmFile.SetPosition(sizeof(recording_header)); */ // Alternative that does not use "SetLength", but instead creates and re-creates the file. FilmFile.SetPosition(0); byte Header[SIZEOF_recording_header]; FilmFile.Read(SIZEOF_recording_header,Header); FilmFile.Close(); FilmFileSpec.Delete(); FilmFileSpec.Create(_typecode_film); FilmFileSpec.Open(FilmFile,true); FilmFile.Write(SIZEOF_recording_header,Header); // Use the packed length here!!! replay.header.length= SIZEOF_recording_header; } }
bool physics_file_is_m1(void) { bool m1_physics = false; // check for M1 physics OpenedFile PhysicsFile; short SavedType, SavedError = get_game_error(&SavedType); if (PhysicsFileSpec.Open(PhysicsFile)) { uint32 tag = SDL_ReadBE32(PhysicsFile.GetRWops()); switch (tag) { case M1_MONSTER_PHYSICS_TAG: case M1_EFFECTS_PHYSICS_TAG: case M1_PROJECTILE_PHYSICS_TAG: case M1_PHYSICS_PHYSICS_TAG: case M1_WEAPONS_PHYSICS_TAG: m1_physics = true; break; default: break; } PhysicsFile.Close(); } set_game_error(SavedType, SavedError); return m1_physics; }
// For reading the master chunk (ideally, whole file) static bool ReadMaster(OpenedFile& OFile, int32 ParentChunkEnd) { int32 Location = 0; OFile.GetPosition(Location); while(Location < ParentChunkEnd) { ChunkHeaderData ChunkHeader; if (!ReadChunkHeader(OFile,ChunkHeader)) return false; switch(ChunkHeader.ID) { case EDITOR: if (!ReadContainer(OFile,ChunkHeader,ReadEditor)) return false; break; default: if (!SkipChunk(OFile,ChunkHeader)) return false; } // Where are we now? OFile.GetPosition(Location); } if (Location > ParentChunkEnd) { if (DBOut) fprintf(DBOut,"ERROR: Overran parent chunk: %ld > %ld\n",Location,ParentChunkEnd); return false; } return true; }
bool XML_Loader_SDL::ParseFile(FileSpecifier &file_name) { // Open file OpenedFile file; if (file_name.Open(file)) { printf ( "Parsing: %s\n", file_name.GetPath() ); // Get file size and allocate buffer file.GetLength(data_size); data = new char[data_size]; // In case there were errors... file_name.GetName(FileName); // Read and parse file if (file.Read(data_size, data)) { if (!DoParse()) { fprintf(stderr, "There were parsing errors in configuration file %s\n", FileName); } } // Delete buffer delete[] data; data = NULL; return true; } else { printf ( "Couldn't open: %s\n", file_name.GetPath() ); } return false; }
static TTF_Font *load_ttf_font(const std::string& path, uint16 style, int16 size) { // already loaded? increment reference counter and return pointer ttf_font_key_t search_key(path, style, size); ttf_font_list_t::iterator it = ttf_font_list.find(search_key); if (it != ttf_font_list.end()) { TTF_Font *font = it->second.first; it->second.second++; return font; } TTF_Font *font = 0; builtin_fonts_t::iterator j = builtin_fonts.find(path); if (j != builtin_fonts.end()) { font = TTF_OpenFontRW(SDL_RWFromConstMem(j->second.data, j->second.size), 0, size); } else { short SavedType, SavedError = get_game_error(&SavedType); FileSpecifier fileSpec(path); OpenedFile file; if (fileSpec.Open(file)) { font = TTF_OpenFontRW(file.TakeRWops(), 1, size); } set_game_error(SavedType, SavedError); } if (font) { int ttf_style = TTF_STYLE_NORMAL; if (style & styleBold) ttf_style |= TTF_STYLE_BOLD; if (style & styleItalic) ttf_style |= TTF_STYLE_ITALIC; TTF_SetFontStyle(font, ttf_style); #ifdef TTF_HINTING_LIGHT if (environment_preferences->smooth_text) TTF_SetFontHinting(font, TTF_HINTING_LIGHT); else TTF_SetFontHinting(font, TTF_HINTING_MONO); #endif ttf_font_key_t key(path, style, size); ref_counted_ttf_font_t value(font, 1); ttf_font_list[key] = value; } return font; }
bool SkipChunk(OpenedFile& OFile, ChunkHeaderData& ChunkHeader) { logTrace2("Skipping chunk 0x%04hx size %u",ChunkHeader.ID,ChunkHeader.Size); int32 DataSize = ChunkHeader.Size - SIZEOF_ChunkHeaderData; int32 Location = 0; OFile.GetPosition(Location); if (!OFile.SetPosition(Location + DataSize)) return false; return true; }
// For reading the object-data chunk static bool ReadObject(OpenedFile& OFile, int32 ParentChunkEnd) { // Read the name if (DBOut) fprintf(DBOut,"Object Name: "); while(true) { char c; if (!OFile.Read(1,&c)) { if (DBOut) fprintf(DBOut,"ERROR in reading name"); return false; } if (c == 0) { if (DBOut) fprintf(DBOut,"\n"); break; } else { if (DBOut) fprintf(DBOut,"%c",c); } } int32 Location = 0; OFile.GetPosition(Location); while(Location < ParentChunkEnd) { ChunkHeaderData ChunkHeader; if (!ReadChunkHeader(OFile,ChunkHeader)) return false; switch(ChunkHeader.ID) { case TRIMESH: if (!ReadContainer(OFile,ChunkHeader,ReadTrimesh)) return false; break; default: if (!SkipChunk(OFile,ChunkHeader)) return false; } // Where are we now? OFile.GetPosition(Location); } if (Location > ParentChunkEnd) { if (DBOut) fprintf(DBOut,"ERROR: Overran parent chunk: %ld > %ld\n",Location,ParentChunkEnd); return false; } return true; }
bool setup_for_replay_from_file( FileSpecifier& File, uint32 map_checksum, bool prompt_to_export) { bool successful= false; (void)(map_checksum); FilmFileSpec = File; if (FilmFileSpec.Open(FilmFile)) { replay.valid= true; replay.have_read_last_chunk = false; replay.game_is_being_replayed = true; assert(!replay.resource_data); replay.resource_data= NULL; replay.resource_data_size= 0l; replay.film_resource_offset= NONE; byte Header[SIZEOF_recording_header]; FilmFile.Read(SIZEOF_recording_header,Header); unpack_recording_header(Header,&replay.header,1); replay.header.game_information.cheat_flags = _allow_crosshair | _allow_tunnel_vision | _allow_behindview | _allow_overlay_map; /* Set to the mapfile this replay came from.. */ if(use_map_file(replay.header.map_checksum)) { replay.fsread_buffer= new char[DISK_CACHE_SIZE]; assert(replay.fsread_buffer); replay.location_in_cache= NULL; replay.bytes_in_cache= 0; replay.replay_speed= 1; #ifdef DEBUG_REPLAY open_stream_file(); #endif if (prompt_to_export) Movie::instance()->PromptForRecording(); successful= true; } else { /* Tell them that this map wasn't found. They lose. */ alert_user(infoError, strERRORS, cantFindReplayMap, 0); replay.valid= false; replay.game_is_being_replayed= false; FilmFile.Close(); } } return successful; }
/* -------------- Entry Point ----------- */ uint32 calculate_crc_for_file(FileSpecifier& File) { uint32 crc = 0; OpenedFile OFile; if (File.Open(OFile)) { crc= calculate_crc_for_opened_file(OFile); OFile.Close(); } return crc; }
bool SndfileDecoder::Open(FileSpecifier& File) { Close(); sfinfo.format = 0; OpenedFile openedFile; if (File.Open(openedFile)) { rwops = openedFile.TakeRWops(); sndfile = sf_open_virtual(&sf_virtual, SFM_READ, &sfinfo, rwops); } return sndfile; }
static void import_m1_physics_data() { OpenedFile PhysicsFile; if (!PhysicsFileSpec.Open(PhysicsFile)) { return; } int32 position = 0; int32 length; PhysicsFile.GetLength(length); while (position < length) { std::vector<uint8> header(12); PhysicsFile.Read(header.size(), &header[0]); AIStreamBE header_stream(&header[0], header.size()); uint32 tag; uint16 count; uint16 size; header_stream >> tag; header_stream.ignore(4); // unused header_stream >> count; header_stream >> size; std::vector<uint8> data(count * size); PhysicsFile.Read(data.size(), &data[0]); switch (tag) { case M1_MONSTER_PHYSICS_TAG: unpack_m1_monster_definition(&data[0], count); break; case M1_EFFECTS_PHYSICS_TAG: unpack_m1_effect_definition(&data[0], count); break; case M1_PROJECTILE_PHYSICS_TAG: unpack_m1_projectile_definition(&data[0], count); break; case M1_PHYSICS_PHYSICS_TAG: unpack_m1_physics_constants(&data[0], count); break; case M1_WEAPONS_PHYSICS_TAG: unpack_m1_weapon_definition(&data[0], count); break; } PhysicsFile.GetPosition(position); } }
void stop_replay( void) { if (replay.game_is_being_replayed) { assert(replay.valid); replay.game_is_being_replayed= false; if (replay.resource_data) { delete []replay.resource_data; replay.resource_data= NULL; } else { FilmFile.Close(); assert(replay.fsread_buffer); delete []replay.fsread_buffer; } #ifdef DEBUG_REPLAY close_stream_file(); #endif } /* Unecessary, because reset_player_queues calls this. */ replay.valid= false; }
static void remove_input_controller( void) { remove_timer_task(input_task); if (replay.game_is_being_recorded) { stop_recording(); } else if (replay.game_is_being_replayed) { if (replay.resource_data) { delete []replay.resource_data; replay.resource_data= NULL; replay.resource_data_size= 0l; replay.film_resource_offset= NONE; } else { FilmFile.Close(); } } replay.valid= false; }
SDL_Surface *WadImageCache::image_from_name(std::string& name) const { FileSpecifier file; file.SetToImageCacheDir(); file.AddPart(name); OpenedFile of; if (!file.Open(of)) return NULL; #ifdef HAVE_SDL_IMAGE SDL_Surface *img = IMG_Load_RW(of.GetRWops(), 0); #else SDL_Surface *img = SDL_LoadBMP_RW(of.GetRWops(), 0); #endif return img; }
// For reading the triangle-mesh-data chunk static bool ReadTrimesh(OpenedFile& OFile, int32 ParentChunkEnd) { int32 Location = 0; OFile.GetPosition(Location); assert(ModelPtr); while(Location < ParentChunkEnd) { ChunkHeaderData ChunkHeader; if (!ReadChunkHeader(OFile,ChunkHeader)) return false; switch(ChunkHeader.ID) { case VERTICES: if (!LoadChunk(OFile,ChunkHeader)) return false; LoadVertices(); break; case TXTR_COORDS: if (!LoadChunk(OFile,ChunkHeader)) return false; LoadTextureCoordinates(); break; case FACE_DATA: if (!ReadContainer(OFile,ChunkHeader,ReadFaceData)) return false; break; default: if (!SkipChunk(OFile,ChunkHeader)) return false; } // Where are we now? OFile.GetPosition(Location); } if (Location > ParentChunkEnd) { if (DBOut) fprintf(DBOut,"ERROR: Overran parent chunk: %ld > %ld\n",Location,ParentChunkEnd); return false; } return true; }
// For reading the object-data chunk static bool ReadObject(OpenedFile& OFile, int32 ParentChunkEnd) { // Read the name char c; do { if (!OFile.Read(1,&c)) { logError1("ERROR when reading name in %s",Path); return false; } } while(c != 0); int32 Location = 0; OFile.GetPosition(Location); while(Location < ParentChunkEnd) { ChunkHeaderData ChunkHeader; if (!ReadChunkHeader(OFile,ChunkHeader)) return false; switch(ChunkHeader.ID) { case TRIMESH: if (!ReadContainer(OFile,ChunkHeader,ReadTrimesh)) return false; break; default: if (!SkipChunk(OFile,ChunkHeader)) return false; } // Where are we now? OFile.GetPosition(Location); } if (Location > ParentChunkEnd) { logError3("ERROR: Overran parent chunk: %d > %d in %s",Location,ParentChunkEnd,Path); return false; } return true; }
void *get_network_physics_buffer( int32 *physics_length) { if (physics_file_is_m1()) { bool success = false; uint8 *data = NULL; OpenedFile PhysicsFile; if (PhysicsFileSpec.Open(PhysicsFile) && PhysicsFile.GetLength(*physics_length)) { data = (uint8 *)malloc(*physics_length + 4); SDL_RWops *ops = SDL_RWFromMem(data, *physics_length + 4); success = SDL_WriteBE32(ops, uint32(M1_PHYSICS_MAGIC_COOKIE)); if (success) success = SDL_WriteBE32(ops, uint32(*physics_length)); SDL_RWclose(ops); if (success) success = PhysicsFile.Read(*physics_length, &data[8]); if (!success) free(data); } if (!success) { *physics_length = 0; return NULL; } return data; } short SavedType, SavedError = get_game_error(&SavedType); void *data= get_flat_data(PhysicsFileSpec, false, 0); set_game_error(SavedType, SavedError); if(data) { *physics_length= get_flat_data_length(data); } else { *physics_length= 0; } return data; }
// DJB OpenGL char* parseFile(FileSpecifier& fileSpec) { if (fileSpec == FileSpecifier() || !fileSpec.Exists()) { return NULL; } OpenedFile file; if (!fileSpec.Open(file)) { fprintf(stderr, "%s not found\n", fileSpec.GetPath()); return NULL; } int32 length; file.GetLength(length); char* str = new char[length + 1]; file.Read(length, str); str[length] = 0; return str; }
bool LoadChunk(OpenedFile& OFile, ChunkHeaderData& ChunkHeader) { logTrace2("Loading chunk 0x%04hx size %u",ChunkHeader.ID,ChunkHeader.Size); int32 DataSize = ChunkHeader.Size - SIZEOF_ChunkHeaderData; SetChunkBufferSize(DataSize); if (!OFile.Read(DataSize,ChunkBufferBase())) { logError1("ERROR reading chunk contents in %s",Path); return false; } return true; }
bool ReadChunkHeader(OpenedFile& OFile, ChunkHeaderData& ChunkHeader) { uint8 Buffer[SIZEOF_ChunkHeaderData]; if (!OFile.Read(SIZEOF_ChunkHeaderData,Buffer)) { logError1("ERROR reading chunk header in %s",Path); return false; } uint8 *S = Buffer; StreamToValue(S,ChunkHeader.ID); StreamToValue(S,ChunkHeader.Size); return true; }
bool ReadChunkHeader(OpenedFile& OFile, ChunkHeaderData& ChunkHeader) { uint8 Buffer[SIZEOF_ChunkHeaderData]; if (!OFile.Read(SIZEOF_ChunkHeaderData,Buffer)) { if (DBOut) fprintf(DBOut,"ERROR reading chunk header\n"); return false; } uint8 *S = Buffer; StreamToValue(S,ChunkHeader.ID); StreamToValue(S,ChunkHeader.Size); return true; }
bool LoadChunk(OpenedFile& OFile, ChunkHeaderData& ChunkHeader) { if (DBOut) fprintf(DBOut,"Loading chunk 0x%04hx size %lu\n",ChunkHeader.ID,ChunkHeader.Size); int32 DataSize = ChunkHeader.Size - SIZEOF_ChunkHeaderData; SetChunkBufferSize(DataSize); if (!OFile.Read(DataSize,ChunkBufferBase())) { if (DBOut) fprintf(DBOut,"ERROR reading chunk contents\n"); return false; } return true; }
// Generic container-chunk reader bool ReadContainer(OpenedFile& OFile, ChunkHeaderData& ChunkHeader, bool (*ContainerCallback)(OpenedFile&,int32)) { logTrace2("Entering chunk 0x%04hx size %u",ChunkHeader.ID,ChunkHeader.Size); int32 ChunkEnd = 0; OFile.GetPosition(ChunkEnd); ChunkEnd += ChunkHeader.Size - SIZEOF_ChunkHeaderData; if (!ContainerCallback(OFile,ChunkEnd)) return false; logTrace2("Exiting chunk 0x%04hx size %u",ChunkHeader.ID,ChunkHeader.Size); return true; }
std::string WadImageCache::image_to_new_name(SDL_Surface *image, int32 *filesize) const { // create name boost::uuids::random_generator gen; boost::uuids::uuid u = gen(); std::string ustr = boost::uuids::to_string(u); FileSpecifier File; File.SetToImageCacheDir(); File.AddPart(ustr); FileSpecifier TempFile; TempFile.SetTempName(File); int ret; //#if defined(HAVE_PNG) && defined(HAVE_SDL_IMAGE) // ret = aoIMG_SavePNG(TempFile.GetPath(), image, IMG_COMPRESS_DEFAULT, NULL, 0); #ifdef HAVE_SDL_IMAGE ret = IMG_SavePNG(image, TempFile.GetPath()); #else ret = SDL_SaveBMP(image, TempFile.GetPath()); #endif if (ret == 0 && TempFile.Rename(File)) { if (filesize) { OpenedFile of; if (File.Open(of)) of.GetLength(*filesize); } return ustr; } if (filesize) *filesize = 0; return ""; }
// Open data file bool FileSpecifier::Open(OpenedFile &OFile, bool Writable) { OFile.Close(); SDL_RWops *f; #ifdef __MACOS__ if (!Writable) f = OFile.f = open_fork_from_existing_path(GetPath(), false); else #endif { #ifdef HAVE_ZZIP if (!Writable) { f = OFile.f = SDL_RWFromZZIP(unix_path_separators(GetPath()).c_str(), "rb"); } else #endif f = OFile.f = SDL_RWFromFile(GetPath(), Writable ? "wb+" : "rb"); } err = f ? 0 : errno; if (f == NULL) { set_game_error(systemError, err); return false; } if (Writable) return true; // Transparently handle AppleSingle and MacBinary files on reading int32 offset, data_length, rsrc_length; if (is_applesingle(f, false, offset, data_length)) { OFile.is_forked = true; OFile.fork_offset = offset; OFile.fork_length = data_length; SDL_RWseek(f, offset, SEEK_SET); return true; } else if (is_macbinary(f, data_length, rsrc_length)) { OFile.is_forked = true; OFile.fork_offset = 128; OFile.fork_length = data_length; SDL_RWseek(f, 128, SEEK_SET); return true; } SDL_RWseek(f, 0, SEEK_SET); return true; }
/* Note that we _must_ set the header information before we start recording!! */ void start_recording( void) { assert(!replay.valid); replay.valid= true; if(get_recording_filedesc(FilmFileSpec)) FilmFileSpec.Delete(); if (FilmFileSpec.Create(_typecode_film)) { /* I debate the validity of fsCurPerm here, but Alain had it, and it has been working */ if (FilmFileSpec.Open(FilmFile,true)) { replay.game_is_being_recorded= true; // save a header containing information about the game. byte Header[SIZEOF_recording_header]; pack_recording_header(Header,&replay.header,1); FilmFile.Write(SIZEOF_recording_header,Header); } } }