Ejemplo n.º 1
0
static int it_asy_read_sample_header(IT_SAMPLE *sample, DUMBFILE *f) {
    int finetune, key_offset;

    /**
         21       22   Chars     Sample 1 name.  If the name is not a full
                                 22 chars in length, it will be null
                                 terminated.

    If
    the sample name begins with a '#' character (ASCII $23 (35)) then this is
    assumed not to be an instrument name, and is probably a message.
    */
    dumbfile_getnc((char *)sample->name, 22, f);
    sample->name[22] = 0;

    sample->filename[0] = 0;

    /** Each  finetune step changes  the note 1/8th  of  a  semitone. */
    finetune = (signed char)(dumbfile_getc(f) << 4) >> 4; /* signed nibble */
    sample->default_volume =
        dumbfile_getc(f); // Should we be setting global_volume to this instead?
    sample->global_volume = 64;
    if (sample->default_volume > 64)
        sample->default_volume = 64;
    key_offset = (signed char)dumbfile_getc(f); /* base key offset */
    sample->length = dumbfile_igetl(f);
    sample->loop_start = dumbfile_igetl(f);
    sample->loop_end = sample->loop_start + dumbfile_igetl(f);

    if (sample->length <= 0) {
        sample->flags = 0;
        return 0;
    }

    sample->flags = IT_SAMPLE_EXISTS;

    sample->default_pan = 0;
    sample->C5_speed =
        (int)(AMIGA_CLOCK / 214.0 *
              pow(DUMB_SEMITONE_BASE, key_offset)); //( long )( 16726.0 * pow(
                                                    // DUMB_PITCH_BASE, finetune
                                                    //* 32 ) );
    sample->finetune = finetune * 32;
    // the above line might be wrong

    if ((sample->loop_end - sample->loop_start > 2) &&
        (sample->loop_end <= sample->length))
        sample->flags |= IT_SAMPLE_LOOP;

    sample->vibrato_speed = 0;
    sample->vibrato_depth = 0;
    sample->vibrato_rate = 0;
    sample->vibrato_waveform = 0; // do we have to set _all_ these?
    sample->max_resampling_quality = -1;

    return dumbfile_error(f);
}
Ejemplo n.º 2
0
static int it_ptm_read_sample_header(IT_SAMPLE *sample, long *offset, DUMBFILE *f)
{
	int flags;

	flags = dumbfile_getc(f);

    dumbfile_getnc((char *)sample->filename, 12, f);
	sample->filename[12] = 0;

	sample->default_volume = dumbfile_getc(f);

	sample->C5_speed = dumbfile_igetw(f) << 1;

	dumbfile_skip(f, 2); /* segment */

	*offset = dumbfile_igetl(f);

	sample->length = dumbfile_igetl(f);
	sample->loop_start = dumbfile_igetl(f);
	sample->loop_end = dumbfile_igetl(f);

	/* GUSBegin, GUSLStart, GUSLEnd, GUSLoop, reserverd */
	dumbfile_skip(f, 4+4+4+1+1);

    dumbfile_getnc((char *)sample->name, 28, f);
	sample->name[28] = 0;

	/*
	if (dumbfile_mgetl(f) != DUMB_ID('P','T','M','S'))
		return -1;
	*/

	/* BLAH! Shit likes to have broken or missing sample IDs */
	dumbfile_skip(f, 4);

	if ((flags & 3) == 0) {
		/* Looks like no sample */
		sample->flags &= ~IT_SAMPLE_EXISTS;
		return dumbfile_error(f);
	}

	sample->global_volume = 64;

	sample->flags = IT_SAMPLE_EXISTS;
	if (flags & 4) sample->flags |= IT_SAMPLE_LOOP;
	if (flags & 8) sample->flags |= IT_SAMPLE_PINGPONG_LOOP;

	if (flags & 16) {
		sample->flags |= IT_SAMPLE_16BIT;

		sample->length >>= 1;
		sample->loop_start >>= 1;
		sample->loop_end >>= 1;
	}
Ejemplo n.º 3
0
/* I (entheh) have two XM files saved by a very naughty program. After a
 * 16-bit sample, it saved a rogue byte. The length of the sample was indeed
 * an odd number, incremented to include the rogue byte.
 *
 * In this function we are converting sample lengths and loop points so they
 * are measured in samples. This means we forget about the extra bytes, and
 * they don't get skipped. So we fail trying to read the next instrument.
 *
 * To get around this, this function returns the number of rogue bytes that
 * won't be accounted for by reading sample->length samples. It returns a
 * negative number on failure.
 */
static int it_xm_read_sample_header(IT_SAMPLE *sample, DUMBFILE *f)
{
	int type;
	int relative_note_number; /* relative to C4 */
	int finetune;
	int roguebytes;
	int roguebytesmask;
	int reserved;

	sample->length         = dumbfile_igetl(f);
	sample->loop_start     = dumbfile_igetl(f);
	sample->loop_end       = sample->loop_start + dumbfile_igetl(f);
	sample->global_volume  = 64;
	sample->default_volume = dumbfile_getc(f);
	finetune               = (signed char)dumbfile_getc(f); /* -128..127 <=> -1 semitone .. +127/128 of a semitone */
	type                   = dumbfile_getc(f);
	sample->default_pan    = dumbfile_getc(f); /* 0-255 */
	relative_note_number   = (signed char)dumbfile_getc(f);

	reserved = dumbfile_getc(f);

    dumbfile_getnc((char *)sample->name, 22, f);
	sample->name[22] = 0;
    trim_whitespace((char *)sample->name, 22);

	sample->filename[0] = 0;

	if (dumbfile_error(f))
		return -1;

	sample->C5_speed = (long)(16726.0*pow(DUMB_SEMITONE_BASE, relative_note_number) /**pow(DUMB_PITCH_BASE, )*/ );
	sample->finetune = finetune*2;

	sample->flags = IT_SAMPLE_EXISTS;

	if (reserved == 0xAD &&
		(!(type & (XM_SAMPLE_16BIT | XM_SAMPLE_STEREO))))
	{
		/* F U Olivier Lapicque */
		roguebytes = 4;
		roguebytesmask = 4 << 2;
	}
	else
	{
		roguebytes = (int)sample->length;
		roguebytesmask = 3;
	}

	if (type & XM_SAMPLE_16BIT) {
		sample->flags |= IT_SAMPLE_16BIT;
		sample->length >>= 1;
		sample->loop_start >>= 1;
		sample->loop_end >>= 1;
	} else
Ejemplo n.º 4
0
static void *combining_load_signal(DUH *duh, DUMBFILE *file)
{
	COMBINING_SIGNAL *signal;
	int n_signals;

	(void)duh;

	n_signals = dumbfile_getc(file);

	/* No point in combining only one signal! */
	if (dumbfile_error(file) || n_signals <= 1)
		return NULL;

	signal = malloc(sizeof(*signal) + n_signals * sizeof(*signal->sig));
	if (!signal)
		return NULL;

	signal->n_signals = n_signals;

	{
		int n;
		for (n = 0; n < signal->n_signals; n++) {
			signal->sig[n] = dumbfile_igetl(file);
			if (dumbfile_error(file)) {
				free(signal);
				return NULL;
			}
		}
	}

	return signal;
}
Ejemplo n.º 5
0
Archivo: readduh.c Proyecto: kode54/Cog
/* read_duh(): reads a DUH from an already open DUMBFILE, and returns its
 * pointer, or null on error. The file is not closed.
 */
DUH *read_duh(DUMBFILE *f) {
    DUH *duh;
    int i;

    if (dumbfile_mgetl(f) != DUH_SIGNATURE)
        return NULL;

    duh = malloc(sizeof(*duh));
    if (!duh)
        return NULL;

    duh->length = dumbfile_igetl(f);
    if (dumbfile_error(f) || duh->length <= 0) {
        free(duh);
        return NULL;
    }

    duh->n_signals = (int)dumbfile_igetl(f);
    if (dumbfile_error(f) || duh->n_signals <= 0) {
        free(duh);
        return NULL;
    }

    duh->signal = malloc(sizeof(*duh->signal) * duh->n_signals);
    if (!duh->signal) {
        free(duh);
        return NULL;
    }

    for (i = 0; i < duh->n_signals; i++)
        duh->signal[i] = NULL;

    for (i = 0; i < duh->n_signals; i++) {
        if (!(duh->signal[i] = read_signal(duh, f))) {
            unload_duh(duh);
            return NULL;
        }
    }

    return duh;
}
Ejemplo n.º 6
0
/* I (entheh) have two XM files saved by a very naughty program. After a
 * 16-bit sample, it saved a rogue byte. The length of the sample was indeed
 * an odd number, incremented to include the rogue byte.
 *
 * In this function we are converting sample lengths and loop points so they
 * are measured in samples. This means we forget about the extra bytes, and
 * they don't get skipped. So we fail trying to read the next instrument.
 *
 * To get around this, this function returns the number of rogue bytes that
 * won't be accounted for by reading sample->length samples. It returns a
 * negative number on failure.
 */
static int it_xm_read_sample_header(IT_SAMPLE *sample, DUMBFILE *f)
{
	int type;
	int relative_note_number; /* relative to C4 */
	int finetune;
	int roguebytes;
	int roguebytesmask;

	sample->length         = dumbfile_igetl(f);
	sample->loop_start     = dumbfile_igetl(f);
	sample->loop_end       = sample->loop_start + dumbfile_igetl(f);
	sample->global_volume  = 64;
	sample->default_volume = dumbfile_getc(f);
	finetune               = (signed char)dumbfile_getc(f); /* -128..127 <=> -1 semitone .. +127/128 of a semitone */
	type                   = dumbfile_getc(f);
	sample->default_pan    = dumbfile_getc(f); /* 0-255 */
	relative_note_number   = (signed char)dumbfile_getc(f);

	dumbfile_skip(f, 1);  /* reserved */

	dumbfile_getnc(sample->name, 22, f);
	sample->name[22] = 0;

	sample->filename[0] = 0;

	if (dumbfile_error(f))
		return -1;

	sample->C5_speed = (long)(16726.0*pow(DUMB_SEMITONE_BASE, relative_note_number)*pow(DUMB_PITCH_BASE, finetune*2));

	sample->flags = IT_SAMPLE_EXISTS;

	roguebytes = (int)sample->length;
	roguebytesmask = 3;

	if (type & XM_SAMPLE_16BIT) {
		sample->flags |= IT_SAMPLE_16BIT;
		sample->length >>= 1;
		sample->loop_start >>= 1;
		sample->loop_end >>= 1;
	} else
Ejemplo n.º 7
0
static void *sequence_load_signal(DUH *duh, DUMBFILE *file)
{
    long size;
    unsigned char *signal;

    (void)duh;

    size = dumbfile_igetl(file);
    if (dumbfile_error(file) || size <= 0)
        return NULL;

    signal = malloc(size);
    if (!signal)
        return NULL;

    if (dumbfile_getnc((char *)signal, size, file) < size) {
        free(signal);
        return NULL;
    }

    return signal;
}
Ejemplo n.º 8
0
static int it_xm_read_instrument(IT_INSTRUMENT *instrument, XM_INSTRUMENT_EXTRA *extra, DUMBFILE *f)
{
	unsigned long size, bytes_read;
	unsigned short vol_points[24];
	unsigned short pan_points[24];
	int i, type;
	const unsigned long max_size = 4 + 22 + 1 + 2 + 4 + 96 + 48 + 48 + 1 * 14 + 2 + 2;
	unsigned long skip_end = 0;

	/* Header size. Tends to be more than the actual size of the structure.
	 * So unread bytes must be skipped before reading the first sample
	 * header.
	 */

	if ( limit_xm_resize( f, 4 ) < 0 ) return -1;

	size = dumbfile_igetl(f);

	if ( size == 0 ) size = max_size;
	else if ( size > max_size )
	{
		skip_end = size - max_size;
		size = max_size;
	}

	if ( limit_xm_resize( f, size - 4 ) < 0 ) return -1;

    dumbfile_getnc((char *)instrument->name, 22, f);
	instrument->name[22] = 0;
    trim_whitespace((char *)instrument->name, 22);
	instrument->filename[0] = 0;
	dumbfile_skip(f, 1);  /* Instrument type. Should be 0, but seems random. */
	extra->n_samples = dumbfile_igetw(f);

	if (dumbfile_error(f) || (unsigned int)extra->n_samples > XM_MAX_SAMPLES_PER_INSTRUMENT)
		return -1;

	bytes_read = 4 + 22 + 1 + 2;

	if (extra->n_samples) {
		/* sample header size */
		/*i = dumbfile_igetl(f);
		if (!i || i > 0x28) i = 0x28;*/
		dumbfile_skip(f, 4);
		i = 0x28;
		extra->sample_header_size = i;

		/* sample map */
		for (i = 0; i < 96; i++) {
			instrument->map_sample[i] = dumbfile_getc(f) + 1;
			instrument->map_note[i] = i;
		}

		if (dumbfile_error(f))
			return 1;

		/* volume/panning envelopes */
		for (i = 0; i < 24; i++)
			vol_points[i] = dumbfile_igetw(f);
		for (i = 0; i < 24; i++)
			pan_points[i] = dumbfile_igetw(f);

		instrument->volume_envelope.n_nodes = dumbfile_getc(f);
		instrument->pan_envelope.n_nodes = dumbfile_getc(f);

		if (dumbfile_error(f))
			return -1;

		instrument->volume_envelope.sus_loop_start = dumbfile_getc(f);
		instrument->volume_envelope.loop_start = dumbfile_getc(f);
		instrument->volume_envelope.loop_end = dumbfile_getc(f);

		instrument->pan_envelope.sus_loop_start = dumbfile_getc(f);
		instrument->pan_envelope.loop_start = dumbfile_getc(f);
		instrument->pan_envelope.loop_end = dumbfile_getc(f);

		/* The envelope handler for XM files won't use sus_loop_end. */

		type = dumbfile_getc(f);
		instrument->volume_envelope.flags = 0;
		if ((type & XM_ENVELOPE_ON) && instrument->volume_envelope.n_nodes)
			instrument->volume_envelope.flags |= IT_ENVELOPE_ON;
		if (type & XM_ENVELOPE_LOOP)    instrument->volume_envelope.flags |= IT_ENVELOPE_LOOP_ON;
#if 1
		if (type & XM_ENVELOPE_SUSTAIN) instrument->volume_envelope.flags |= IT_ENVELOPE_SUSTAIN_LOOP;
#else // This is now handled in itrender.c
		/* let's avoid fading out when reaching the last envelope node */
		if (!(type & XM_ENVELOPE_LOOP)) {
			instrument->volume_envelope.loop_start = instrument->volume_envelope.n_nodes-1;
			instrument->volume_envelope.loop_end = instrument->volume_envelope.n_nodes-1;
		}
		instrument->volume_envelope.flags |= IT_ENVELOPE_LOOP_ON;
#endif

		type = dumbfile_getc(f);
		instrument->pan_envelope.flags = 0;
		if ((type & XM_ENVELOPE_ON) && instrument->pan_envelope.n_nodes)
			instrument->pan_envelope.flags |= IT_ENVELOPE_ON;
		if (type & XM_ENVELOPE_LOOP)    instrument->pan_envelope.flags |= IT_ENVELOPE_LOOP_ON; // should this be here?
		if (type & XM_ENVELOPE_SUSTAIN) instrument->pan_envelope.flags |= IT_ENVELOPE_SUSTAIN_LOOP;

		if (it_xm_make_envelope(&instrument->volume_envelope, vol_points, 0) != 0) {
			TRACE("XM error: volume envelope\n");
			if (instrument->volume_envelope.flags & IT_ENVELOPE_ON) return -1;
		}

		if (it_xm_make_envelope(&instrument->pan_envelope, pan_points, -32) != 0) {
			TRACE("XM error: pan envelope\n");
			if (instrument->pan_envelope.flags & IT_ENVELOPE_ON) return -1;
		}

		instrument->pitch_envelope.flags = 0;

		extra->vibrato_type = dumbfile_getc(f);
		extra->vibrato_sweep = dumbfile_getc(f);
		extra->vibrato_depth = dumbfile_getc(f);
		extra->vibrato_speed = dumbfile_getc(f);

		if (dumbfile_error(f) || extra->vibrato_type > 4) // XXX
			return -1;

		/** WARNING: lossy approximation */
		instrument->fadeout = (dumbfile_igetw(f)*128 + 64)/0xFFF;

		dumbfile_skip(f, 2); /* reserved */

		bytes_read += 4 + 96 + 48 + 48 + 14*1 + 2 + 2;
	} else
		for (i = 0; i < 96; i++)
			instrument->map_sample[i] = 0;

	if (size > bytes_read && dumbfile_skip(f, size - bytes_read))
		return -1;

	if (skip_end && limit_xm_skip_end(f, skip_end))
		return -1;

	instrument->new_note_action = NNA_NOTE_CUT;
	instrument->dup_check_type = DCT_OFF;
	instrument->dup_check_action = DCA_NOTE_CUT;
	instrument->pp_separation = 0;
	instrument->pp_centre = 60; /* C-5 */
	instrument->global_volume = 128;
	instrument->default_pan = 32;
	instrument->random_volume = 0;
	instrument->random_pan = 0;
	instrument->filter_cutoff = 0;
	instrument->filter_resonance = 0;

	return 0;
}
Ejemplo n.º 9
0
static int it_xm_read_pattern(IT_PATTERN *pattern, DUMBFILE *f, int n_channels, unsigned char *buffer, int version)
{
	int size;
	int pos;
	int channel;
	int row;
	int effect, effectvalue;
	IT_ENTRY *entry;

	/* pattern header size */
	if (dumbfile_igetl(f) != ( version == 0x0102 ? 0x08 : 0x09 ) ) {
		TRACE("XM error: unexpected pattern header size\n");
		return -1;
	}

	/* pattern data packing type */
	if (dumbfile_getc(f) != 0) {
		TRACE("XM error: unexpected pattern packing type\n");
		return -1;
	}

	if ( version == 0x0102 )
		pattern->n_rows = dumbfile_getc(f) + 1;
	else
		pattern->n_rows = dumbfile_igetw(f);  /* 1..256 */
	size = dumbfile_igetw(f);
	pattern->n_entries = 0;

	if (dumbfile_error(f))
		return -1;

	if (size == 0)
		return 0;

	if (size > 1280 * n_channels) {
		TRACE("XM error: pattern data size > %d bytes\n", 1280 * n_channels);
		return -1;
	}

    if (dumbfile_getnc((char *)buffer, size, f) < size)
		return -1;

	/* compute number of entries */
	pattern->n_entries = 0;
	pos = channel = row = 0;
	while (pos < size) {
		if (!(buffer[pos] & XM_ENTRY_PACKED) || (buffer[pos] & 31))
			pattern->n_entries++;

		channel++;
		if (channel >= n_channels) {
			channel = 0;
			row++;
			pattern->n_entries++;
		}

		if (buffer[pos] & XM_ENTRY_PACKED) {
			static const char offset[] = { 0, 1, 1, 2, 1, 2, 2, 3,   1, 2, 2, 3, 2, 3, 3, 4,
			                               1, 2, 2, 3, 2, 3, 3, 4,   2, 3, 3, 4, 3, 4, 4, 5 };
			pos += 1 + offset[buffer[pos] & 31];
		} else {
			pos += 5;
		}
	}

	if (row > pattern->n_rows) {
		TRACE("XM error: wrong number of rows in pattern data\n");
		return -1;
	}

	/* Whoops, looks like some modules may be short, a few channels, maybe even rows... */

	while (row < pattern->n_rows)
	{
		pattern->n_entries++;
		row++;
	}

	pattern->entry = malloc(pattern->n_entries * sizeof(*pattern->entry));
	if (!pattern->entry)
		return -1;

	/* read the entries */
	entry = pattern->entry;
	pos = channel = row = 0;
	while (pos < size) {
		unsigned char mask;

		if (buffer[pos] & XM_ENTRY_PACKED)
			mask = buffer[pos++] & 31;
		else
			mask = 31;

		if (mask) {
			ASSERT(entry < pattern->entry + pattern->n_entries);

			entry->channel = channel;
			entry->mask = 0;

			if (mask & XM_ENTRY_NOTE) {
				int note = buffer[pos++]; /* 1-96 <=> C0-B7 */
				entry->note = (note == XM_NOTE_OFF) ? (IT_NOTE_OFF) : (note-1);
				entry->mask |= IT_ENTRY_NOTE;
			}

			if (mask & XM_ENTRY_INSTRUMENT) {
				entry->instrument = buffer[pos++]; /* 1-128 */
				entry->mask |= IT_ENTRY_INSTRUMENT;
			}

			if (mask & XM_ENTRY_VOLUME)
				it_xm_convert_volume(buffer[pos++], entry);

			effect = effectvalue = 0;
			if (mask & XM_ENTRY_EFFECT)      effect = buffer[pos++];
			if (mask & XM_ENTRY_EFFECTVALUE) effectvalue = buffer[pos++];
			_dumb_it_xm_convert_effect(effect, effectvalue, entry, 0);

			entry++;
		}

		channel++;
		if (channel >= n_channels) {
			channel = 0;
			row++;
			IT_SET_END_ROW(entry);
			entry++;
		}
	}

	while (row < pattern->n_rows)
	{
		row++;
		IT_SET_END_ROW(entry);
		entry++;
	}

	return 0;
}
Ejemplo n.º 10
0
static int it_riff_dsmf_process_sample( IT_SAMPLE * sample, DUMBFILE * f, int len )
{
    int flags;

    dumbfile_getnc( (char *) sample->filename, 13, f );
    sample->filename[ 14 ] = 0;

    flags = dumbfile_igetw( f );
    sample->default_volume = dumbfile_getc( f );
    sample->length = dumbfile_igetl( f );
    sample->loop_start = dumbfile_igetl( f );
    sample->loop_end = dumbfile_igetl( f );
    dumbfile_skip( f, 32 - 28 );
    sample->C5_speed = dumbfile_igetw( f ) * 2;
    dumbfile_skip( f, 36 - 34 );
    dumbfile_getnc( (char *) sample->name, 28, f );
    sample->name[ 28 ] = 0;

    /*if ( data[ 0x38 ] || data[ 0x39 ] || data[ 0x3A ] || data[ 0x3B ] )
    	return -1;*/

    if ( ! sample->length ) {
        sample->flags &= ~IT_SAMPLE_EXISTS;
        return 0;
    }

    /*if ( flags & ~( 2 | 1 ) )
    	return -1;*/

    if ( sample->length + 64 > len )
        return -1;

    sample->flags = IT_SAMPLE_EXISTS;

    sample->default_pan = 0;
    sample->global_volume = 64;
    sample->vibrato_speed = 0;
    sample->vibrato_depth = 0;
    sample->vibrato_rate = 0;
    sample->vibrato_waveform = IT_VIBRATO_SINE;
    sample->finetune = 0;
    sample->max_resampling_quality = -1;

    if ( flags & 1 )
    {
        if (((unsigned int)sample->loop_end <= (unsigned int)sample->length) &&
                ((unsigned int)sample->loop_start < (unsigned int)sample->loop_end))
        {
            sample->length = sample->loop_end;
            sample->flags |= IT_SAMPLE_LOOP;
            if ( flags & 0x10 ) sample->flags |= IT_SAMPLE_PINGPONG_LOOP;
        }
    }

    sample->data = malloc( sample->length );
    if ( ! sample->data )
        return -1;

    dumbfile_getnc( sample->data, sample->length, f );

    if ( ! ( flags & 2 ) )
    {
        for ( flags = 0; flags < sample->length; ++flags )
            ( ( signed char * ) sample->data ) [ flags ] ^= 0x80;
    }

    return 0;
}
Ejemplo n.º 11
0
static int it_s3m_read_sample_header(IT_SAMPLE *sample, long *offset,
                                     unsigned char *pack, int cwtv,
                                     DUMBFILE *f) {
    unsigned char type;
    int flags;

    type = dumbfile_getc(f);

    dumbfile_getnc((char *)sample->filename, 12, f);
    sample->filename[12] = 0;

    if (type > 1) {
        /** WARNING: no adlib support */
        dumbfile_skip(f, 3 + 12 + 1 + 1 + 2 + 2 + 2 + 12);
        dumbfile_getnc((char *)sample->name, 28, f);
        sample->name[28] = 0;
        dumbfile_skip(f, 4);
        sample->flags &= ~IT_SAMPLE_EXISTS;
        return dumbfile_error(f);
    }

    *offset = dumbfile_getc(f) << 20;
    *offset += dumbfile_igetw(f) << 4;

    sample->length = dumbfile_igetl(f);
    sample->loop_start = dumbfile_igetl(f);
    sample->loop_end = dumbfile_igetl(f);

    sample->default_volume = dumbfile_getc(f);

    dumbfile_skip(f, 1);

    flags = dumbfile_getc(f);

    if (flags < 0 || (flags != 0 && flags != 4))
        /* Sample is packed apparently (or error reading from file). We don't
         * know how to read packed samples.
         */
        return -1;

    *pack = flags;

    flags = dumbfile_getc(f);

    sample->C5_speed = dumbfile_igetl(f) << 1;

    /* Skip four unused bytes and three internal variables. */
    dumbfile_skip(f, 4 + 2 + 2 + 4);

    dumbfile_getnc((char *)sample->name, 28, f);
    sample->name[28] = 0;

    if (type == 0 || sample->length <= 0) {
        /* Looks like no-existy. Anyway, there's for sure no 'SCRS' ... */
        sample->flags &= ~IT_SAMPLE_EXISTS;
        return dumbfile_error(f);
    }

    if (dumbfile_mgetl(f) != DUMB_ID('S', 'C', 'R', 'S'))
        return -1;

    sample->global_volume = 64;

    sample->flags = IT_SAMPLE_EXISTS;
    if (flags & 1)
        sample->flags |= IT_SAMPLE_LOOP;

    /* The ST3 TECH.DOC is unclear on this, but IMAGO Orpheus is not. Piece of
     * crap. */

    if (flags & 2) {
        sample->flags |= IT_SAMPLE_STEREO;

        if ((cwtv & 0xF000) == 0x2000) {
            sample->length >>= 1;
            sample->loop_start >>= 1;
            sample->loop_end >>= 1;
        }
Ejemplo n.º 12
0
Archivo: riff.c Proyecto: kode54/Cog
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;
}
Ejemplo n.º 13
0
static int it_s3m_read_sample_header(IT_SAMPLE *sample, long *offset, DUMBFILE *f)
{
	unsigned char type;
	int flags;

	type = dumbfile_getc(f);

	if (type > 1) {
		/** WARNING: no adlib support */
	}

	dumbfile_getnc(sample->filename, 13, f);
	sample->filename[13] = 0;

	*offset = dumbfile_igetw(f) << 4;

	sample->length = dumbfile_igetl(f);
	sample->loop_start = dumbfile_igetl(f);
	sample->loop_end = dumbfile_igetl(f);

	sample->default_volume = dumbfile_getc(f);

	dumbfile_skip(f, 1);

	if (dumbfile_getc(f) != 0)
		/* Sample is packed apparently (or error reading from file). We don't
		 * know how to read packed samples.
		 */
		return -1;

	flags = dumbfile_getc(f);

	sample->C5_speed = dumbfile_igetl(f) << 1;

	/* Skip four unused bytes and three internal variables. */
	dumbfile_skip(f, 4+2+2+4);

	dumbfile_getnc(sample->name, 28, f);
	sample->name[28] = 0;

	if (type == 0) {
		/* Looks like no-existy. Anyway, there's for sure no 'SCRS' ... */
		sample->flags &= ~IT_SAMPLE_EXISTS;
		return dumbfile_error(f);
	}

	if (dumbfile_mgetl(f) != DUMB_ID('S','C','R','S'))
		return -1;

	sample->global_volume = 64;

	sample->flags = IT_SAMPLE_EXISTS;
	if (flags & 1) sample->flags |= IT_SAMPLE_LOOP;
	if (flags & 2) sample->flags |= IT_SAMPLE_STEREO;
	if (flags & 4) sample->flags |= IT_SAMPLE_16BIT;

	sample->default_pan = 0; // 0 = don't use, or 160 = centre?

	if (sample->length <= 0)
		sample->flags &= ~IT_SAMPLE_EXISTS;
	else if (sample->flags & IT_SAMPLE_LOOP) {
		if ((unsigned int)sample->loop_end > (unsigned int)sample->length)
			sample->flags &= ~IT_SAMPLE_LOOP;
		else if ((unsigned int)sample->loop_start >= (unsigned int)sample->loop_end)
			sample->flags &= ~IT_SAMPLE_LOOP;
		else
			/* ScreamTracker seems not to save what comes after the loop end
			 * point, but rather to assume it is a duplicate of what comes at
			 * the loop start point. I am not completely sure of this though.
			 * It is easy to evade; simply truncate the sample.
			 */
			sample->length = sample->loop_end;
	}


	//Do we need to set all these?
	sample->vibrato_speed = 0;
	sample->vibrato_depth = 0;
	sample->vibrato_rate = 0;
	sample->vibrato_waveform = IT_VIBRATO_SINE;

	return dumbfile_error(f);
}
Ejemplo n.º 14
0
static sigdata_t *sample_load_sigdata(DUH *duh, DUMBFILE *file)
{
	SAMPLE_SIGDATA *sigdata;
	long size;
	long n;
	int flags;

	(void)duh;

	size = dumbfile_igetl(file);

	if (dumbfile_error(file) || size <= 0)
		return NULL;

	flags = dumbfile_getc(file);
	if (flags < 0)
		return NULL;

	sigdata = malloc(sizeof(*sigdata));
	if (!sigdata)
		return NULL;

	sigdata->samples = malloc(size * sizeof(sample_t));
	if (!sigdata->samples) {
		free(sigdata);
		return NULL;
	}

	sigdata->size = size;
	sigdata->flags = flags;

	if (sigdata->flags & (SAMPFLAG_LOOP | SAMPFLAG_XLOOP)) {
		sigdata->loop_start = dumbfile_igetl(file);

		if (dumbfile_error(file) || (unsigned long)sigdata->loop_start >= (unsigned long)size) {
			free(sigdata->samples);
			free(sigdata);
			return NULL;
		}

		if (sigdata->flags & SAMPFLAG_LOOP)
			sigdata->loop_end = size;
		else {
			sigdata->loop_end = dumbfile_igetl(file);

			if (dumbfile_error(file) || sigdata->loop_end <= sigdata->loop_start || sigdata->loop_end > size) {
				free(sigdata->samples);
				free(sigdata);
				return NULL;
			}
		}
	} else {
		sigdata->loop_start = 0;
		sigdata->loop_end = size;
	}

	if (sigdata->flags & SAMPFLAG_16BIT) {
		for (n = 0; n < size; n++) {
			int m = dumbfile_igetw(file);
			if (m < 0) {
				free(sigdata->samples);
				free(sigdata);
				return NULL;
			}
			sigdata->samples[n] = (int)(signed short)m << 8;
		}
	} else {
		for (n = 0; n < size; n++) {
			int m = dumbfile_getc(file);
			if (m < 0) {
				free(sigdata->samples);
				free(sigdata);
				return NULL;
			}
			sigdata->samples[n] = (int)(signed char)m << 16;
		}
	}

	return sigdata;
}