static int loadsample (TCHAR *path, struct drvsample *ds) { struct zfile *f; uae_u8 *buf; int size; TCHAR name[MAX_DPATH]; f = zfile_fopen (path, _T("rb"), ZFD_NORMAL); if (!f) { _tcscpy (name, path); _tcscat (name, _T(".wav")); f = zfile_fopen (name, _T("rb"), ZFD_NORMAL); if (!f) { write_log (_T("driveclick: can't open '%s' (or '%s')\n"), path, name); return 0; } } zfile_fseek (f, 0, SEEK_END); size = zfile_ftell (f); buf = xmalloc (uae_u8, size); zfile_fseek (f, 0, SEEK_SET); zfile_fread (buf, size, 1, f); zfile_fclose (f); ds->len = size; ds->p = decodewav (buf, &ds->len); xfree (buf); return 1; }
int caps_loadimage (struct zfile *zf, unsigned int drv, unsigned int *num_tracks) { struct CapsImageInfo ci; int len, ret; uae_u8 *buf; char s1[100]; struct CapsDateTimeExt *cdt; if (!caps_init ()) return 0; caps_unloadimage (drv); zfile_fseek (zf, 0, SEEK_END); len = zfile_ftell (zf); zfile_fseek (zf, 0, SEEK_SET); buf = xmalloc (uae_u8, len); if (!buf) return 0; if (zfile_fread (buf, len, 1, zf) == 0) return 0; ret = CAPSLockImageMemory (caps_cont[drv], buf, len, 0); xfree (buf); if (ret != imgeOk) return 0; caps_locked[drv] = 1; CAPSGetImageInfo (&ci, caps_cont[drv]); *num_tracks = (ci.maxcylinder - ci.mincylinder + 1) * (ci.maxhead - ci.minhead + 1); CAPSLoadImage (caps_cont[drv], caps_flags); cdt = &ci.crdt; sprintf (s1, "%d.%d.%d %d:%d:%d", cdt->day, cdt->month, cdt->year, cdt->hour, cdt->min, cdt->sec); write_log ("CAPS: type:%d date:%s rel:%d rev:%d\n", ci.type, s1, ci.release, ci.revision); return 1; }
static int load_extendedkickstart (void) { struct zfile *f; int size; if (strlen (currprefs.romextfile) == 0) return 0; f = zfile_open (currprefs.romextfile, "rb"); if (!f) { printf ("No extended Kickstart ROM found"); return 0; } zfile_fseek (f, 0, SEEK_END); size = zfile_ftell (f); if (size > 300000) extendedkickmem_size = 524288; else extendedkickmem_size = 262144; zfile_fseek (f, 0, SEEK_SET); switch (extromtype ()) { case EXTENDED_ROM_CDTV: extendedkickmemory = (uae_u8 *) mapped_malloc (extendedkickmem_size, "rom_f0"); extendedkickmem_bank.baseaddr = (uae_u8 *) extendedkickmemory; break; case EXTENDED_ROM_CD32: extendedkickmemory = (uae_u8 *) mapped_malloc (extendedkickmem_size, "rom_e0"); extendedkickmem_bank.baseaddr = (uae_u8 *) extendedkickmemory; break; } read_kickstart (f, extendedkickmemory, 524288, 0, 0); return 1; }
int caps_loadimage (struct zfile *zf, int drv, int *num_tracks) { static int notified; struct CapsImageInfo ci; int len, ret; uae_u8 *buf; TCHAR s1[100]; struct CapsDateTimeExt *cdt; if (!caps_init ()) return 0; caps_unloadimage (drv); zfile_fseek (zf, 0, SEEK_END); len = zfile_ftell (zf); zfile_fseek (zf, 0, SEEK_SET); buf = xmalloc (uae_u8, len); if (!buf) return 0; if (zfile_fread (buf, len, 1, zf) == 0) return 0; ret = pCAPSLockImageMemory (caps_cont[drv], buf, len, 0); xfree (buf); if (ret != imgeOk) { if (ret == imgeIncompatible || ret == imgeUnsupported) { if (!notified) notify_user (NUMSG_OLDCAPS); notified = 1; } write_log (L"caps: CAPSLockImageMemory() returned %d\n", ret); return 0; } caps_locked[drv] = 1; ret = pCAPSGetImageInfo(&ci, caps_cont[drv]); *num_tracks = (ci.maxcylinder - ci.mincylinder + 1) * (ci.maxhead - ci.minhead + 1); if (cvi.release < 4) { // pre-4.x bug workaround struct CapsTrackInfoT1 cit; cit.type = 1; if (pCAPSLockTrack ((PCAPSTRACKINFO)&cit, caps_cont[drv], 0, 0, caps_flags) == imgeIncompatible) { if (!notified) notify_user (NUMSG_OLDCAPS); notified = 1; caps_unloadimage (drv); return 0; } pCAPSUnlockAllTracks (caps_cont[drv]); } ret = pCAPSLoadImage(caps_cont[drv], caps_flags); cdt = &ci.crdt; _stprintf (s1, L"%d.%d.%d %d:%d:%d", cdt->day, cdt->month, cdt->year, cdt->hour, cdt->min, cdt->sec); write_log (L"caps: type:%d date:%s rel:%d rev:%d\n", ci.type, s1, ci.release, ci.revision); return 1; }
/* Locate the Central directory of a zipfile (at the end, just before the global comment) */ local uLong unzlocal_SearchCentralDir(struct zfile *fin) { unsigned char* buf; uLong uSizeFile; uLong uBackRead; uLong uMaxBack=0xffff; /* maximum size of global comment */ uLong uPosFound=0; if (zfile_fseek(fin,0,SEEK_END) != 0) return 0; uSizeFile = zfile_ftell( fin ); if (uMaxBack>uSizeFile) uMaxBack = uSizeFile; buf = (unsigned char*)ALLOC(BUFREADCOMMENT+4); if (buf==NULL) return 0; uBackRead = 4; while (uBackRead<uMaxBack) { uLong uReadSize,uReadPos ; int i; if (uBackRead+BUFREADCOMMENT>uMaxBack) uBackRead = uMaxBack; else uBackRead+=BUFREADCOMMENT; uReadPos = uSizeFile-uBackRead ; uReadSize = ((BUFREADCOMMENT+4) < (uSizeFile-uReadPos)) ? (BUFREADCOMMENT+4) : (uSizeFile-uReadPos); if (zfile_fseek(fin,uReadPos,SEEK_SET)!=0) break; if (zfile_fread(buf,(uInt)uReadSize,1,fin)!=1) break; for (i=(int)uReadSize-3; (i--)>0;) if (((*(buf+i))==0x50) && ((*(buf+i+1))==0x4b) && ((*(buf+i+2))==0x05) && ((*(buf+i+3))==0x06)) { uPosFound = uReadPos+i; break; } if (uPosFound!=0) break; } TRYFREE(buf); return uPosFound; }
int32_t inprec_open(char *fname, int32_t record) { uint32_t t = (uint32_t)time(0); int32_t i; inprec_close(); inprec_zf = zfile_fopen(fname, record > 0 ? "wb" : "rb"); if (inprec_zf == NULL) return 0; inprec_size = 10000; inprec_div = 1; if (record < 0) { uint32_t id; zfile_fseek (inprec_zf, 0, SEEK_END); inprec_size = zfile_ftell (inprec_zf); zfile_fseek (inprec_zf, 0, SEEK_SET); inprec_buffer = inprec_p = (uint8_t*)xmalloc (inprec_size); zfile_fread (inprec_buffer, inprec_size, 1, inprec_zf); inprec_plastptr = inprec_buffer; id = inprec_pu32(); if (id != 'UAE\0') { inprec_close(); return 0; } inprec_pu32(); t = inprec_pu32(); i = inprec_pu32(); while (i-- > 0) inprec_pu8(); inprec_p = inprec_plastptr; oldbuttons[0] = oldbuttons[1] = oldbuttons[2] = oldbuttons[3] = 0; oldjoy[0] = oldjoy[1] = 0; if (record < -1) inprec_div = maxvpos; } else if (record > 0) { inprec_buffer = inprec_p = (uint8_t*)xmalloc (inprec_size); inprec_ru32('UAE\0'); inprec_ru8(1); inprec_ru8(UAEMAJOR); inprec_ru8(UAEMINOR); inprec_ru8(UAESUBREV); inprec_ru32(t); inprec_ru32(0); // extra header size } else { return 0; } input_recording = record; srand(t); CIA_inprec_prepare(); write_log ("inprec initialized '%s', mode=%d\n", fname, input_recording); return 1; }
static int hdf_seek (struct hardfiledata *hfd, uae_u64 offset) { size_t ret; if (hfd->handle_valid == 0) { gui_message ("hd: hdf handle is not valid. bug."); abort(); } if (offset >= hfd->physsize - hfd->virtual_size) { gui_message ("hd: tried to seek out of bounds! (0x%llx >= 0x%llx)\n", offset, hfd->physsize); abort (); } offset += hfd->offset; if (offset & (hfd->ci.blocksize - 1)) { gui_message ("hd: poscheck failed, offset=0x%llx not aligned to blocksize=%d! (0x%llx & 0x%04.4x = 0x%04.4x)\n", offset, hfd->ci.blocksize, offset, hfd->ci.blocksize, offset & (hfd->ci.blocksize - 1)); abort (); } if (hfd->handle_valid == HDF_HANDLE_LINUX) { ret = uae_fseeko64 (hfd->handle->h, offset, SEEK_SET); if (ret) { write_log("hdf_seek failed\n"); return -1; } } else if (hfd->handle_valid == HDF_HANDLE_ZFILE) { zfile_fseek (hfd->handle->zf, (long)offset, SEEK_SET); } return 0; }
/* Get the global comment string of the ZipFile, in the szComment buffer. uSizeBuf is the size of the szComment buffer. return the number of byte copied or an error code <0 */ extern int ZEXPORT unzGetGlobalComment (unzFile file, char *szComment, uLong uSizeBuf) { // int err=UNZ_OK; unz_s* s; uLong uReadThis ; if (file==NULL) return UNZ_PARAMERROR; s=(unz_s*)file; uReadThis = uSizeBuf; if (uReadThis>s->gi.size_comment) uReadThis = s->gi.size_comment; if (zfile_fseek(s->file,s->central_pos+22,SEEK_SET)!=0) return UNZ_ERRNO; if (uReadThis>0) { *szComment='\0'; if (zfile_fread(szComment,(uInt)uReadThis,1,s->file)!=1) return UNZ_ERRNO; } if ((szComment != NULL) && (uSizeBuf > s->gi.size_comment)) *(szComment+s->gi.size_comment)='\0'; return (int)uReadThis; }
static int read_kickstart (struct zfile *f, uae_u8 *mem, int size, int dochecksum, int *cloanto_rom) { unsigned char buffer[20]; int i, j, cr = 0; fprintf(stderr,"read_kickstart\n"); if (cloanto_rom) *cloanto_rom = 0; i = zfile_fread (buffer, 1, 11, f); if (strncmp ((char *) buffer, "AMIROMTYPE1", 11) != 0) { zfile_fseek (f, 0, SEEK_SET); } else { cr = 1; } if (cloanto_rom) *cloanto_rom = cr; i = zfile_fread (mem, 1, size, f); if (i != 8192 && i != 65536 && i != 131072 && i != 262144 && i != 524288 && i != 524288 * 2 && i != 524288 * 4) { gui_message ("Error while reading Kickstart ROM file."); return 0; } if (i == size / 2) memcpy (mem + size / 2, mem, size / 2); if (cr) { if (!decode_cloanto_rom (mem, size, i, 0)) return 0; } if (currprefs.cs_a1000ram) { int off = 0; a1000_bootrom = xcalloc (262144, 1); while (off + i < 262144) { memcpy (a1000_bootrom + off, kickmemory, i); off += i; } memset (kickmemory, 0, kickmem_size); a1000_handle_kickstart (1); dochecksum = 0; i = 524288; } zfile_fclose (f); for (j = 0; j < 256 && i >= 262144; j++) { if (!memcmp (mem + j, kickstring, strlen (kickstring) + 1)) break; } if (j == 256 || i < 262144) dochecksum = 0; if (dochecksum) kickstart_checksum (mem, size); return 1; }
static void *cdda_unpack_func (void *v) { cdimage_unpack_thread = 1; mp3decoder *mp3dec = NULL; for (;;) { uae_u32 cduidx = read_comm_pipe_u32_blocking (&unpack_pipe); if (cdimage_unpack_thread == 0) break; uae_u32 tocidx = read_comm_pipe_u32_blocking (&unpack_pipe); struct cdunit *cdu = &cdunits[cduidx]; struct cdtoc *t = &cdu->toc[tocidx]; if (t->handle) { // force unpack if handle points to delayed zipped file uae_s64 pos = zfile_ftell (t->handle); zfile_fseek (t->handle, -1, SEEK_END); uae_u8 b; zfile_fread (&b, 1, 1, t->handle); zfile_fseek (t->handle, pos, SEEK_SET); if (!t->data && (t->enctype == AUDENC_MP3 || t->enctype == AUDENC_FLAC)) { t->data = xcalloc (uae_u8, t->filesize + 2352); cdimage_unpack_active = 1; if (t->data) { if (t->enctype == AUDENC_MP3) { if (!mp3dec) { try { mp3dec = new mp3decoder(); } catch (exception) { }; } if (mp3dec) t->data = mp3dec->get (t->handle, t->data, t->filesize); } else if (t->enctype == AUDENC_FLAC) { flac_get_data (t); } } } } cdimage_unpack_active = 2; } delete mp3dec; cdimage_unpack_thread = -1; return 0; }
void addkeyfile (const TCHAR *path) { struct zfile *f; int keysize; uae_u8 *keybuf; f = zfile_fopen (path, L"rb", ZFD_NORMAL); if (!f) return; zfile_fseek (f, 0, SEEK_END); keysize = zfile_ftell (f); if (keysize > 0) { zfile_fseek (f, 0, SEEK_SET); keybuf = xmalloc (uae_u8, keysize); zfile_fread (keybuf, 1, keysize, f); addkey (keybuf, keysize, path); } zfile_fclose (f); }
static int do_read (struct cdunit *cdu, struct cdtoc *t, uae_u8 *data, int sector, int offset, int size) { if (t->enctype == ENC_CHD) { return read_partial_sector(cdu->chd_cdf, data, sector + t->offset, 0, offset, size) == CHDERR_NONE; } else if (t->handle) { int ssize = t->size + t->skipsize; zfile_fseek (t->handle, t->offset + (uae_u64)sector * ssize + offset, SEEK_SET); return zfile_fread (data, 1, size, t->handle) == size; } return 0; }
inline void chd_file::file_read(UINT64 offset, void *dest, UINT32 length) { // no file = failure if (m_file == NULL) throw CHDERR_NOT_OPEN; // seek and read zfile_fseek(m_file, offset, SEEK_SET); UINT32 count = zfile_fread(dest, 1, length, m_file); if (count != length) throw CHDERR_READ_ERROR; }
void amax_init (void) { struct zfile *z; if (!currprefs.amaxromfile[0]) return; amax_reset (); z = zfile_fopen (currprefs.amaxromfile, _T("rb"), ZFD_NORMAL); if (!z) { write_log (_T("AMAX: failed to load rom '%s'\n"), currprefs.amaxromfile); return; } zfile_fseek (z, 0, SEEK_END); amax_rom_size = zfile_ftell (z); zfile_fseek (z, 0, SEEK_SET); rom = xmalloc (uae_u8, amax_rom_size); zfile_fread (rom, amax_rom_size, 1, z); zfile_fclose (z); write_log (_T("AMAX: '%s' loaded, %d bytes\n"), currprefs.amaxromfile, amax_rom_size); dselect = 0x20; }
struct zfile *read_rom_name (const TCHAR *filename) { int i; struct zfile *f; for (i = 0; i < romlist_cnt; i++) { if (!_tcsicmp (filename, rl[i].path)) { struct romdata *rd = rl[i].rd; f = read_rom (&rd); if (f) return f; } } f = rom_fopen (filename, L"rb", ZFD_NORMAL); if (f) { uae_u8 tmp[11]; zfile_fread (tmp, sizeof tmp, 1, f); if (!memcmp (tmp, "AMIROMTYPE1", sizeof tmp)) { struct zfile *df; int size; uae_u8 *buf; addkeydir (filename); zfile_fseek (f, 0, SEEK_END); size = zfile_ftell (f) - sizeof tmp; zfile_fseek (f, sizeof tmp, SEEK_SET); buf = xmalloc (uae_u8, size); zfile_fread (buf, size, 1, f); df = zfile_fopen_empty (f, L"tmp.rom", size); decode_cloanto_rom_do (buf, size, size); zfile_fwrite (buf, size, 1, df); zfile_fclose (f); xfree (buf); zfile_fseek (df, 0, SEEK_SET); f = df; } else { zfile_fseek (f, -((int)sizeof tmp), SEEK_CUR); } } return f; }
struct zvolume *archive_directory_lha (struct zfile *zf) { struct zvolume *zv; struct zarchive_info zai; LzHeader hdr; int i; _tzset(); zv = zvolume_alloc (zf, ArchiveFormatLHA, NULL, NULL); while (get_header(zf, &hdr)) { struct znode *zn; int method; for (i = 0; methods[i]; i++) { if (!strcmp (methods[i], hdr.method)) method = i; } memset (&zai, 0, sizeof zai); zai.name = au (hdr.name); zai.size = hdr.original_size; zai.flags = hdr.attribute; if (hdr.extend_type != 0) { zai.tv.tv_sec = hdr.unix_last_modified_stamp -= _timezone; } else { struct tm t; uae_u32 v = hdr.last_modified_stamp; t.tm_sec = (v & 0x1f) * 2; t.tm_min = (v >> 5) & 0x3f; t.tm_hour = (v >> 11) & 0x1f; t.tm_mday = (v >> 16) & 0x1f; t.tm_mon = ((v >> 21) & 0xf) - 1; t.tm_year = ((v >> 25) & 0x7f) + 80; zai.tv.tv_sec = mktime (&t) - _timezone; } if (hdr.name[strlen(hdr.name) + 1] != 0) zai.comment = au (&hdr.name[strlen(hdr.name) + 1]); if (method == LZHDIRS_METHOD_NUM) { zvolume_adddir_abs (zv, &zai); } else { zn = zvolume_addfile_abs (zv, &zai); zn->offset = zfile_ftell(zf); zn->packedsize = hdr.packed_size; zn->method = method; } xfree (zai.name); xfree (zai.comment); zfile_fseek (zf, hdr.packed_size, SEEK_CUR); } return zv; }
static int loadsample (const char *path, struct drvsample *ds) { struct zfile *f; uae_u8 *buf; int size; f = zfile_fopen (path, "rb"); if (!f) { write_log ("driveclick: can't open '%s'\n", path); return 0; } zfile_fseek (f, 0, SEEK_END); size = zfile_ftell (f); buf = malloc (size); zfile_fseek (f, 0, SEEK_SET); zfile_fread (buf, size, 1, f); zfile_fclose (f); ds->len = size; ds->p = decodewav (buf, &ds->len); free (buf); return 1; }
struct romdata *getromdatabyzfile (struct zfile *f) { int pos, size; uae_u8 *p; struct romdata *rd; pos = zfile_ftell (f); zfile_fseek (f, 0, SEEK_END); size = zfile_ftell (f); if (size > 2048 * 1024) return NULL; p = xmalloc (uae_u8, size); if (!p) return NULL; memset (p, 0, size); zfile_fseek (f, 0, SEEK_SET); zfile_fread (p, 1, size, f); zfile_fseek (f, pos, SEEK_SET); rd = getromdatabydata (p, size); xfree (p); return rd; }
uae_u32 zfile_crc32 (struct zfile *f) { uae_u8 *p; int pos, size; uae_u32 crc; if (!f) return 0; if (f->data) return get_crc32 (f->data, f->size); pos = zfile_ftell (f); zfile_fseek (f, 0, SEEK_END); size = zfile_ftell (f); p = xmalloc (size); if (!p) return 0; memset (p, 0, size); zfile_fseek (f, 0, SEEK_SET); zfile_fread (p, 1, size, f); zfile_fseek (f, pos, SEEK_SET); crc = get_crc32 (p, size); free (p); return crc; }
static struct zfile *zuncompress (struct zfile *z) { char *name = z->name; char *ext = strrchr (name, '.'); uae_u8 header[4]; if (ext != NULL) { ext++; if (strcasecmp (ext, "zip") == 0 && zlib_test ()) return unzip (z); if (strcasecmp (ext, "gz") == 0) return gunzip (z); if (strcasecmp (ext, "adz") == 0) // thinkp adz-file support return unzip (z); // thinkp adz-file support if (strcasecmp (ext, "roz") == 0) return gunzip (z); if (strcasecmp (ext, "dms") == 0) return dms (z); if (strcasecmp (ext, "lha") == 0 || strcasecmp (ext, "lzh") == 0) return lha (z); memset (header, 0, sizeof (header)); zfile_fseek (z, 0, SEEK_SET); zfile_fread (header, sizeof (header), 1, z); zfile_fseek (z, 0, SEEK_SET); if (header[0] == 0x1f && header[1] == 0x8b) return gunzip (z); if (header[0] == 'P' && header[1] == 'K') return unzip (z); if (header[0] == 'D' && header[1] == 'M' && header[2] == 'S' && header[3] == '!') return dms (z); } return z; }
static int getsub_deinterleaved (uae_u8 *dst, struct cdunit *cdu, struct cdtoc *t, int sector) { int ret = 0; uae_sem_wait (&cdu->sub_sem); if (t->subcode) { if (t->enctype == ENC_CHD) { const cdrom_track_info *cti = t->chdtrack; ret = do_read (cdu, t, dst, sector, cti->datasize, cti->subsize); if (ret) ret = t->subcode; } else if (t->subhandle) { int offset = 0; int totalsize = SUB_CHANNEL_SIZE; if (t->skipsize) { totalsize += t->size; offset = t->size; } zfile_fseek (t->subhandle, (uae_u64)sector * totalsize + t->suboffset + offset, SEEK_SET); if (zfile_fread (dst, SUB_CHANNEL_SIZE, 1, t->subhandle) > 0) ret = t->subcode; } else { memcpy (dst, t->subdata + sector * SUB_CHANNEL_SIZE + t->suboffset, SUB_CHANNEL_SIZE); ret = t->subcode; } } if (!ret) { memset (dst, 0, SUB_CHANNEL_SIZE); // regenerate Q-subchannel uae_u8 *s = dst + 12; s[0] = (t->ctrl << 4) | (t->adr << 0); s[1] = tobcd (t - &cdu->toc[0] + 1); s[2] = tobcd (1); int msf = lsn2msf (sector); tolongbcd (s + 7, msf); msf = lsn2msf (sector - t->address - 150); tolongbcd (s + 3, msf); ret = 2; } if (ret == 1) { uae_u8 tmp[SUB_CHANNEL_SIZE]; memcpy (tmp, dst, SUB_CHANNEL_SIZE); sub_to_deinterleaved (tmp, dst); ret = 2; } uae_sem_post (&cdu->sub_sem); return ret; }
static void cdtvcr_battram_write (int addr, int v) { struct zfile *f; int offset = addr & CDTVCR_RAM_MASK; if (offset >= CDTVCR_RAM_SIZE) return; gui_flicker_led (LED_MD, 0, 2); if (cdtvcr_ram[offset] == v) return; cdtvcr_ram[offset] = v; f = zfile_fopen (currprefs.flashfile, _T("rb+"), ZFD_NORMAL); if (!f) return; zfile_fseek (f, offset, SEEK_SET); zfile_fwrite (cdtvcr_ram + offset, 1, 1, f); zfile_fclose (f); }
static void addextra(TCHAR *name, struct zfile **extra, uae_u8 *p, int size) { int i; struct zfile *zf = NULL; if (!extra) return; for (i = 0; i < DMS_EXTRA_SIZE; i++) { if (!extra[i]) break; } if (i == DMS_EXTRA_SIZE) return; zf = zfile_fopen_empty (NULL, name, size); if (!zf) return; zfile_fwrite (p, size, 1, zf); zfile_fseek (zf, 0, SEEK_SET); extra[i] = zf; }
int zfile_gettype (struct zfile *z) { uae_u8 buf[8]; char *ext; if (!z) return ZFILE_UNKNOWN; ext = strrchr (z->name, '.'); if (ext != NULL) { ext++; if (strcasecmp (ext, "adf") == 0) return ZFILE_DISKIMAGE; if (strcasecmp (ext, "adz") == 0) return ZFILE_DISKIMAGE; if (strcasecmp (ext, "roz") == 0) return ZFILE_ROM; if (strcasecmp (ext, "ipf") == 0) return ZFILE_DISKIMAGE; if (strcasecmp (ext, "fdi") == 0) return ZFILE_DISKIMAGE; if (strcasecmp (ext, "uss") == 0) return ZFILE_STATEFILE; if (strcasecmp (ext, "dms") == 0) return ZFILE_DISKIMAGE; if (strcasecmp (ext, "rom") == 0) return ZFILE_ROM; if (strcasecmp (ext, "key") == 0) return ZFILE_KEY; if (strcasecmp (ext, "nvr") == 0) return ZFILE_NVR; if (strcasecmp (ext, "uae") == 0) return ZFILE_CONFIGURATION; } memset (buf, 0, sizeof (buf)); zfile_fread (buf, 8, 1, z); zfile_fseek (z, -8, SEEK_CUR); if (!memcmp (buf, exeheader, sizeof(buf))) return ZFILE_DISKIMAGE; return ZFILE_UNKNOWN; }
/* Read extra field from the current file (opened by unzOpenCurrentFile) This is the local-header version of the extra field (sometimes, there is more info in the local-header version than in the central-header) if buf==NULL, it return the size of the local extra field that can be read if buf!=NULL, len is the size of the buffer, the extra header is copied in buf. the return value is the number of bytes copied in buf, or (if <0) the error code */ extern int ZEXPORT unzGetLocalExtrafield (unzFile file, voidp buf, unsigned int len) { unz_s* s; file_in_zip_read_info_s* pfile_in_zip_read_info; uInt read_now; uLong size_to_read; if (file==NULL) return UNZ_PARAMERROR; s=(unz_s*)file; pfile_in_zip_read_info=s->pfile_in_zip_read; if (pfile_in_zip_read_info==NULL) return UNZ_PARAMERROR; size_to_read = (pfile_in_zip_read_info->size_local_extrafield - pfile_in_zip_read_info->pos_local_extrafield); if (buf==NULL) return (int)size_to_read; if (len>size_to_read) read_now = (uInt)size_to_read; else read_now = (uInt)len ; if (read_now==0) return 0; if (zfile_fseek(pfile_in_zip_read_info->file, pfile_in_zip_read_info->offset_local_extrafield + pfile_in_zip_read_info->pos_local_extrafield,SEEK_SET)!=0) return UNZ_ERRNO; if (zfile_fread(buf,(uInt)size_to_read,1,pfile_in_zip_read_info->file)!=1) return UNZ_ERRNO; return (int)read_now; }
struct zfile *archive_access_lha (struct znode *zn) { struct zfile *zf = zn->volume->archive; struct zfile *out = zfile_fopen_empty (zf, zn->name, zn->size); struct interfacing lhinterface; zfile_fseek(zf, zn->offset, SEEK_SET); lhinterface.method = zn->method; lhinterface.dicbit = 13; /* method + 8; -lh5- */ lhinterface.infile = zf; lhinterface.outfile = out; lhinterface.original = zn->size; lhinterface.packed = zn->packedsize; switch (zn->method) { case LZHUFF0_METHOD_NUM: case LARC4_METHOD_NUM: zfile_fread(out->data, zn->size, 1, zf); break; case LARC_METHOD_NUM: /* -lzs- */ lhinterface.dicbit = 11; decode(&lhinterface); break; case LZHUFF1_METHOD_NUM: /* -lh1- */ case LZHUFF4_METHOD_NUM: /* -lh4- */ case LARC5_METHOD_NUM: /* -lz5- */ lhinterface.dicbit = 12; decode(&lhinterface); break; case LZHUFF6_METHOD_NUM: /* -lh6- */ /* Added N.Watazaki (^_^) */ case LZHUFF7_METHOD_NUM: /* -lh7- */ lhinterface.dicbit = (zn->method - LZHUFF6_METHOD_NUM) + 15; default: decode(&lhinterface); } return out; }
static struct zfile *gunzip (struct zfile *z) { uae_u8 header[2 + 1 + 1 + 4 + 1 + 1]; z_stream zs; int i, size, ret, first; uae_u8 flags; long offset; char name[MAX_DPATH]; uae_u8 buffer[8192]; struct zfile *z2; uae_u8 b; if (!zlib_test ()) return z; strcpy (name, z->name); memset (&zs, 0, sizeof (zs)); memset (header, 0, sizeof (header)); zfile_fread (header, sizeof (header), 1, z); flags = header[3]; if (header[0] != 0x1f && header[1] != 0x8b) return z; if (flags & 2) /* multipart not supported */ return z; if (flags & 32) /* encryption not supported */ return z; if (flags & 4) { /* skip extra field */ zfile_fread (&b, 1, 1, z); size = b; zfile_fread (&b, 1, 1, z); size |= b << 8; zfile_fseek (z, size + 2, SEEK_CUR); } if (flags & 8) { /* get original file name */ i = 0; do { zfile_fread (name + i, 1, 1, z); } while (name[i++]); } if (flags & 16) { /* skip comment */ i = 0; do { zfile_fread (&b, 1, 1, z); } while (b); } offset = zfile_ftell (z); zfile_fseek (z, -4, SEEK_END); zfile_fread (&b, 1, 1, z); size = b; zfile_fread (&b, 1, 1, z); size |= b << 8; zfile_fread (&b, 1, 1, z); size |= b << 16; zfile_fread (&b, 1, 1, z); size |= b << 24; if (size < 8 || size > 10000000) /* safety check */ return z; zfile_fseek (z, offset, SEEK_SET); z2 = zfile_fopen_empty (name, size); if (!z2) return z; zs.next_out = z2->data; zs.avail_out = size; first = 1; do { zs.next_in = buffer; zs.avail_in = sizeof (buffer); zfile_fread (buffer, sizeof (buffer), 1, z); if (first) { if (inflateInit2 (&zs, -MAX_WBITS) != Z_OK) break; first = 0; } ret = inflate (&zs, 0); } while (ret == Z_OK); inflateEnd (&zs); if (ret != Z_STREAM_END || first != 0) { zfile_fclose (z2); return z; } zfile_fclose (z); return z2; }
static int unpack (const TCHAR *src, const TCHAR *filename, const TCHAR *dst, int out, int all, int level) { struct zdirectory *h; struct zvolume *zv; int ret; uae_u8 *b; int size; TCHAR fn[MAX_DPATH]; ret = 0; zv = zfile_fopen_archive_root (src, ZFD_ALL); if (zv == NULL) { geterror(); _tprintf (_T("Couldn't open archive '%s'\n"), src); return 0; } h = zfile_opendir_archive (src); if (!h) { geterror(); _tprintf (_T("Couldn't open directory '%s'\n"), src); return 0; } while (zfile_readdir_archive (h, fn)) { if (all || !_tcsicmp (filename, fn)) { TCHAR tmp[MAX_DPATH]; struct zfile *s, *d; struct mystat st; found = 1; _tcscpy (tmp, src); _tcscat (tmp, sep); _tcscat (tmp, fn); if (!zfile_stat_archive (tmp, &st)) { _tprintf (_T("Couldn't stat '%s'\n"), tmp); continue; } if (dst == NULL || all) dst = fn; if (st.mode) { if (all > 0) continue; if (all < 0) { TCHAR oldcur[MAX_DPATH]; my_mkdir (fn); my_setcurrentdir (fn, oldcur); unpack (tmp, fn, dst, out, all, 1); my_setcurrentdir (oldcur, NULL); setdate (dst, st.mtime.tv_sec); continue; } _tprintf (_T("Directory extraction not yet supported\n")); return 0; } s = zfile_open_archive (tmp, ZFD_ARCHIVE | ZFD_NORECURSE); if (!s) { geterror(); _tprintf (_T("Couldn't open '%s' for reading\n"), src); continue; } zfile_fseek (s, 0, SEEK_END); size = zfile_ftell (s); zfile_fseek (s, 0, SEEK_SET); b = xcalloc (uae_u8, size); if (b) { if (zfile_fread (b, size, 1, s) == 1) { if (out) { _tprintf (_T("\n")); fwrite (b, size, 1, stdout); } else { d = zfile_fopen (dst, _T("wb"), 0); if (d) { if (zfile_fwrite (b, size, 1, d) == 1) { ret = 1; _tprintf (_T("%s extracted, %d bytes\n"), dst, size); } zfile_fclose (d); setdate (dst, st.mtime.tv_sec); } } } xfree (b); } zfile_fclose (s); if (!all) break; } } geterror (); if (!found && !level) { if (filename[0]) _tprintf (_T("'%s' not found\n"), filename); else _tprintf (_T("nothing extracted\n")); } return ret; }
static int unpack2 (const TCHAR *src, const TCHAR *match, int level) { struct zdirectory *h; struct zvolume *zv; int ret; uae_u8 *b; int size; TCHAR fn[MAX_DPATH]; ret = 0; zv = zfile_fopen_archive_root (src, ZFD_ALL); if (zv == NULL) { geterror(); _tprintf (_T("Couldn't open archive '%s'\n"), src); return 0; } h = zfile_opendir_archive (src); if (!h) { geterror(); _tprintf (_T("Couldn't open directory '%s'\n"), src); return 0; } while (zfile_readdir_archive (h, fn)) { TCHAR tmp[MAX_DPATH]; TCHAR *dst; struct zfile *s, *d; int isdir, flags; _tcscpy (tmp, src); _tcscat (tmp, sep); _tcscat (tmp, fn); zfile_fill_file_attrs_archive (tmp, &isdir, &flags, NULL); if (isdir) { TCHAR *p = _tcsstr (fn, _T(".DIR")); if (isdir == ZNODE_VDIR && p && _tcslen (p) == 4) { p[0] = 0; if (pattern_match (fn, match)) continue; p[0] = '.'; } unpack2 (tmp, match, 1); continue; } if (pattern_match (fn, match)) { struct mystat st; if (!zfile_stat_archive (tmp, &st)) { st.mtime.tv_sec = st.mtime.tv_usec = -1; } found = 1; dst = fn; s = zfile_open_archive (tmp, ZFD_NORECURSE); if (!s) { geterror(); _tprintf (_T("Couldn't open '%s' for reading\n"), tmp); continue; } zfile_fseek (s, 0, SEEK_END); size = zfile_ftell (s); zfile_fseek (s, 0, SEEK_SET); b = xcalloc (uae_u8, size); if (b) { if (zfile_fread (b, size, 1, s) == 1) { d = zfile_fopen (dst, _T("wb"), 0); if (d) { if (zfile_fwrite (b, size, 1, d) == 1) { ret = 1; _tprintf (_T("%s extracted, %d bytes\n"), dst, size); } zfile_fclose (d); setdate (dst, st.mtime.tv_sec); } } xfree (b); } zfile_fclose (s); } } geterror (); if (!found && !level) { _tprintf (_T("'%s' not matched\n"), match); } return ret; }
int hdf_open_target (struct hardfiledata *hfd, const char *pname) { FILE *h = INVALID_HANDLE_VALUE; int i; struct uae_driveinfo *udi; char *name = strdup (pname); if (getenv("FS_DEBUG_HDF")) { g_debug = 1; } if (g_debug) { write_log("\n\n-- hdf_open_target pname = %s\n", pname); } hfd->flags = 0; hfd->drive_empty = 0; hdf_close (hfd); hfd->cache = (uae_u8*)xmalloc (uae_u8, CACHE_SIZE); hfd->cache_valid = 0; hfd->virtual_size = 0; hfd->virtual_rdb = NULL; if (!hfd->cache) { write_log ("VirtualAlloc(%d) failed, error %d\n", CACHE_SIZE, errno); goto end; } hfd->handle = xcalloc (struct hardfilehandle, 1); hfd->handle->h = INVALID_HANDLE_VALUE; hfd_log ("hfd open: '%s'\n", name); if (_tcslen (name) > 4 && !_tcsncmp (name,"HD_", 3)) { hdf_init_target (); i = isharddrive (name); if (i >= 0) { udi = &uae_drives[i]; hfd->flags = HFD_FLAGS_REALDRIVE; if (udi->nomedia) hfd->drive_empty = -1; if (udi->readonly) hfd->ci.readonly = 1; h = uae_tfopen (udi->device_path, hfd->ci.readonly ? "rb" : "r+b"); hfd->handle->h = h; if (h == INVALID_HANDLE_VALUE) goto end; _tcsncpy (hfd->vendor_id, udi->vendor_id, 8); _tcsncpy (hfd->product_id, udi->product_id, 16); _tcsncpy (hfd->product_rev, udi->product_rev, 4); hfd->offset = udi->offset; hfd->physsize = hfd->virtsize = udi->size; hfd->ci.blocksize = udi->bytespersector; if (hfd->offset == 0 && !hfd->drive_empty) { int sf = safetycheck (hfd->handle->h, udi->device_path, 0, hfd->cache, hfd->ci.blocksize); if (sf > 0) goto end; if (sf == 0 && !hfd->ci.readonly && harddrive_dangerous != 0x1234dead) { write_log ("'%s' forced read-only, safetycheck enabled\n", udi->device_path); hfd->dangerous = 1; // clear GENERIC_WRITE fclose (h); h = uae_tfopen (udi->device_path, "r+b"); hfd->handle->h = h; if (h == INVALID_HANDLE_VALUE) goto end; } } hfd->handle_valid = HDF_HANDLE_LINUX; hfd->emptyname = strdup (name); } else { hfd->flags = HFD_FLAGS_REALDRIVE; hfd->drive_empty = -1; hfd->emptyname = strdup (name); } } else { int zmode = 0; char *ext = _tcsrchr (name, '.'); if (ext != NULL) { ext++; for (i = 0; hdz[i]; i++) { if (!_tcsicmp (ext, hdz[i])) zmode = 1; } } h = uae_tfopen (name, hfd->ci.readonly ? "rb" : "r+b"); if (h == INVALID_HANDLE_VALUE) goto end; hfd->handle->h = h; i = _tcslen (name) - 1; while (i >= 0) { if ((i > 0 && (name[i - 1] == '/' || name[i - 1] == '\\')) || i == 0) { _tcscpy (hfd->vendor_id, "UAE"); _tcsncpy (hfd->product_id, name + i, 15); _tcscpy (hfd->product_rev, "0.3"); break; } i--; } if (h != INVALID_HANDLE_VALUE) { // determine size of hdf file int ret; off_t low = -1; #if defined(MACOSX) || defined(OPENBSD) // check type of file struct stat st; ret = stat(name,&st); if (ret) { write_log("osx: can't stat '%s'\n", name); goto end; } // block devices need special handling on BSD and OSX if (S_ISBLK(st.st_mode) || S_ISCHR(st.st_mode)) { int fh = fileno(h); #if defined(MACOSX) uint32_t block_size; uint64_t block_count; // get number of blocks ret = ioctl(fh, DKIOCGETBLOCKCOUNT, &block_count); if (ret) { write_log("osx: can't get block count of '%s' (%d)\n", name, fh); goto end; } // get block size ret = ioctl(fh, DKIOCGETBLOCKSIZE, &block_size); if (ret) { write_log("osx: can't get block size of '%s' (%d)\n", name, fh); goto end; } write_log("osx: found raw device: block_size=%u " "block_count=%llu\n", block_size, block_count); low = block_size * block_count; #elif defined(OPENBSD) struct disklabel label; if (ioctl(fh, DIOCGDINFO, &label) < 0) { write_log("openbsd: can't get disklabel of '%s' (%d)\n", name, fh); goto end; } write_log("openbsd: bytes per sector: %u\n", label.d_secsize); write_log("openbsd: sectors per unit: %u\n", label.d_secperunit); low = label.d_secsize * label.d_secperunit; write_log("openbsd: total bytes: %llu\n", low); #endif } #endif // OPENBSD || MACOSX if (low == -1) { // assuming regular file; seek to end and ftell ret = uae_fseeko64 (h, 0, SEEK_END); if (ret) goto end; low = uae_ftello64 (h); if (low == -1) goto end; } low &= ~(hfd->ci.blocksize - 1); hfd->physsize = hfd->virtsize = low; if (g_debug) { write_log("set physsize = virtsize = %lld (low)\n", hfd->virtsize); } hfd->handle_valid = HDF_HANDLE_LINUX; if (hfd->physsize < 64 * 1024 * 1024 && zmode) { write_log ("HDF '%s' re-opened in zfile-mode\n", name); fclose (h); hfd->handle->h = INVALID_HANDLE_VALUE; hfd->handle->zf = zfile_fopen(name, hfd->ci.readonly ? "rb" : "r+b", ZFD_NORMAL); hfd->handle->zfile = 1; if (!h) goto end; zfile_fseek (hfd->handle->zf, 0, SEEK_END); hfd->physsize = hfd->virtsize = zfile_ftell (hfd->handle->zf); if (g_debug) { write_log("set physsize = virtsize = %lld\n", hfd->virtsize); } zfile_fseek (hfd->handle->zf, 0, SEEK_SET); hfd->handle_valid = HDF_HANDLE_ZFILE; } } else { write_log ("HDF '%s' failed to open. error = %d\n", name, errno); } } if (hfd->handle_valid || hfd->drive_empty) { hfd_log ("HDF '%s' opened, size=%dK mode=%d empty=%d\n", name, (int) (hfd->physsize / 1024), hfd->handle_valid, hfd->drive_empty); return 1; } end: hdf_close (hfd); xfree (name); return 0; }