/** WARNING: this is duplicated in itread.c */ static int it_seek(DUMBFILE *f, long offset) { long pos = dumbfile_pos(f); if (pos > offset) return -1; if (pos < offset) if (dumbfile_skip(f, offset - pos)) return -1; return 0; }
/** WARNING: this is duplicated in itread.c */ static int it_seek(DUMBFILE *f, int32 offset) { int32 pos = dumbfile_pos(f); if (pos > offset) { return -1; } if (pos < offset) if (dumbfile_skip(f, offset - pos)) return -1; return 0; }
static int it_riff_dsmf_process_pattern( IT_PATTERN * pattern, DUMBFILE * f, int len ) { int length, row; unsigned flags; long start, end; int p, q, r; IT_ENTRY * entry; length = dumbfile_igetw( f ); if ( length > len ) return -1; len = length - 2; pattern->n_rows = 64; pattern->n_entries = 64; row = 0; start = dumbfile_pos( f ); end = start + len; while ( (row < 64) && !dumbfile_error( f ) && (dumbfile_pos( f ) < end) ) { p = dumbfile_getc( f ); if ( ! p ) { ++ row; continue; } flags = p & 0xF0; if (flags) { ++ pattern->n_entries; if (flags & 0x80) dumbfile_skip( f, 1 ); if (flags & 0x40) dumbfile_skip( f, 1 ); if (flags & 0x20) dumbfile_skip( f, 1 ); if (flags & 0x10) dumbfile_skip( f, 2 ); } } if ( pattern->n_entries == 64 ) return 0; pattern->entry = malloc( pattern->n_entries * sizeof( * pattern->entry ) ); if ( ! pattern->entry ) return -1; entry = pattern->entry; row = 0; if ( dumbfile_seek( f, start, DFS_SEEK_SET ) ) return -1; while ( ( row < 64 ) && !dumbfile_error( f ) && ( dumbfile_pos( f ) < end ) ) { p = dumbfile_getc( f ); if ( ! p ) { IT_SET_END_ROW( entry ); ++ entry; ++ row; continue; } flags = p; entry->channel = flags & 0x0F; entry->mask = 0; if ( flags & 0xF0 ) { if ( flags & 0x80 ) { q = dumbfile_getc( f ); if ( q ) { entry->mask |= IT_ENTRY_NOTE; entry->note = q - 1; } } if ( flags & 0x40 ) { q = dumbfile_getc( f ); if ( q ) { entry->mask |= IT_ENTRY_INSTRUMENT; entry->instrument = q; } } if ( flags & 0x20 ) { entry->mask |= IT_ENTRY_VOLPAN; entry->volpan = dumbfile_getc( f ); } if ( flags & 0x10 ) { q = dumbfile_getc( f ); r = dumbfile_getc( f ); _dumb_it_xm_convert_effect( q, r, entry, 0 ); } if (entry->mask) entry++; } } while ( row < 64 ) { IT_SET_END_ROW( entry ); ++ entry; ++ row; } pattern->n_entries = entry - pattern->entry; if ( ! pattern->n_entries ) return -1; return 0; }
struct riff *riff_parse(DUMBFILE *f, long offset, long size, unsigned proper) { unsigned stream_size; struct riff *stream; if (size < 8) return 0; if (dumbfile_seek(f, offset, DFS_SEEK_SET)) return 0; if (dumbfile_mgetl(f) != DUMB_ID('R', 'I', 'F', 'F')) return 0; stream_size = (int)dumbfile_igetl(f); if (stream_size + 8 > size) return 0; if (stream_size < 4) return 0; stream = (struct riff *)malloc(sizeof(struct riff)); if (!stream) return 0; stream->type = (int)dumbfile_mgetl(f); stream->chunk_count = 0; stream->chunks = 0; stream_size -= 4; while (stream_size && !dumbfile_error(f)) { struct riff_chunk *chunk; if (stream_size < 8) break; stream->chunks = (struct riff_chunk *)realloc( stream->chunks, (stream->chunk_count + 1) * sizeof(struct riff_chunk)); if (!stream->chunks) break; chunk = stream->chunks + stream->chunk_count; chunk->type = (int)dumbfile_mgetl(f); chunk->size = (int)dumbfile_igetl(f); chunk->offset = dumbfile_pos(f); stream_size -= 8; if (stream_size < chunk->size) break; if (chunk->type == DUMB_ID('R', 'I', 'F', 'F')) { chunk->nested = riff_parse(f, chunk->offset - 8, chunk->size + 8, proper); if (!chunk->nested) break; } else { chunk->nested = 0; } dumbfile_seek(f, chunk->offset + chunk->size, DFS_SEEK_SET); stream_size -= chunk->size; if (proper && (chunk->size & 1)) { dumbfile_skip(f, 1); --stream_size; } ++stream->chunk_count; } if (stream_size) { riff_free(stream); stream = 0; } return stream; }