コード例 #1
0
ファイル: gal5_load.c プロジェクト: GenericHero/libxmp-3ds
static int gal5_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	iff_handle handle;
	int i, ret, offset;
	struct local_data data;

	LOAD_INIT();

	hio_read32b(f);	/* Skip RIFF */
	hio_read32b(f);	/* Skip size */
	hio_read32b(f);	/* Skip AM   */

	offset = hio_tell(f);

	mod->smp = mod->ins = 0;

	handle = iff_new();
	if (handle == NULL)
		return -1;

	/* IFF chunk IDs */
	ret = iff_register(handle, "INIT", get_init);		/* Galaxy 5.0 */
	ret |= iff_register(handle, "ORDR", get_ordr);
	ret |= iff_register(handle, "PATT", get_patt_cnt);
	ret |= iff_register(handle, "INST", get_inst_cnt);

	if (ret != 0)
		return -1;

	iff_set_quirk(handle, IFF_LITTLE_ENDIAN);
	iff_set_quirk(handle, IFF_SKIP_EMBEDDED);
	iff_set_quirk(handle, IFF_CHUNK_ALIGN2);

	/* Load IFF chunks */
	if (iff_load(handle, m, f, &data) < 0) {
		iff_release(handle);
		return -1;
	}

	iff_release(handle);

	mod->trk = mod->pat * mod->chn;
	mod->smp = mod->ins;

	MODULE_INFO();

	if (instrument_init(mod) < 0)
		return -1;

	if (pattern_init(mod) < 0)
		return -1;

	D_(D_INFO "Stored patterns: %d", mod->pat);
	D_(D_INFO "Stored samples: %d ", mod->smp);

	hio_seek(f, start + offset, SEEK_SET);

	handle = iff_new();
	if (handle == NULL)
		return -1;

	/* IFF chunk IDs */
	ret = iff_register(handle, "PATT", get_patt);
	ret |= iff_register(handle, "INST", get_inst);

	if (ret != 0)
		return -1;

	iff_set_quirk(handle, IFF_LITTLE_ENDIAN);
	iff_set_quirk(handle, IFF_SKIP_EMBEDDED);
	iff_set_quirk(handle, IFF_CHUNK_ALIGN2);

	/* Load IFF chunks */
	if (iff_load(handle, m, f, &data) < 0) {
		iff_release(handle);
		return -1;
	}

	iff_release(handle);

	/* Alloc missing patterns */
	for (i = 0; i < mod->pat; i++) {
		if (mod->xxp[i] == NULL) {
			if (pattern_tracks_alloc(mod, i, 64) < 0) {
				return -1;
			}
		}
	}

	for (i = 0; i < mod->chn; i++) {
		mod->xxc[i].pan = data.chn_pan[i] * 2;
	}

	m->quirk |= QUIRKS_FT2;
	m->read_event_type = READ_EVENT_FT2;

	return 0;
}
コード例 #2
0
ファイル: pt3_load.c プロジェクト: Nlcke/gideros
static int ptdt_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	int i, j;
	struct xmp_event *event;
	struct mod_header mh;
	uint8 mod_event[4];

	hio_read(&mh.name, 20, 1, f);
	for (i = 0; i < 31; i++) {
		hio_read(&mh.ins[i].name, 22, 1, f);
		mh.ins[i].size = hio_read16b(f);
		mh.ins[i].finetune = hio_read8(f);
		mh.ins[i].volume = hio_read8(f);
		mh.ins[i].loop_start = hio_read16b(f);
		mh.ins[i].loop_size = hio_read16b(f);
	}
	mh.len = hio_read8(f);
	mh.restart = hio_read8(f);
	hio_read(&mh.order, 128, 1, f);
	hio_read(&mh.magic, 4, 1, f);

	mod->ins = 31;
	mod->smp = mod->ins;
	mod->chn = 4;
	mod->len = mh.len;
	mod->rst = mh.restart;
	memcpy(mod->xxo, mh.order, 128);

	for (i = 0; i < 128; i++) {
		if (mod->xxo[i] > mod->pat)
			mod->pat = mod->xxo[i];
	}

	mod->pat++;
	mod->trk = mod->chn * mod->pat;

	if (instrument_init(mod) < 0)
		return -1;

	for (i = 0; i < mod->ins; i++) {
		if (subinstrument_alloc(mod, i, 1) < 0)
			return -1;

		mod->xxs[i].len = 2 * mh.ins[i].size;
		mod->xxs[i].lps = 2 * mh.ins[i].loop_start;
		mod->xxs[i].lpe = mod->xxs[i].lps + 2 * mh.ins[i].loop_size;
		mod->xxs[i].flg = mh.ins[i].loop_size > 1 ? XMP_SAMPLE_LOOP : 0;

		if (mod->xxs[i].len > 0)
			mod->xxi[i].nsm = 1;

		mod->xxi[i].sub[0].fin = (int8)(mh.ins[i].finetune << 4);
		mod->xxi[i].sub[0].vol = mh.ins[i].volume;
		mod->xxi[i].sub[0].pan = 0x80;
		mod->xxi[i].sub[0].sid = i;
		mod->xxi[i].rls = 0xfff;

		instrument_name(mod, i, mh.ins[i].name, 22);

		D_(D_INFO "[%2X] %-22.22s %04x %04x %04x %c V%02x %+d",
				i, mod->xxi[i].name,
				mod->xxs[i].len, mod->xxs[i].lps,
				mod->xxs[i].lpe,
				mh.ins[i].loop_size > 1 ? 'L' : ' ',
				mod->xxi[i].sub[0].vol,
				mod->xxi[i].sub[0].fin >> 4);
	}

	if (pattern_init(mod) < 0)
		return -1;

	/* Load and convert patterns */
	D_(D_INFO "Stored patterns: %d", mod->pat);

	for (i = 0; i < mod->pat; i++) {
		if (pattern_tracks_alloc(mod, i, 64) < 0)
			return -1;

		for (j = 0; j < (64 * 4); j++) {
			event = &EVENT(i, j % 4, j / 4);
			hio_read(mod_event, 1, 4, f);
			decode_protracker_event(event, mod_event);
		}
	}

	m->quirk |= QUIRK_MODRNG;

	/* Load samples */
	D_(D_INFO "Stored samples: %d", mod->smp);

	for (i = 0; i < mod->smp; i++) {
		if (!mod->xxs[i].len)
			continue;

		if (load_sample(m, f, 0, &mod->xxs[i], NULL) < 0)
			return -1;
	}

	return 0;
}
コード例 #3
0
ファイル: mod_load.c プロジェクト: GCrean/libxmp
static int mod_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
    struct xmp_module *mod = &m->mod;
    int i, j;
    int smp_size, pat_size, wow, ptsong = 0;
    struct xmp_event *event;
    struct mod_header mh;
    uint8 mod_event[4];
    char *x, pathname[PATH_MAX] = "", *tracker = "";
    int detected = 0;
    char magic[8], idbuffer[32];
    int ptkloop = 0;			/* Protracker loop */
    int tracker_id = TRACKER_PROTRACKER;

    LOAD_INIT();

    mod->ins = 31;
    mod->smp = mod->ins;
    mod->chn = 0;
    smp_size = 0;
    pat_size = 0;

    m->quirk |= QUIRK_MODRNG;

    hio_read(&mh.name, 20, 1, f);
    for (i = 0; i < 31; i++) {
	hio_read(&mh.ins[i].name, 22, 1, f);	/* Instrument name */
	mh.ins[i].size = hio_read16b(f);	/* Length in 16-bit words */
	mh.ins[i].finetune = hio_read8(f);	/* Finetune (signed nibble) */
	mh.ins[i].volume = hio_read8(f);	/* Linear playback volume */
	mh.ins[i].loop_start = hio_read16b(f);	/* Loop start in 16-bit words */
	mh.ins[i].loop_size = hio_read16b(f);	/* Loop size in 16-bit words */

	smp_size += 2 * mh.ins[i].size;
    }
    mh.len = hio_read8(f);
    mh.restart = hio_read8(f);
    hio_read(&mh.order, 128, 1, f);
    memset(magic, 0, 8);
    hio_read(magic, 4, 1, f);

    for (i = 0; mod_magic[i].ch; i++) {
	if (!(strncmp (magic, mod_magic[i].magic, 4))) {
	    mod->chn = mod_magic[i].ch;
	    tracker_id = mod_magic[i].id;
	    detected = mod_magic[i].flag;
	    break;
	}
    }

    if (!mod->chn) {
	if (!strncmp(magic + 2, "CH", 2) &&
	    isdigit((int)magic[0]) && isdigit((int)magic[1])) {
	    mod->chn = (*magic - '0') * 10 + magic[1] - '0';
	} else if (!strncmp(magic + 1, "CHN", 3) && isdigit((int)*magic)) {
	    mod->chn = *magic - '0';
	} else {
	    return -1;
	}
	tracker_id = mod->chn & 1 ? TRACKER_TAKETRACKER : TRACKER_FASTTRACKER2;
	detected = 1;
	m->quirk &= ~QUIRK_MODRNG;
    }

    strncpy(mod->name, (char *) mh.name, 20);

    mod->len = mh.len;
    /* mod->rst = mh.restart; */

    if (mod->rst >= mod->len)
	mod->rst = 0;
    memcpy(mod->xxo, mh.order, 128);

    for (i = 0; i < 128; i++) {
	/* This fixes dragnet.mod (garbage in the order list) */
	if (mod->xxo[i] > 0x7f)
		break;
	if (mod->xxo[i] > mod->pat)
	    mod->pat = mod->xxo[i];
    }
    mod->pat++;

    pat_size = 256 * mod->chn * mod->pat;

    if (instrument_init(mod) < 0)
	return -1;

    for (i = 0; i < mod->ins; i++) {
	if (subinstrument_alloc(mod, i, 1) < 0)
	    return -1;

	mod->xxs[i].len = 2 * mh.ins[i].size;
	mod->xxs[i].lps = 2 * mh.ins[i].loop_start;
	mod->xxs[i].lpe = mod->xxs[i].lps + 2 * mh.ins[i].loop_size;
	if (mod->xxs[i].lpe > mod->xxs[i].len)
		mod->xxs[i].lpe = mod->xxs[i].len;
	mod->xxs[i].flg = (mh.ins[i].loop_size > 1 && mod->xxs[i].lpe >= 4) ?
		XMP_SAMPLE_LOOP : 0;
	mod->xxi[i].sub[0].fin = (int8)(mh.ins[i].finetune << 4);
	mod->xxi[i].sub[0].vol = mh.ins[i].volume;
	mod->xxi[i].sub[0].pan = 0x80;
	mod->xxi[i].sub[0].sid = i;
	instrument_name(mod, i, mh.ins[i].name, 22);

	if (mod->xxs[i].len > 0)
		mod->xxi[i].nsm = 1;
    }

    /*
     * Experimental tracker-detection routine
     */ 

    if (detected)
	goto skip_test;

    /* Test for Flextrax modules
     *
     * FlexTrax is a soundtracker for Atari Falcon030 compatible computers.
     * FlexTrax supports the standard MOD file format (up to eight channels)
     * for compatibility reasons but also features a new enhanced module
     * format FLX. The FLX format is an extended version of the standard
     * MOD file format with support for real-time sound effects like reverb
     * and delay.
     */

    if (0x43c + mod->pat * 4 * mod->chn * 0x40 + smp_size < m->size) {
	int pos = hio_tell(f);
	hio_seek(f, start + 0x43c + mod->pat * 4 * mod->chn * 0x40 + smp_size, SEEK_SET);
	hio_read(idbuffer, 1, 4, f);
	hio_seek(f, start + pos, SEEK_SET);

	if (!memcmp(idbuffer, "FLEX", 4)) {
	    tracker_id = TRACKER_FLEXTRAX;
	    goto skip_test;
	}
    }

    /* Test for Mod's Grave WOW modules
     *
     * Stefan Danes <*****@*****.**> said:
     * This weird format is identical to '8CHN' but still uses the 'M.K.' ID.
     * You can only test for WOW by calculating the size of the module for 8 
     * channels and comparing this to the actual module length. If it's equal, 
     * the module is an 8 channel WOW.
     */

    if ((wow = (!strncmp(magic, "M.K.", 4) &&
		(0x43c + mod->pat * 32 * 0x40 + smp_size == m->size)))) {
	mod->chn = 8;
	tracker_id = TRACKER_MODSGRAVE;
	goto skip_test;
    }

    /* Test for Protracker song files
     */
    else if ((ptsong = (!strncmp((char *)magic, "M.K.", 4) &&
		(0x43c + mod->pat * 0x400 == m->size)))) {
	tracker_id = TRACKER_PROTRACKER;
	goto skip_test;
    }

    /* Test Protracker-like files
     */
    if (mod->chn == 4 && mh.restart == mod->pat) {
	tracker_id = TRACKER_SOUNDTRACKER;
    } else if (mod->chn == 4 && mh.restart == 0x78) {
        tracker_id = TRACKER_NOISETRACKER;
    } else if (mh.restart < 0x7f) {
	if (mod->chn == 4) {
	    tracker_id = TRACKER_NOISETRACKER;
	} else {
	    tracker_id = TRACKER_UNKNOWN;
	}
	mod->rst = mh.restart;
    }

    if (mod->chn != 4 && mh.restart == 0x7f) {
	tracker_id = TRACKER_SCREAMTRACKER3;
	m->quirk &= ~QUIRK_MODRNG;
	m->read_event_type = READ_EVENT_ST3;
    }

    if (mod->chn == 4 && mh.restart == 0x7f) {
	for (i = 0; i < 31; i++) {
	    if (mh.ins[i].loop_size == 0)
		break;
	}
	if (i < 31) {
	    tracker_id = TRACKER_CLONE;
	}
    }

    if (mh.restart != 0x78 && mh.restart < 0x7f) {
	for (i = 0; i < 31; i++) {
	    if (mh.ins[i].loop_size == 0)
		break;
	}
	if (i == 31) {	/* All loops are size 2 or greater */
	    for (i = 0; i < 31; i++) {
		if (mh.ins[i].size == 1 && mh.ins[i].volume == 0) {
		    tracker_id = TRACKER_CONVERTED;
		    goto skip_test;
		}
	    }

	    for (i = 0; i < 31; i++) {
	        if (is_st_ins((char *)mh.ins[i].name))
		    break;
	    }
	    if (i == 31) {	/* No st- instruments */
	        for (i = 0; i < 31; i++) {
		    if (mh.ins[i].size == 0 && mh.ins[i].loop_size == 1) {
			switch (mod->chn) {
			case 4:
			    tracker_id = TRACKER_NOISETRACKER;	/* or Octalyser */
			    break;
			case 6:
			case 8:
		            tracker_id = TRACKER_OCTALYSER;
			    break;
			default:
		            tracker_id = TRACKER_UNKNOWN;
			}
		        goto skip_test;
		    }
	        }

		if (mod->chn == 4) {
	    	    tracker_id = TRACKER_PROTRACKER;
		} else if (mod->chn == 6 || mod->chn == 8) {
	    	    tracker_id = TRACKER_FASTTRACKER;	/* FastTracker 1.01? */
		    m->quirk &= ~QUIRK_MODRNG;
		} else {
	    	    tracker_id = TRACKER_UNKNOWN;
		}
	    }
	} else {	/* Has loops with 0 size */
	    for (i = 15; i < 31; i++) {
	        if (strlen((char *)mh.ins[i].name) || mh.ins[i].size > 0)
		    break;
	    }
	    if (i == 31 && is_st_ins((char *)mh.ins[14].name)) {
		tracker_id = TRACKER_CONVERTEDST;
		goto skip_test;
	    }

	    /* Assume that Fast Tracker modules won't have ST- instruments */
	    for (i = 0; i < 31; i++) {
	        if (is_st_ins((char *)mh.ins[i].name))
		    break;
	    }
	    if (i < 31) {
		tracker_id = TRACKER_UNKNOWN_CONV;
		goto skip_test;
	    }

	    if (mod->chn == 4 || mod->chn == 6 || mod->chn == 8) {
	    	tracker_id = TRACKER_FASTTRACKER;
	        m->quirk &= ~QUIRK_MODRNG;
		goto skip_test;
	    }

	    tracker_id = TRACKER_UNKNOWN;	/* ??!? */
	}
    }

skip_test:

    switch (tracker_id) {
    case TRACKER_PROTRACKER:
	tracker = "Protracker";
	ptkloop = 1;
	break;
    case TRACKER_NOISETRACKER:
	tracker = "Noisetracker";
	ptkloop = 1;
	break;
    case TRACKER_SOUNDTRACKER:
	tracker = "Soundtracker";
	ptkloop = 1;
	break;
    case TRACKER_FASTTRACKER:
	tracker = "Fast Tracker";
	break;
    case TRACKER_FASTTRACKER2:
	tracker = "FastTracker 2";
	break;
    case TRACKER_OCTALYSER:
	tracker = "Octalyser";
	break;
    case TRACKER_TAKETRACKER:
	tracker = "TakeTracker";
	break;
    case TRACKER_DIGITALTRACKER:
	tracker = "Digital Tracker";
	break;
    case TRACKER_FLEXTRAX:
	tracker = "Flextrax";
	break;
    case TRACKER_MODSGRAVE:
	tracker = "Mod's Grave";
	break;
    case TRACKER_SCREAMTRACKER3:
	tracker = "Scream Tracker III";
	break;
    case TRACKER_UNKNOWN_CONV:
	tracker = "unknown or converted";
	break;
    case TRACKER_CONVERTEDST:
	tracker = "converted ST2.2 or earlier";
	break;
    case TRACKER_CONVERTED:
	tracker = "converted";
	break;
    case TRACKER_CLONE:
	tracker = "Protracker clone";
	break;
    default:
    case TRACKER_UNKNOWN:
	tracker = "unknown";
	break;
    }

    mod->trk = mod->chn * mod->pat;

    snprintf(mod->type, XMP_NAME_SIZE, "%s (%s)", tracker, magic);
    MODULE_INFO();

    for (i = 0; i < mod->ins; i++) {
	D_(D_INFO "[%2X] %-22.22s %04x %04x %04x %c V%02x %+d %c\n",
		i, mod->xxi[i].name,
		mod->xxs[i].len, mod->xxs[i].lps, mod->xxs[i].lpe,
		(mh.ins[i].loop_size > 1 && mod->xxs[i].lpe > 8) ?
			'L' : ' ', mod->xxi[i].sub[0].vol,
		mod->xxi[i].sub[0].fin >> 4,
		ptkloop && mod->xxs[i].lps == 0 && mh.ins[i].loop_size > 1 &&
			mod->xxs[i].len > mod->xxs[i].lpe ? '!' : ' ');
    }

    if (pattern_init(mod) < 0)
	return -1;

    /* Load and convert patterns */
    D_(D_INFO "Stored patterns: %d", mod->pat);

    for (i = 0; i < mod->pat; i++) {
	if (pattern_tracks_alloc(mod, i, 64) < 0)
	    return -1;

	for (j = 0; j < (64 * mod->chn); j++) {
	    event = &EVENT (i, j % mod->chn, j / mod->chn);
	    hio_read (mod_event, 1, 4, f);

	    switch (tracker_id) {
	    case TRACKER_NOISETRACKER:
		decode_noisetracker_event(event, mod_event);
		break;
	    case TRACKER_PROTRACKER:
	    default:
		decode_protracker_event(event, mod_event);
		break;
	    }
	}
    }

    /* Load samples */

    if (m->filename && (x = strrchr(m->filename, '/')))
	strncpy(pathname, m->filename, x - m->filename);

    D_(D_INFO "Stored samples: %d", mod->smp);

    for (i = 0; i < mod->smp; i++) {
	int flags;

	if (!mod->xxs[i].len)
	    continue;

	flags = ptkloop ? SAMPLE_FLAG_FULLREP : 0;

	if (ptsong) {
	    HIO_HANDLE *s;
	    char sn[256];
	    snprintf(sn, XMP_NAME_SIZE, "%s%s", pathname, mod->xxi[i].name);
	
	    if ((s = hio_open_file(sn, "rb"))) {
	        if (load_sample(m, s, flags, &mod->xxs[i], NULL) < 0) {
		    hio_close(s);
		    return -1;
		}
		hio_close(s);
	    }
	} else {
	    if (load_sample(m, f, flags, &mod->xxs[i], NULL) < 0)
		return -1;
	}
    }

    if (mod->chn > 4) {
	m->quirk &= ~QUIRK_MODRNG;
	m->quirk |= QUIRKS_FT2;
	m->read_event_type = READ_EVENT_FT2;
    } else if (strcmp(tracker, "Protracker") == 0) {
	m->quirk |= QUIRK_INVLOOP;
    }

    return 0;
}
コード例 #4
0
ファイル: okt_load.c プロジェクト: yulizi1937/modo_android
static int get_pbod(struct module_data *m, int size, HIO_HANDLE *f, void *parm)
{
    struct xmp_module *mod = &m->mod;
    struct local_data *data = (struct local_data *)parm;
    struct xmp_event *e;
    uint16 rows;
    int j;

    if (data->pattern >= mod->pat)
        return 0;

    if (!data->pattern) {
        if (pattern_init(mod) < 0)
            return -1;
        D_(D_INFO "Stored patterns: %d", mod->pat);
    }

    rows = hio_read16b(f);

    if (pattern_tracks_alloc(mod, data->pattern, rows) < 0)
        return -1;

    for (j = 0; j < rows * mod->chn; j++) {
        uint8 note, ins;

        e = &EVENT(data->pattern, j % mod->chn, j / mod->chn);
        memset(e, 0, sizeof(struct xmp_event));

        note = hio_read8(f);
        ins = hio_read8(f);

        if (note) {
            e->note = 48 + note;
            e->ins = 1 + ins;
        }

        e->fxt = fx[hio_read8(f)];
        e->fxp = hio_read8(f);

        if ((e->fxt == FX_VOLSET) && (e->fxp > 0x40)) {
            if (e->fxp <= 0x50) {
                e->fxt = FX_VOLSLIDE;
                e->fxp -= 0x40;
            } else if (e->fxp <= 0x60) {
                e->fxt = FX_VOLSLIDE;
                e->fxp = (e->fxp - 0x50) << 4;
            } else if (e->fxp <= 0x70) {
                e->fxt = FX_F_VSLIDE_DN;
                e->fxp = e->fxp - 0x60;
            } else if (e->fxp <= 0x80) {
                e->fxt = FX_F_VSLIDE_UP;
                e->fxp = e->fxp - 0x70;
            }
        }
        if (e->fxt == FX_ARPEGGIO)	/* Arpeggio fixup */
            e->fxp = (((24 - MSN(e->fxp)) % 12) << 4) | LSN(e->fxp);
        if (e->fxt == NONE)
            e->fxt = e->fxp = 0;
    }
    data->pattern++;

    return 0;
}
コード例 #5
0
ファイル: med3_load.c プロジェクト: GCrean/libxmp
static int med3_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	int i, j;
	uint32 mask;
	int transp, sliding;

	LOAD_INIT();

	hio_read32b(f);

	set_type(m, "MED 2.00 MED3");

	mod->ins = mod->smp = 32;

	if (instrument_init(mod) < 0)
		return -1;

	/* read instrument names */
	for (i = 0; i < 32; i++) {
		uint8 c, buf[40];
		for (j = 0; j < 40; j++) {
			c = hio_read8(f);
			buf[j] = c;
			if (c == 0)
				break;
		}
		instrument_name(mod, i, buf, 32);
		if (subinstrument_alloc(mod, i, 1) < 0)
			return -1;
	}

	/* read instrument volumes */
	mask = hio_read32b(f);
	for (i = 0; i < 32; i++, mask <<= 1) {
		mod->xxi[i].sub[0].vol = mask & MASK ? hio_read8(f) : 0;
		mod->xxi[i].sub[0].pan = 0x80;
		mod->xxi[i].sub[0].fin = 0;
		mod->xxi[i].sub[0].sid = i;
	}

	/* read instrument loops */
	mask = hio_read32b(f);
	for (i = 0; i < 32; i++, mask <<= 1) {
		mod->xxs[i].lps = mask & MASK ? hio_read16b(f) : 0;
	}

	/* read instrument loop length */
	mask = hio_read32b(f);
	for (i = 0; i < 32; i++, mask <<= 1) {
		uint32 lsiz = mask & MASK ? hio_read16b(f) : 0;
		mod->xxs[i].len = mod->xxs[i].lps + lsiz;
		mod->xxs[i].lpe = mod->xxs[i].lps + lsiz;
		mod->xxs[i].flg = lsiz > 1 ? XMP_SAMPLE_LOOP : 0;
	}

	mod->chn = 4;
	mod->pat = hio_read16b(f);
	mod->trk = mod->chn * mod->pat;

	mod->len = hio_read16b(f);
	hio_read(mod->xxo, 1, mod->len, f);
	mod->spd = hio_read16b(f);
	if (mod->spd > 10) {
		mod->bpm = 125 * mod->spd / 33;
		mod->spd = 6;
	}
	transp = hio_read8s(f);
	hio_read8(f);			/* flags */
	sliding = hio_read16b(f);	/* sliding */
	hio_read32b(f);			/* jumping mask */
	hio_seek(f, 16, SEEK_CUR);	/* rgb */

	/* read midi channels */
	mask = hio_read32b(f);
	for (i = 0; i < 32; i++, mask <<= 1) {
		if (mask & MASK)
			hio_read8(f);
	}

	/* read midi programs */
	mask = hio_read32b(f);
	for (i = 0; i < 32; i++, mask <<= 1) {
		if (mask & MASK)
			hio_read8(f);
	}
	
	MODULE_INFO();

	D_(D_INFO "Sliding: %d", sliding);
	D_(D_INFO "Play transpose: %d", transp);

	if (sliding == 6)
		m->quirk |= QUIRK_VSALL | QUIRK_PBALL;

	for (i = 0; i < 32; i++)
		mod->xxi[i].sub[0].xpo = transp;

	if (pattern_init(mod) < 0)
		return -1;

	/* Load and convert patterns */
	D_(D_INFO "Stored patterns: %d", mod->pat);

	for (i = 0; i < mod->pat; i++) {
		uint32 *conv;
		uint8 b, tracks;
		uint16 convsz;

		if (pattern_tracks_alloc(mod, i, 64) < 0)
			return -1;

		tracks = hio_read8(f);

		b = hio_read8(f);
		convsz = hio_read16b(f);
		conv = calloc(1, convsz + 16);
		if (conv == NULL)
			return -1;

                if (b & M0F_LINEMSK00)
			*conv = 0L;
                else if (b & M0F_LINEMSK0F)
			*conv = 0xffffffff;
                else
			*conv = hio_read32b(f);

                if (b & M0F_LINEMSK10)
			*(conv + 1) = 0L;
                else if (b & M0F_LINEMSK1F)
			*(conv + 1) = 0xffffffff;
                else
			*(conv + 1) = hio_read32b(f);

                if (b & M0F_FXMSK00)
			*(conv + 2) = 0L;
                else if (b & M0F_FXMSK0F)
			*(conv + 2) = 0xffffffff;
                else
			*(conv + 2) = hio_read32b(f);

                if (b & M0F_FXMSK10)
			*(conv + 3) = 0L;
                else if (b & M0F_FXMSK1F)
			*(conv + 3) = 0xffffffff;
                else
			*(conv + 3) = hio_read32b(f);

		hio_read(conv + 4, 1, convsz, f);

                if (unpack_block(m, i, (uint8 *)conv) < 0) {
			free(conv);
			return -1;
		}

		free(conv);
	}

	/* Load samples */

	D_(D_INFO "Instruments: %d", mod->ins);

	mask = hio_read32b(f);
	for (i = 0; i < 32; i++, mask <<= 1) {
		if (~mask & MASK)
			continue;

		mod->xxi[i].nsm = 1;
		mod->xxs[i].len = hio_read32b(f);

		if (mod->xxs[i].len == 0)
			mod->xxi[i].nsm = 0;

		if (hio_read16b(f))		/* type */
			continue;

		D_(D_INFO "[%2X] %-32.32s %04x %04x %04x %c V%02x ",
			i, mod->xxi[i].name, mod->xxs[i].len, mod->xxs[i].lps,
			mod->xxs[i].lpe,
			mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
			mod->xxi[i].sub[0].vol);

		if (load_sample(m, f, 0, &mod->xxs[i], NULL) < 0)
			return -1;
	}

	return 0;
}
コード例 #6
0
ファイル: coco_load.c プロジェクト: GCrean/libxmp
static int coco_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	struct xmp_event *event;
	int i, j;
	int seq_ptr, pat_ptr, smp_ptr[100];

	LOAD_INIT();

	mod->chn = hio_read8(f) & 0x3f;
	read_title(f, mod->name, 20);

	for (i = 0; i < 20; i++) {
		if (mod->name[i] == 0x0d)
			mod->name[i] = 0;
	}

	set_type(m, "Coconizer");

	mod->ins = mod->smp = hio_read8(f);
	mod->len = hio_read8(f);
	mod->pat = hio_read8(f);
	mod->trk = mod->pat * mod->chn;

	seq_ptr = hio_read32l(f);
	pat_ptr = hio_read32l(f);

	MODULE_INFO();

	if (instrument_init(mod) < 0)
		return -1;

	m->vol_table = (int *)arch_vol_table;
	m->volbase = 0xff;

	for (i = 0; i < mod->ins; i++) {
		if (subinstrument_alloc(mod, i, 1) < 0)
			return -1;

		smp_ptr[i] = hio_read32l(f);
		mod->xxs[i].len = hio_read32l(f);
		mod->xxi[i].sub[0].vol = 0xff - hio_read32l(f);
		mod->xxi[i].sub[0].pan = 0x80;
		mod->xxs[i].lps = hio_read32l(f);
                mod->xxs[i].lpe = mod->xxs[i].lps + hio_read32l(f);
		if (mod->xxs[i].lpe)
			mod->xxs[i].lpe -= 1;
		mod->xxs[i].flg = mod->xxs[i].lps > 0 ?  XMP_SAMPLE_LOOP : 0;
		hio_read(mod->xxi[i].name, 1, 11, f);
		for (j = 0; j < 11; j++) {
			if (mod->xxi[i].name[j] == 0x0d)
				mod->xxi[i].name[j] = 0;
		}
		hio_read8(f);	/* unused */
		mod->xxi[i].sub[0].sid = i;

		if (mod->xxs[i].len > 0)
			mod->xxi[i].nsm = 1;

		D_(D_INFO "[%2X] %-10.10s  %05x %05x %05x %c V%02x",
				i, mod->xxi[i].name,
				mod->xxs[i].len, mod->xxs[i].lps, mod->xxs[i].lpe,
				mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
				mod->xxi[i].sub[0].vol);
	}

	/* Sequence */

	hio_seek(f, start + seq_ptr, SEEK_SET);
	for (i = 0; ; i++) {
		uint8 x = hio_read8(f);
		if (x == 0xff)
			break;
		mod->xxo[i] = x;
	}
	for (i++; i % 4; i++)	/* for alignment */
		hio_read8(f);


	/* Patterns */

	if (pattern_init(mod) < 0)
		return -1;

	D_(D_INFO "Stored patterns: %d", mod->pat);

	for (i = 0; i < mod->pat; i++) {
		if (pattern_tracks_alloc(mod, i, 64) < 0)
			return -1;

		for (j = 0; j < (64 * mod->chn); j++) {
			event = &EVENT (i, j % mod->chn, j / mod->chn);
			event->fxp = hio_read8(f);
			event->fxt = hio_read8(f);
			event->ins = hio_read8(f);
			event->note = hio_read8(f);
			if (event->note)
				event->note += 12;

			fix_effect(event);
		}
	}

	/* Read samples */

	D_(D_INFO "Stored samples : %d", mod->smp);

	for (i = 0; i < mod->ins; i++) {
		if (mod->xxi[i].nsm == 0)
			continue;

		hio_seek(f, start + smp_ptr[i], SEEK_SET);
		if (load_sample(m, f, SAMPLE_FLAG_VIDC, &mod->xxs[i], NULL) < 0)
			return -1;
	}

	for (i = 0; i < mod->chn; i++)
		mod->xxc[i].pan = (((i + 3) / 2) % 2) * 0xff;

	return 0;
}
コード例 #7
0
ファイル: emod_load.c プロジェクト: Nlcke/gideros
static int get_emic(struct module_data *m, int size, HIO_HANDLE * f, void *parm)
{
	struct xmp_module *mod = &m->mod;
	int i, ver;
	uint8 reorder[256];

	ver = hio_read16b(f);
	hio_read(mod->name, 1, 20, f);
	hio_seek(f, 20, SEEK_CUR);
	mod->bpm = hio_read8(f);
	mod->ins = hio_read8(f);
	mod->smp = mod->ins;

	m->quirk |= QUIRK_MODRNG;

	snprintf(mod->type, XMP_NAME_SIZE, "Quadra Composer EMOD v%d", ver);
	MODULE_INFO();

	if (instrument_init(mod) < 0)
		return -1;

	for (i = 0; i < mod->ins; i++) {
		struct xmp_instrument *xxi = &mod->xxi[i];
		struct xmp_sample *xxs = &mod->xxs[i];
		struct xmp_subinstrument *sub;

		if (subinstrument_alloc(mod, i, 1) < 0)
			return -1;

		sub = &xxi->sub[0];

		hio_read8(f);	/* num */
		sub->vol = hio_read8(f);
		xxs->len = 2 * hio_read16b(f);
		hio_read(xxi->name, 1, 20, f);
		xxs->flg = hio_read8(f) & 1 ? XMP_SAMPLE_LOOP : 0;
		sub->fin = hio_read8s(f) << 4;
		xxs->lps = 2 * hio_read16b(f);
		xxs->lpe = xxs->lps + 2 * hio_read16b(f);
		hio_read32b(f);	/* ptr */

		xxi->nsm = 1;
		sub->pan = 0x80;
		sub->sid = i;

		D_(D_INFO "[%2X] %-20.20s %05x %05x %05x %c V%02x %+d",
			i, xxi->name, xxs->len, xxs->lps, xxs->lpe,
			xxs->flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
			sub->vol, sub->fin >> 4);
	}

	hio_read8(f);		/* pad */
	mod->pat = hio_read8(f);
	mod->trk = mod->pat * mod->chn;

	if (pattern_init(mod) < 0)
		return -1;

	memset(reorder, 0, 256);

	for (i = 0; i < mod->pat; i++) {
		reorder[hio_read8(f)] = i;

		if (pattern_tracks_alloc(mod, i, hio_read8(f) + 1) < 0)
			return -1;

		hio_seek(f, 20, SEEK_CUR);	/* skip name */
		hio_read32b(f);	/* ptr */
	}

	mod->len = hio_read8(f);

	D_(D_INFO "Module length: %d", mod->len);

	for (i = 0; i < mod->len; i++)
		mod->xxo[i] = reorder[hio_read8(f)];

	return 0;
}
コード例 #8
0
ファイル: mgt_load.c プロジェクト: B0rschti/libxmp-4.3.0
static int mgt_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	struct xmp_event *event;
	int i, j;
	int ver;
	int sng_ptr, seq_ptr, ins_ptr, pat_ptr, trk_ptr, smp_ptr;
	int sdata[64];

	LOAD_INIT();

	hio_read24b(f);		/* MGT */
	ver = hio_read8(f);
	hio_read32b(f);		/* MCS */

	set_type(m, "Megatracker MGT v%d.%d", MSN(ver), LSN(ver));

	mod->chn = hio_read16b(f);
	hio_read16b(f);			/* number of songs */
	mod->len = hio_read16b(f);
	mod->pat = hio_read16b(f);
	mod->trk = hio_read16b(f);
	mod->ins = mod->smp = hio_read16b(f);
	hio_read16b(f);			/* reserved */
	hio_read32b(f);			/* reserved */

	sng_ptr = hio_read32b(f);
	seq_ptr = hio_read32b(f);
	ins_ptr = hio_read32b(f);
	pat_ptr = hio_read32b(f);
	trk_ptr = hio_read32b(f);
	smp_ptr = hio_read32b(f);
	hio_read32b(f);			/* total smp len */
	hio_read32b(f);			/* unpacked trk size */

	hio_seek(f, start + sng_ptr, SEEK_SET);

	hio_read(mod->name, 1, 32, f);
	seq_ptr = hio_read32b(f);
	mod->len = hio_read16b(f);
	mod->rst = hio_read16b(f);
	mod->bpm = hio_read8(f);
	mod->spd = hio_read8(f);
	hio_read16b(f);			/* global volume */
	hio_read8(f);			/* master L */
	hio_read8(f);			/* master R */

	for (i = 0; i < mod->chn; i++) {
		hio_read16b(f);		/* pan */
	}
	
	MODULE_INFO();

	/* Sequence */

	hio_seek(f, start + seq_ptr, SEEK_SET);
	for (i = 0; i < mod->len; i++)
		mod->xxo[i] = hio_read16b(f);

	/* Instruments */

	if (instrument_init(mod) < 0)
		return -1;

	hio_seek(f, start + ins_ptr, SEEK_SET);

	for (i = 0; i < mod->ins; i++) {
		int c2spd, flags;

		if (subinstrument_alloc(mod, i , 1) < 0)
			return -1;

		hio_read(mod->xxi[i].name, 1, 32, f);
		sdata[i] = hio_read32b(f);
		mod->xxs[i].len = hio_read32b(f);
		mod->xxs[i].lps = hio_read32b(f);
		mod->xxs[i].lpe = mod->xxs[i].lps + hio_read32b(f);
		hio_read32b(f);
		hio_read32b(f);
		c2spd = hio_read32b(f);
		c2spd_to_note(c2spd, &mod->xxi[i].sub[0].xpo, &mod->xxi[i].sub[0].fin);
		mod->xxi[i].sub[0].vol = hio_read16b(f) >> 4;
		hio_read8(f);		/* vol L */
		hio_read8(f);		/* vol R */
		mod->xxi[i].sub[0].pan = 0x80;
		flags = hio_read8(f);
		mod->xxs[i].flg = flags & 0x03 ? XMP_SAMPLE_LOOP : 0;
		mod->xxs[i].flg |= flags & 0x02 ? XMP_SAMPLE_LOOP_BIDIR : 0;
		mod->xxi[i].sub[0].fin += 0 * hio_read8(f);	// FIXME
		hio_read8(f);		/* unused */
		hio_read8(f);
		hio_read8(f);
		hio_read8(f);
		hio_read16b(f);
		hio_read32b(f);
		hio_read32b(f);

		mod->xxi[i].nsm = !!mod->xxs[i].len;
		mod->xxi[i].sub[0].sid = i;
		
		D_(D_INFO "[%2X] %-32.32s %04x %04x %04x %c V%02x %5d\n",
				i, mod->xxi[i].name,
				mod->xxs[i].len, mod->xxs[i].lps, mod->xxs[i].lpe,
				mod->xxs[i].flg & XMP_SAMPLE_LOOP_BIDIR ? 'B' :
				mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
				mod->xxi[i].sub[0].vol, c2spd);
	}

	/* PATTERN_INIT - alloc extra track*/
	if (pattern_init(mod) < 0)
		return -1;

	D_(D_INFO "Stored tracks: %d", mod->trk);

	/* Tracks */

	for (i = 1; i < mod->trk; i++) {
		int offset, rows;
		uint8 b;

		hio_seek(f, start + trk_ptr + i * 4, SEEK_SET);
		offset = hio_read32b(f);
		hio_seek(f, start + offset, SEEK_SET);

		rows = hio_read16b(f);

		if (track_alloc(mod, i, rows) < 0)
			return -1;

		//printf("\n=== Track %d ===\n\n", i);
		for (j = 0; j < rows; j++) {
			uint8 note, f2p;

			b = hio_read8(f);
			j += b & 0x03;

			note = 0;
			event = &mod->xxt[i]->event[j];
			if (b & 0x04)
				note = hio_read8(f);
			if (b & 0x08)
				event->ins = hio_read8(f);
			if (b & 0x10)
				event->vol = hio_read8(f);
			if (b & 0x20)
				event->fxt = hio_read8(f);
			if (b & 0x40)
				event->fxp = hio_read8(f);
			if (b & 0x80)
				f2p = hio_read8(f);

			if (note == 1)
				event->note = XMP_KEY_OFF;
			else if (note > 11) /* adjusted to play codeine.mgt */
				event->note = note + 1;

			/* effects */
			if (event->fxt < 0x10)
				/* like amiga */ ;
			else switch (event->fxt) {
			case 0x13: 
			case 0x14: 
			case 0x15: 
			case 0x17: 
			case 0x1c: 
			case 0x1d: 
			case 0x1e: 
				event->fxt = FX_EXTENDED;
				event->fxp = ((event->fxt & 0x0f) << 4) |
							(event->fxp & 0x0f);
				break;
			default:
				event->fxt = event->fxp = 0;
			}

			/* volume and volume column effects */
			if ((event->vol >= 0x10) && (event->vol <= 0x50)) {
				event->vol -= 0x0f;
				continue;
			}

			switch (event->vol >> 4) {
			case 0x06:	/* Volume slide down */
				event->f2t = FX_VOLSLIDE_2;
				event->f2p = event->vol - 0x60;
				break;
			case 0x07:	/* Volume slide up */
				event->f2t = FX_VOLSLIDE_2;
				event->f2p = (event->vol - 0x70) << 4;
				break;
			case 0x08:	/* Fine volume slide down */
				event->f2t = FX_EXTENDED;
				event->f2p = (EX_F_VSLIDE_DN << 4) |
							(event->vol - 0x80);
				break;
			case 0x09:	/* Fine volume slide up */
				event->f2t = FX_EXTENDED;
				event->f2p = (EX_F_VSLIDE_UP << 4) |
							(event->vol - 0x90);
				break;
			case 0x0a:	/* Set vibrato speed */
				event->f2t = FX_VIBRATO;
				event->f2p = (event->vol - 0xa0) << 4;
				break;
			case 0x0b:	/* Vibrato */
				event->f2t = FX_VIBRATO;
				event->f2p = event->vol - 0xb0;
				break;
			case 0x0c:	/* Set panning */
				event->f2t = FX_SETPAN;
				event->f2p = ((event->vol - 0xc0) << 4) + 8;
				break;
			case 0x0d:	/* Pan slide left */
				event->f2t = FX_PANSLIDE;
				event->f2p = (event->vol - 0xd0) << 4;
				break;
			case 0x0e:	/* Pan slide right */
				event->f2t = FX_PANSLIDE;
				event->f2p = event->vol - 0xe0;
				break;
			case 0x0f:	/* Tone portamento */
				event->f2t = FX_TONEPORTA;
				event->f2p = (event->vol - 0xf0) << 4;
				break;
			}
	
			event->vol = 0;

			/*printf("%02x  %02x %02x %02x %02x %02x\n",
				j, event->note, event->ins, event->vol,
				event->fxt, event->fxp);*/
		}
	}

	/* Extra track */
	mod->xxt[0] = calloc(sizeof(struct xmp_track) +
			sizeof(struct xmp_event) * 64 - 1, 1);
	mod->xxt[0]->rows = 64;

	/* Read and convert patterns */
	D_(D_INFO "Stored patterns: %d", mod->pat);

	hio_seek(f, start + pat_ptr, SEEK_SET);

	for (i = 0; i < mod->pat; i++) {
		if (pattern_alloc(mod, i) < 0)
			return -1;

		mod->xxp[i]->rows = hio_read16b(f);
		for (j = 0; j < mod->chn; j++) {
			mod->xxp[i]->index[j] = hio_read16b(f) - 1;
		}
	}

	/* Read samples */

	D_(D_INFO "Stored samples: %d", mod->smp);

	for (i = 0; i < mod->ins; i++) {
		if (mod->xxi[i].nsm == 0)
			continue;

		hio_seek(f, start + sdata[i], SEEK_SET);
		if (load_sample(m, f, 0, &mod->xxs[i], NULL) < 0)
			return -1;
	}

	return 0;
}
コード例 #9
0
ファイル: hmn_load.c プロジェクト: Acidburn0zzz/libxmp
static int hmn_load(struct module_data *m, HIO_HANDLE * f, const int start)
{
	struct xmp_module *mod = &m->mod;
	int i, j;
	struct xmp_event *event;
	struct mod_header mh;
	struct mupp mupp[31];
	uint8 mod_event[4];
	int mupp_index, num_mupp;

	LOAD_INIT();

	/*
	 *    clr.b   $1c(a6) ;prog on/off
	 *    CMP.L   #'Mupp',-$16(a3,d4.l)
	 *    bne.s   noprgo
	 *    move.l  a0,-(a7)
	 *    move.b  #1,$1c(a6)      ;prog on
	 *    move.l  l697,a0
	 *    lea     $43c(a0),a0
	 *    moveq   #0,d2
	 *    move.b  -$16+$4(a3,d4.l),d2     ;pattno
	 *    mulu    #$400,d2
	 *    lea     (a0,d2.l),a0
	 *    move.l  a0,4(a6)        ;proginstr data-start
	 *    moveq   #0,d2
	 *    MOVE.B  $3C0(A0),$12(A6)
	 *    AND.B   #$7F,$12(A6)
	 *    move.b  $380(a0),d2
	 *    mulu    #$20,d2
	 *    lea     (a0,d2.w),a0
	 *    move.l  a0,$a(a6)       ;loopstartmempoi = startmempoi
	 *    move.B  $3(a3,d4.l),$13(a6)     ;volume
	 *    move.b  -$16+$5(a3,d4.l),8(a6)  ;dataloopstart
	 *    move.b  -$16+$6(a3,d4.l),9(a6)  ;dataloopend
	 *    move.w  #$10,$e(a6)     ;looplen
	 *    move.l  (a7)+,a0
	 *    MOVE.W  $12(A6),(A2)
	 *    AND.W   #$FF,(A2)
	 *    BRA.S   L505_LQ
	 */

	/*
	 * Wavetable structure is 22 * 32 byte waveforms and 32 byte
	 * wave control data with looping.
	 */
	memset(mupp, 0, 31 * sizeof (struct mupp));

	hio_read(&mh.name, 20, 1, f);
	num_mupp = 0;

	for (i = 0; i < 31; i++) {
		hio_read(&mh.ins[i].name, 22, 1, f);	/* Instrument name */
		if (memcmp(mh.ins[i].name, "Mupp", 4) == 0) {
			mupp[i].prgon = 1;
			mupp[i].pattno = mh.ins[i].name[4];
			mupp[i].dataloopstart = mh.ins[i].name[5];
			mupp[i].dataloopend = mh.ins[i].name[6];
			num_mupp++;
		}

		mh.ins[i].size = hio_read16b(f);
		mh.ins[i].finetune = hio_read8(f);
		mh.ins[i].volume = hio_read8(f);
		mh.ins[i].loop_start = hio_read16b(f);
		mh.ins[i].loop_size = hio_read16b(f);
	}
	mh.len = hio_read8(f);
	mh.restart = hio_read8(f);
	hio_read(&mh.order, 128, 1, f);
	hio_read(&mh.magic, 4, 1, f);

	mod->chn = 4;
	mod->ins = 31;
	mod->smp = mod->ins + 28 * num_mupp;
	mod->len = mh.len;
	mod->rst = mh.restart;
	memcpy(mod->xxo, mh.order, 128);

	for (i = 0; i < 128; i++) {
		if (mod->xxo[i] > mod->pat)
			mod->pat = mod->xxo[i];
	}

	mod->pat++;
	mod->trk = mod->chn * mod->pat;

	if (hmn_new_module_extras(m) != 0)
		return -1;

	strncpy(mod->name, (char *)mh.name, 20);
	set_type(m, "%s (%4.4s)", "His Master's Noise", mh.magic);
	MODULE_INFO();

	if (instrument_init(mod) < 0)
		return -1;

	for (i = 0; i < mod->ins; i++) {
		if (mupp[i].prgon) {
			mod->xxi[i].nsm = 28;
			snprintf(mod->xxi[i].name, 32,
				"Mupp %02x %02x %02x", mupp[i].pattno,
				mupp[i].dataloopstart, mupp[i].dataloopend);
			if (hmn_new_instrument_extras(&mod->xxi[i]) != 0)
				return -1;
		} else {
			mod->xxi[i].nsm = 1;
			instrument_name(mod, i, mh.ins[i].name, 22);

			mod->xxs[i].len = 2 * mh.ins[i].size;
			mod->xxs[i].lps = 2 * mh.ins[i].loop_start;
			mod->xxs[i].lpe = mod->xxs[i].lps +
						2 * mh.ins[i].loop_size;
			mod->xxs[i].flg = mh.ins[i].loop_size > 1 ?
						XMP_SAMPLE_LOOP : 0;
		}

		if (subinstrument_alloc(mod, i, mod->xxi[i].nsm) < 0)
			return -1;

		for (j = 0; j < mod->xxi[i].nsm; j++) {
			mod->xxi[i].sub[j].fin =
					-(int8)(mh.ins[i].finetune << 3);
			mod->xxi[i].sub[j].vol = mh.ins[i].volume;
			mod->xxi[i].sub[j].pan = 0x80;
			mod->xxi[i].sub[j].sid = i;
		}
	}

	if (pattern_init(mod) < 0)
		return -1;

	/* Load and convert patterns */
	D_(D_INFO "Stored patterns: %d", mod->pat);

	for (i = 0; i < mod->pat; i++) {
		if (pattern_tracks_alloc(mod, i, 64) < 0)
			return -1;

		for (j = 0; j < (64 * 4); j++) {
			event = &EVENT(i, j % 4, j / 4);
			hio_read(mod_event, 1, 4, f);
			decode_protracker_event(event, mod_event);

			switch (event->fxt) {
			case 0x07:
				event->fxt = FX_MEGAARP;
				break;
			case 0x08:
			case 0x09:
			case 0x0e:
				event->fxt = event->fxp = 0;
				break;
			}
		}
	}

	m->period_type = PERIOD_MODRNG;

	/* Load samples */

	D_(D_INFO "Stored samples: %d", mod->smp);

	for (i = 0; i < 31; i++) {
		if (load_sample(m, f, SAMPLE_FLAG_FULLREP,
						&mod->xxs[i], NULL) < 0) {
			return -1;
		}
	}


	/* Load Mupp samples */

	mupp_index = 0;
	for (i = 0; i < 31; i ++) {
		struct hmn_instrument_extras *extra =
			(struct hmn_instrument_extras *)mod->xxi[i].extra;

		if (!mupp[i].prgon)
			continue;

		hio_seek(f, start + 1084 + 1024 * mupp[i].pattno, SEEK_SET);
		for (j = 0; j < 28; j++) {
			int k = 31 + 28 * mupp_index + j;
			mod->xxi[i].sub[j].sid = k;
			mod->xxs[k].len = 32;
			mod->xxs[k].lps = 0;
			mod->xxs[k].lpe = 32;
			mod->xxs[k].flg = XMP_SAMPLE_LOOP;
			if (load_sample(m, f, 0, &mod->xxs[k], NULL) < 0)
				return -1;
		}

		extra->dataloopstart = mupp[i].dataloopstart;
		extra->dataloopend = mupp[i].dataloopend;

		hio_read(extra->data, 1, 64, f);
		hio_read(extra->progvolume, 1, 64, f);

		mupp_index++;
	}

	return 0;
}
コード例 #10
0
ファイル: no_load.c プロジェクト: GCrean/libxmp
static int no_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	struct xmp_event *event;
	int i, j, k;
	int nsize;

	LOAD_INIT();

	hio_read32b(f);			/* NO 0x00 0x00 */

	set_type(m, "Liquid Tracker");

	nsize = hio_read8(f);
	for (i = 0; i < nsize; i++) {
		uint8 x = hio_read8(f);
		if (i < XMP_NAME_SIZE)
			mod->name[i] = x;
	}

	hio_read16l(f);
	hio_read16l(f);
	hio_read16l(f);
	hio_read16l(f);
	hio_read8(f);
	mod->pat = hio_read8(f);
	hio_read8(f);
	mod->chn = hio_read8(f);
	mod->trk = mod->pat * mod->chn;
	hio_read8(f);
	hio_read16l(f);
	hio_read16l(f);
	hio_read8(f);
	mod->ins = mod->smp = 63;

	for (i = 0; i < 256; i++) {
		uint8 x = hio_read8(f);
		if (x == 0xff)
			break;
		mod->xxo[i] = x;
	}
	hio_seek(f, 255 - i, SEEK_CUR);
	mod->len = i;

	MODULE_INFO();

	if (instrument_init(mod) < 0)
		return -1;

	/* Read instrument names */
	for (i = 0; i < mod->ins; i++) {
		int hasname, c2spd;

		if (subinstrument_alloc(mod, i, 1) < 0)
			return -1;

		nsize = hio_read8(f);
		hasname = 0;
		for (j = 0; j < nsize; j++) {
			uint8 x = hio_read8(f);
			if (x != 0x20)
				hasname = 1;
			if (j < 32)
				mod->xxi[i].name[j] = x;
		}
		if (!hasname)
			mod->xxi[i].name[0] = 0;

		hio_read32l(f);
		hio_read32l(f);
		mod->xxi[i].sub[0].vol = hio_read8(f);
		c2spd = hio_read16l(f);
		mod->xxs[i].len = hio_read16l(f);
		mod->xxs[i].lps = hio_read16l(f);
		mod->xxs[i].lpe = hio_read16l(f);
		hio_read32l(f);
		hio_read16l(f);

		if (mod->xxs[i].len > 0)
			mod->xxi[i].nsm = 1;

		/*
		mod->xxs[i].lps = 0;
		mod->xxs[i].lpe = 0;
		*/
		mod->xxs[i].flg = mod->xxs[i].lpe > 0 ? XMP_SAMPLE_LOOP : 0;
		mod->xxi[i].sub[0].fin = 0;
		mod->xxi[i].sub[0].pan = 0x80;
		mod->xxi[i].sub[0].sid = i;

		D_(D_INFO "[%2X] %-22.22s  %04x %04x %04x %c V%02x %5d",
				i, mod->xxi[i].name,
				mod->xxs[i].len, mod->xxs[i].lps, mod->xxs[i].lpe,
				mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
				mod->xxi[i].sub[0].vol, c2spd);

		c2spd = 8363 * c2spd / 8448;
		c2spd_to_note(c2spd, &mod->xxi[i].sub[0].xpo, &mod->xxi[i].sub[0].fin);
	}

	if (pattern_init(mod) < 0)
		return -1;

	/* Read and convert patterns */
	D_(D_INFO "Stored patterns: %d ", mod->pat);

	for (i = 0; i < mod->pat; i++) {
		if (pattern_tracks_alloc(mod, i, 64) < 0)
			return -1;

		for (j = 0; j < mod->xxp[i]->rows; j++) {
			for (k = 0; k < mod->chn; k++) {
				uint32 x, note, ins, vol, fxt, fxp;

				event = &EVENT (i, k, j);

				x = hio_read32l(f);
				note = x & 0x0000003f;
				ins = (x & 0x00001fc0) >> 6;
				vol = (x & 0x000fe000) >> 13;
				fxt = (x & 0x00f00000) >> 20;
				fxp = (x & 0xff000000) >> 24;

				if (note != 0x3f)
					event->note = 36 + note;
				if (ins != 0x7f)
					event->ins = 1 + ins;
				if (vol != 0x7f)
					event->vol = vol;
				if (fxt != 0x0f) {
					event->fxt = fx[fxt];
					event->fxp = fxp;
				}
			}
		}
	}

	/* Read samples */
	D_(D_INFO "Stored samples: %d", mod->smp);

	for (i = 0; i < mod->ins; i++) {
		if (mod->xxs[i].len == 0)
			continue;
		if (load_sample(m, f, SAMPLE_FLAG_UNS, &mod->xxs[i], NULL) < 0)
			return -1;
	}

	m->quirk |= QUIRKS_ST3;
	m->read_event_type = READ_EVENT_ST3;

	return 0;
}
コード例 #11
0
ファイル: mmd3_load.c プロジェクト: duongbaoduy/libxmp
static int mmd3_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	int i, j, k;
	struct MMD0 header;
	struct MMD2song song;
	struct MMD1Block block;
	struct InstrHdr instr;
	struct SynthInstr synth;
	struct InstrExt exp_smp;
	struct MMD0exp expdata;
	struct xmp_event *event;
	int ver = 0;
	int smp_idx = 0;
	uint8 e[4];
	int song_offset;
	int seqtable_offset;
	int trackvols_offset;
	int trackpans_offset;
	int blockarr_offset;
	int smplarr_offset;
	int expdata_offset;
	int expsmp_offset;
	int songname_offset;
	int iinfo_offset;
	int playseq_offset;
	int pos;
	int bpm_on, bpmlen, med_8ch;

	LOAD_INIT();

	hio_read(&header.id, 4, 1, f);

	ver = *((char *)&header.id + 3) - '1' + 1;

	D_(D_WARN "load header");
	header.modlen = hio_read32b(f);
	song_offset = hio_read32b(f);
	D_(D_INFO "song_offset = 0x%08x", song_offset);
	hio_read16b(f);
	hio_read16b(f);
	blockarr_offset = hio_read32b(f);
	D_(D_INFO "blockarr_offset = 0x%08x", blockarr_offset);
	hio_read32b(f);
	smplarr_offset = hio_read32b(f);
	D_(D_INFO "smplarr_offset = 0x%08x", smplarr_offset);
	hio_read32b(f);
	expdata_offset = hio_read32b(f);
	D_(D_INFO "expdata_offset = 0x%08x", expdata_offset);
	hio_read32b(f);
	header.pstate = hio_read16b(f);
	header.pblock = hio_read16b(f);
	header.pline = hio_read16b(f);
	header.pseqnum = hio_read16b(f);
	header.actplayline = hio_read16b(f);
	header.counter = hio_read8(f);
	header.extra_songs = hio_read8(f);

	/*
	 * song structure
	 */
	D_(D_WARN "load song");
	hio_seek(f, start + song_offset, SEEK_SET);
	for (i = 0; i < 63; i++) {
		song.sample[i].rep = hio_read16b(f);
		song.sample[i].replen = hio_read16b(f);
		song.sample[i].midich = hio_read8(f);
		song.sample[i].midipreset = hio_read8(f);
		song.sample[i].svol = hio_read8(f);
		song.sample[i].strans = hio_read8s(f);
	}
	song.numblocks = hio_read16b(f);
	song.songlen = hio_read16b(f);
	D_(D_INFO "song.songlen = %d", song.songlen);
	seqtable_offset = hio_read32b(f);
	hio_read32b(f);
	trackvols_offset = hio_read32b(f);
	song.numtracks = hio_read16b(f);
	song.numpseqs = hio_read16b(f);
	trackpans_offset = hio_read32b(f);
	song.flags3 = hio_read32b(f);
	song.voladj = hio_read16b(f);
	song.channels = hio_read16b(f);
	song.mix_echotype = hio_read8(f);
	song.mix_echodepth = hio_read8(f);
	song.mix_echolen = hio_read16b(f);
	song.mix_stereosep = hio_read8(f);

	hio_seek(f, 223, SEEK_CUR);

	song.deftempo = hio_read16b(f);
	song.playtransp = hio_read8(f);
	song.flags = hio_read8(f);
	song.flags2 = hio_read8(f);
	song.tempo2 = hio_read8(f);
	for (i = 0; i < 16; i++)
		hio_read8(f);		/* reserved */
	song.mastervol = hio_read8(f);
	song.numsamples = hio_read8(f);

	/*
	 * read sequence
	 */
	hio_seek(f, start + seqtable_offset, SEEK_SET);
	playseq_offset = hio_read32b(f);
	hio_seek(f, start + playseq_offset, SEEK_SET);
	hio_seek(f, 32, SEEK_CUR);	/* skip name */
	hio_read32b(f);
	hio_read32b(f);
	mod->len = hio_read16b(f);
	for (i = 0; i < mod->len; i++)
		mod->xxo[i] = hio_read16b(f);

	/*
	 * convert header
	 */
	m->c4rate = C4_NTSC_RATE;
	m->quirk |= song.flags & FLAG_STSLIDE ? 0 : QUIRK_VSALL | QUIRK_PBALL;
	med_8ch = song.flags & FLAG_8CHANNEL;
	bpm_on = song.flags2 & FLAG2_BPM;
	bpmlen = 1 + (song.flags2 & FLAG2_BMASK);
	m->time_factor = MED_TIME_FACTOR;

	mmd_set_bpm(m, med_8ch, song.deftempo, bpm_on, bpmlen);

	mod->spd = song.tempo2;
	mod->pat = song.numblocks;
	mod->ins = song.numsamples;
	mod->rst = 0;
	mod->chn = 0;
	mod->name[0] = 0;

	/*
	 * Obtain number of samples from each instrument
	 */
	mod->smp = 0;
	for (i = 0; i < mod->ins; i++) {
		uint32 smpl_offset;
		int16 type;
		hio_seek(f, start + smplarr_offset + i * 4, SEEK_SET);
		smpl_offset = hio_read32b(f);
		if (smpl_offset == 0)
			continue;
		hio_seek(f, start + smpl_offset, SEEK_SET);
		hio_read32b(f);				/* length */
		type = hio_read16b(f);
		if (type == -1) {			/* type is synth? */
			hio_seek(f, 14, SEEK_CUR);
			mod->smp += hio_read16b(f);		/* wforms */
		} else {
			mod->smp++;
		}
	}

	/*
	 * expdata
	 */
	D_(D_WARN "load expdata");
	expdata.s_ext_entries = 0;
	expdata.s_ext_entrsz = 0;
	expdata.i_ext_entries = 0;
	expdata.i_ext_entrsz = 0;
	expsmp_offset = 0;
	iinfo_offset = 0;
	if (expdata_offset) {
		hio_seek(f, start + expdata_offset, SEEK_SET);
		hio_read32b(f);
		expsmp_offset = hio_read32b(f);
		D_(D_INFO "expsmp_offset = 0x%08x", expsmp_offset);
		expdata.s_ext_entries = hio_read16b(f);
		expdata.s_ext_entrsz = hio_read16b(f);
		hio_read32b(f);
		hio_read32b(f);
		iinfo_offset = hio_read32b(f);
		D_(D_INFO "iinfo_offset = 0x%08x", iinfo_offset);
		expdata.i_ext_entries = hio_read16b(f);
		expdata.i_ext_entrsz = hio_read16b(f);
		hio_read32b(f);
		hio_read32b(f);
		hio_read32b(f);
		hio_read32b(f);
		songname_offset = hio_read32b(f);
		D_(D_INFO "songname_offset = 0x%08x", songname_offset);
		expdata.songnamelen = hio_read32b(f);
		hio_seek(f, start + songname_offset, SEEK_SET);
		D_(D_INFO "expdata.songnamelen = %d", expdata.songnamelen);
		for (i = 0; i < expdata.songnamelen; i++) {
			if (i >= XMP_NAME_SIZE)
				break;
			mod->name[i] = hio_read8(f);
		}
	}

	/*
	 * Quickly scan patterns to check the number of channels
	 */
	D_(D_WARN "find number of channels");

	for (i = 0; i < mod->pat; i++) {
		int block_offset;

		hio_seek(f, start + blockarr_offset + i * 4, SEEK_SET);
		block_offset = hio_read32b(f);
		D_(D_INFO "block %d block_offset = 0x%08x", i, block_offset);
		if (block_offset == 0)
			continue;
		hio_seek(f, start + block_offset, SEEK_SET);

		block.numtracks = hio_read16b(f);
		block.lines = hio_read16b(f);

		if (block.numtracks > mod->chn)
			mod->chn = block.numtracks;
	}

	mod->trk = mod->pat * mod->chn;

	if (ver == 2)
	    set_type(m, "OctaMED v5 MMD2");
	else
	    set_type(m, "OctaMED Soundstudio MMD%c", '0' + ver);

	MODULE_INFO();

	D_(D_INFO "BPM mode: %s (length = %d)", bpm_on ? "on" : "off", bpmlen);
	D_(D_INFO "Song transpose : %d", song.playtransp);
	D_(D_INFO "Stored patterns: %d", mod->pat);

	/*
	 * Read and convert patterns
	 */
	D_(D_WARN "read patterns");

	if (pattern_init(mod) < 0)
		return -1;

	for (i = 0; i < mod->pat; i++) {
		int block_offset;

		hio_seek(f, start + blockarr_offset + i * 4, SEEK_SET);
		block_offset = hio_read32b(f);
		if (block_offset == 0)
			continue;
		hio_seek(f, start + block_offset, SEEK_SET);

		block.numtracks = hio_read16b(f);
		block.lines = hio_read16b(f);
		hio_read32b(f);

		if (pattern_tracks_alloc(mod, i, block.lines + 1) < 0)
			return -1;

		for (j = 0; j < mod->xxp[i]->rows; j++) {
			for (k = 0; k < block.numtracks; k++) {
				e[0] = hio_read8(f);
				e[1] = hio_read8(f);
				e[2] = hio_read8(f);
				e[3] = hio_read8(f);

				event = &EVENT(i, k, j);
				event->note = e[0] & 0x7f;
				if (event->note) {
					event->note += song.playtransp;
					if (ver == 2)
						event->note += 12;
					else
						event->note -= 12;
				};

				if (event->note < 0 || event->note >=
								XMP_MAX_KEYS)
					event->note = 0;

				event->ins = e[1] & 0x3f;

				/* Decay */
				if (event->ins && !event->note) {
					event->f2t = FX_MED_HOLD;
				}

				event->fxt = e[2];
				event->fxp = e[3];
				mmd_xlat_fx(event, bpm_on, bpmlen, med_8ch);
			}
		}
	}

	if (med_new_module_extras(m) != 0)
		return -1;

	/*
	 * Read and convert instruments and samples
	 */
	D_(D_WARN "read instruments");

	if (instrument_init(mod) < 0)
		return -1;

	D_(D_INFO "Instruments: %d", mod->ins);

	for (smp_idx = i = 0; i < mod->ins; i++) {
		int smpl_offset;
		char name[40] = "";

		hio_seek(f, start + smplarr_offset + i * 4, SEEK_SET);
		smpl_offset = hio_read32b(f);

		D_(D_INFO "sample %d smpl_offset = 0x%08x", i, smpl_offset);

		if (smpl_offset == 0)
			continue;

		hio_seek(f, start + smpl_offset, SEEK_SET);
		instr.length = hio_read32b(f);
		instr.type = hio_read16b(f);

		pos = hio_tell(f);

		if (expdata_offset && i < expdata.i_ext_entries) {
			hio_seek(f, iinfo_offset + i * expdata.i_ext_entrsz,
								SEEK_SET);
			hio_read(name, 40, 1, f);
			D_(D_INFO "[%2x] %-40.40s %d", i, name, instr.type);
		}

		exp_smp.finetune = 0;
		if (expdata_offset && i < expdata.s_ext_entries) {
			hio_seek(f, expsmp_offset + i * expdata.s_ext_entrsz,
							SEEK_SET);
			exp_smp.hold = hio_read8(f);
			exp_smp.decay = hio_read8(f);
			exp_smp.suppress_midi_off = hio_read8(f);
			exp_smp.finetune = hio_read8(f);

			if (expdata.s_ext_entrsz > 4) {	/* Octamed V5 */
				exp_smp.default_pitch = hio_read8(f);
				exp_smp.instr_flags = hio_read8(f);
			}
		}

		hio_seek(f, pos, SEEK_SET);

		if (instr.type == -2) {			/* Hybrid */
			int ret = mmd_load_hybrid_instrument(f, m, i,
				smp_idx, &synth, &exp_smp, &song.sample[i]);

			if (ret < 0)
				return -1;

			smp_idx++;

			if (mmd_alloc_tables(m, i, &synth) != 0)
				return -1;

			continue;
		}

		if (instr.type == -1) {			/* Synthetic */
			int ret = mmd_load_synth_instrument(f, m, i, smp_idx,
				&synth, &exp_smp, &song.sample[i]);

			if (ret > 0)
				continue;

			if (ret < 0)
				return -1;

			smp_idx += synth.wforms;

			if (mmd_alloc_tables(m, i, &synth) != 0)
				return -1;

			continue;
		}

		if (instr.type >= 1 && instr.type <= 6) {	/* IFFOCT */
			int ret;
			const int oct = num_oct[instr.type - 1];

			hio_seek(f, start + smpl_offset + 6, SEEK_SET);

			ret = mmd_load_iffoct_instrument(f, m, i, smp_idx,
				&instr, oct, &exp_smp, &song.sample[i]);

			if (ret < 0)
				return -1;

			smp_idx += oct;

			continue;
		}

		/* Filter out stereo samples */
		if ((instr.type & ~(S_16 | STEREO)) != 0)
			continue;

		if (instr.type == 0) {			/* Sample */
			int ret;

			hio_seek(f, start + smpl_offset + 6, SEEK_SET);

			ret = mmd_load_sampled_instrument(f, m, i, smp_idx,
				&instr, &expdata, &exp_smp, &song.sample[i],
				ver);

			if (ret < 0)
				return -1;

			smp_idx++;

			continue;
		}
	}

	hio_seek(f, start + trackvols_offset, SEEK_SET);
	for (i = 0; i < mod->chn; i++)
		mod->xxc[i].vol = hio_read8(f);;

	if (trackpans_offset) {
		hio_seek(f, start + trackpans_offset, SEEK_SET);
		for (i = 0; i < mod->chn; i++) {
			int p = 8 * hio_read8s(f);
			mod->xxc[i].pan = 0x80 + (p > 127 ? 127 : p);
		}
	} else {
		for (i = 0; i < mod->chn; i++)
			mod->xxc[i].pan = 0x80;
	}

	m->read_event_type = READ_EVENT_MED;

	return 0;
}
コード例 #12
0
ファイル: alm_load.c プロジェクト: yulizi1937/modo_android
static int alm_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
    struct xmp_module *mod = &m->mod;
    int i, j;
    struct alm_file_header afh;
    struct xmp_event *event;
    struct stat stat;
    uint8 b;
    char *basename;
    char filename[NAME_SIZE];
    char modulename[NAME_SIZE];

    LOAD_INIT();

    hio_read(&afh.id, 7, 1, f);

    if (!strncmp((char *)afh.id, "ALEYMOD", 7))		/* Version 1.0 */
        mod->spd = afh.speed / 2;

    strncpy(modulename, m->filename, NAME_SIZE);
    basename = strtok (modulename, ".");

    afh.speed = hio_read8(f);
    afh.length = hio_read8(f);
    afh.restart = hio_read8(f);
    hio_read(&afh.order, 128, 1, f);

    mod->len = afh.length;
    mod->rst = afh.restart;
    memcpy (mod->xxo, afh.order, mod->len);

    for (mod->pat = i = 0; i < mod->len; i++)
        if (mod->pat < afh.order[i])
            mod->pat = afh.order[i];
    mod->pat++;

    mod->ins = 31;
    mod->trk = mod->pat * mod->chn;
    mod->smp = mod->ins;
    m->c4rate = C4_NTSC_RATE;

    set_type(m, "Aley's Module");

    MODULE_INFO();

    if (pattern_init(mod) < 0)
        return -1;

    /* Read and convert patterns */
    D_(D_INFO "Stored patterns: %d", mod->pat);

    for (i = 0; i < mod->pat; i++) {
        if (pattern_tracks_alloc(mod, i, 64) < 0)
            return -1;

        for (j = 0; j < 64 * mod->chn; j++) {
            event = &EVENT (i, j % mod->chn, j / mod->chn);
            b = hio_read8(f);
            if (b)
                event->note = (b == 37) ? 0x61 : b + 48;
            event->ins = hio_read8(f);
        }
    }

    if (instrument_init(mod) < 0)
        return -1;

    /* Read and convert instruments and samples */

    D_(D_INFO "Loading samples: %d", mod->ins);

    for (i = 0; i < mod->ins; i++) {
        HIO_HANDLE *s;

        if (subinstrument_alloc(mod, i, 1) < 0)
            return -1;

        mod->xxi[i].sub = calloc(sizeof (struct xmp_subinstrument), 1);
        snprintf(filename, NAME_SIZE, "%s.%d", basename, i + 1);
        s = hio_open_file(filename, "rb");

        if (s == NULL)
            continue;

        mod->xxi[i].nsm = 1;

        hio_stat(s, &stat);
        b = hio_read8(s);		/* Get first octet */
        mod->xxs[i].len = stat.st_size - 5 * !b;

        if (!b) {		/* Instrument with header */
            mod->xxs[i].lps = hio_read16l(f);
            mod->xxs[i].lpe = hio_read16l(f);
            mod->xxs[i].flg = mod->xxs[i].lpe > mod->xxs[i].lps ? XMP_SAMPLE_LOOP : 0;
        } else {
            hio_seek(s, 0, SEEK_SET);
        }

        mod->xxi[i].sub[0].pan = 0x80;
        mod->xxi[i].sub[0].vol = 0x40;
        mod->xxi[i].sub[0].sid = i;

        D_(D_INFO "[%2X] %-14.14s %04x %04x %04x %c V%02x", i,
           filename, mod->xxs[i].len, mod->xxs[i].lps, mod->xxs[i].lpe,
           mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ', mod->xxi[i].sub[0].vol);

        if (load_sample(m, s, SAMPLE_FLAG_UNS, &mod->xxs[i], NULL) < 0)
            return -1;

        hio_close(s);
    }

    /* ALM is LRLR, not LRRL */
    for (i = 0; i < mod->chn; i++)
        mod->xxc[i].pan = (i % 2) * 0xff;

    return 0;
}
コード例 #13
0
ファイル: gal4_load.c プロジェクト: visy/turha
static int gal4_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	iff_handle handle;
	int i, ret, offset;
	struct local_data data;

	LOAD_INIT();

	hio_read32b(f);	/* Skip RIFF */
	hio_read32b(f);	/* Skip size */
	hio_read32b(f);	/* Skip AM   */

	offset = hio_tell(f);

	mod->smp = mod->ins = 0;

	handle = iff_new();
	if (handle == NULL)
		return -1;

	/* IFF chunk IDs */
	ret = iff_register(handle, "MAIN", get_main);
	ret |= iff_register(handle, "ORDR", get_ordr);
	ret |= iff_register(handle, "PATT", get_patt_cnt);
	ret |= iff_register(handle, "INST", get_inst_cnt);

	if (ret != 0)
		return -1;

	iff_set_quirk(handle, IFF_LITTLE_ENDIAN);
	iff_set_quirk(handle, IFF_CHUNK_TRUNC4);

	/* Load IFF chunks */
	if (iff_load(handle, m, f, &data) < 0) {
		iff_release(handle);
		return -1;
	}

	iff_release(handle);

	mod->trk = mod->pat * mod->chn;

	MODULE_INFO();

	if (instrument_init(mod) < 0)
		return -1;

	if (pattern_init(mod) < 0)
		return -1;

	D_(D_INFO "Stored patterns: %d\n", mod->pat);
	D_(D_INFO "Stored samples : %d ", mod->smp);

	hio_seek(f, start + offset, SEEK_SET);
	data.snum = 0;

	handle = iff_new();
	if (handle == NULL)
		return -1;

	/* IFF chunk IDs */
	ret = iff_register(handle, "PATT", get_patt);
	ret |= iff_register(handle, "INST", get_inst);

	if (ret != 0)
		return -1;

	iff_set_quirk(handle, IFF_LITTLE_ENDIAN);
	iff_set_quirk(handle, IFF_CHUNK_TRUNC4);

	/* Load IFF chunks */
	if (iff_load(handle, m, f, &data) < 0) {
		iff_release(handle);
		return -1;
	}

	iff_release(handle);

	for (i = 0; i < mod->chn; i++)
		mod->xxc[i].pan = 0x80;

	m->quirk |= QUIRKS_FT2;
	m->read_event_type = READ_EVENT_FT2;

	return 0;
}
コード例 #14
0
ファイル: xm_load.c プロジェクト: GCrean/libxmp
static int load_patterns(struct module_data *m, int version, HIO_HANDLE *f)
{
    struct xmp_module *mod = &m->mod;
    struct xm_pattern_header xph;
    struct xmp_event *event;
    uint8 *patbuf, *pat, b;
    int i, j, r;

    mod->pat++;
    if (pattern_init(mod) < 0)
	return -1;

    D_(D_INFO "Stored patterns: %d", mod->pat - 1);

    /* Endianism fixed by Miodrag Vallat <*****@*****.**>
     * Mon, 04 Jan 1999 11:17:20 +0100
     */
    for (i = 0; i < mod->pat - 1; i++) {
	xph.length = hio_read32l(f);
	xph.packing = hio_read8(f);
	xph.rows = version > 0x0102 ? hio_read16l(f) : hio_read8(f) + 1;
	xph.datasize = hio_read16l(f);

	r = xph.rows;
	if (r == 0)
	    r = 0x100;

	if (pattern_tracks_alloc(mod, i, r) < 0)
	    return -1;

	if (xph.datasize) {
	    pat = patbuf = calloc(1, xph.datasize);
	    if (patbuf == NULL)
		return -1;

	    hio_read(patbuf, 1, xph.datasize, f);
	    for (j = 0; j < (mod->chn * r); j++) {
		if ((pat - patbuf) >= xph.datasize)
		    break;
		event = &EVENT(i, j % mod->chn, j / mod->chn);
		if ((b = *pat++) & XM_EVENT_PACKING) {
		    if (b & XM_EVENT_NOTE_FOLLOWS)
			event->note = *pat++;
		    if (b & XM_EVENT_INSTRUMENT_FOLLOWS)
			event->ins = *pat++;
		    if (b & XM_EVENT_VOLUME_FOLLOWS)
			event->vol = *pat++;
		    if (b & XM_EVENT_FXTYPE_FOLLOWS) {
			event->fxt = *pat++;
#if 0
			if (event->fxt == FX_GLOBALVOL)
			    event->fxt = FX_TRK_VOL;
			if (event->fxt == FX_G_VOLSLIDE)
			    event->fxt = FX_TRK_VSLIDE;
#endif
		    }
		    if (b & XM_EVENT_FXPARM_FOLLOWS)
			event->fxp = *pat++;
		} else {
		    event->note = b;
		    event->ins = *pat++;
		    event->vol = *pat++;
		    event->fxt = *pat++;
		    event->fxp = *pat++;
		}

		if (event->note == 0x61)
		    event->note = XMP_KEY_OFF;
		else if (event->note > 0)
		    event->note += 12;

		if (!event->vol)
		    continue;

		/* Volume set */
		if ((event->vol >= 0x10) && (event->vol <= 0x50)) {
		    event->vol -= 0x0f;
		    continue;
		}
		/* Volume column effects */
		switch (event->vol >> 4) {
		case 0x06:	/* Volume slide down */
		    event->f2t = FX_VOLSLIDE_2;
		    event->f2p = event->vol - 0x60;
		    break;
		case 0x07:	/* Volume slide up */
		    event->f2t = FX_VOLSLIDE_2;
		    event->f2p = (event->vol - 0x70) << 4;
		    break;
		case 0x08:	/* Fine volume slide down */
		    event->f2t = FX_EXTENDED;
		    event->f2p = (EX_F_VSLIDE_DN << 4) | (event->vol - 0x80);
		    break;
		case 0x09:	/* Fine volume slide up */
		    event->f2t = FX_EXTENDED;
		    event->f2p = (EX_F_VSLIDE_UP << 4) | (event->vol - 0x90);
		    break;
		case 0x0a:	/* Set vibrato speed */
		    event->f2t = FX_VIBRATO;
		    event->f2p = (event->vol - 0xa0) << 4;
		    break;
		case 0x0b:	/* Vibrato */
		    event->f2t = FX_VIBRATO;
		    event->f2p = event->vol - 0xb0;
		    break;
		case 0x0c:	/* Set panning */
		    event->f2t = FX_SETPAN;
		    event->f2p = ((event->vol - 0xc0) << 4) + 8;
		    break;
		case 0x0d:	/* Pan slide left */
		    event->f2t = FX_PANSLIDE;
		    event->f2p = (event->vol - 0xd0) << 4;
		    break;
		case 0x0e:	/* Pan slide right */
		    event->f2t = FX_PANSLIDE;
		    event->f2p = event->vol - 0xe0;
		    break;
		case 0x0f:	/* Tone portamento */
		    event->f2t = FX_TONEPORTA;
		    event->f2p = (event->vol - 0xf0) << 4;
		    break;
		}
		event->vol = 0;
	    }
	    free (patbuf);
	}
    }
コード例 #15
0
ファイル: stx_load.c プロジェクト: Justasic/libxmp
static int stx_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
    struct xmp_module *mod = &m->mod;
    int c, r, i, broken = 0;
    struct xmp_event *event = 0, dummy;
    struct stx_file_header sfh;
    struct stx_instrument_header sih;
    uint8 n, b;
    uint16 x16;
    int bmod2stm = 0;
    uint16 *pp_ins;		/* Parapointers to instruments */
    uint16 *pp_pat;		/* Parapointers to patterns */

    LOAD_INIT();

    hio_read(&sfh.name, 20, 1, f);
    hio_read(&sfh.magic, 8, 1, f);
    sfh.psize = hio_read16l(f);
    sfh.unknown1 = hio_read16l(f);
    sfh.pp_pat = hio_read16l(f);
    sfh.pp_ins = hio_read16l(f);
    sfh.pp_chn = hio_read16l(f);
    sfh.unknown2 = hio_read16l(f);
    sfh.unknown3 = hio_read16l(f);
    sfh.gvol = hio_read8(f);
    sfh.tempo = hio_read8(f);
    sfh.unknown4 = hio_read16l(f);
    sfh.unknown5 = hio_read16l(f);
    sfh.patnum = hio_read16l(f);
    sfh.insnum = hio_read16l(f);
    sfh.ordnum = hio_read16l(f);
    sfh.unknown6 = hio_read16l(f);
    sfh.unknown7 = hio_read16l(f);
    sfh.unknown8 = hio_read16l(f);
    hio_read(&sfh.magic2, 4, 1, f);

    /* Sanity check */
    if (sfh.patnum > 254 || sfh.insnum > 256 || sfh.ordnum > 256)
	return -1;

    /* BMOD2STM does not convert pitch */
    if (!strncmp ((char *) sfh.magic, "BMOD2STM", 8))
	bmod2stm = 1;

#if 0
    if ((strncmp ((char *) sfh.magic, "!Scream!", 8) &&
	!bmod2stm) || strncmp ((char *) sfh.magic2, "SCRM", 4))
	return -1;
#endif

    mod->ins = sfh.insnum;
    mod->pat = sfh.patnum;
    mod->trk = mod->pat * mod->chn;
    mod->len = sfh.ordnum;
    mod->spd = MSN (sfh.tempo);
    mod->smp = mod->ins;
    m->c4rate = C4_NTSC_RATE;

    /* STM2STX 1.0 released with STMIK 0.2 converts STMs with the pattern
     * length encoded in the first two bytes of the pattern (like S3M).
     */
    hio_seek(f, start + (sfh.pp_pat << 4), SEEK_SET);
    x16 = hio_read16l(f);
    hio_seek(f, start + (x16 << 4), SEEK_SET);
    x16 = hio_read16l(f);
    if (x16 == sfh.psize)
	broken = 1;

    strncpy(mod->name, (char *)sfh.name, 20);
    if (bmod2stm)
	set_type(m, "BMOD2STM STX");
    else
	snprintf(mod->type, XMP_NAME_SIZE, "STM2STX 1.%d", broken ? 0 : 1);

    MODULE_INFO();
 
    pp_pat = calloc (2, mod->pat);
    if (pp_pat == NULL)
	goto err;

    pp_ins = calloc (2, mod->ins);
    if (pp_ins == NULL)
	goto err2;

    /* Read pattern pointers */
    hio_seek(f, start + (sfh.pp_pat << 4), SEEK_SET);
    for (i = 0; i < mod->pat; i++)
	pp_pat[i] = hio_read16l(f);

    /* Read instrument pointers */
    hio_seek(f, start + (sfh.pp_ins << 4), SEEK_SET);
    for (i = 0; i < mod->ins; i++)
	pp_ins[i] = hio_read16l(f);

    /* Skip channel table (?) */
    hio_seek(f, start + (sfh.pp_chn << 4) + 32, SEEK_SET);

    /* Read orders */
    for (i = 0; i < mod->len; i++) {
	mod->xxo[i] = hio_read8(f);
	hio_seek(f, 4, SEEK_CUR);
    }
 
    if (instrument_init(mod) < 0)
	goto err3;

    /* Read and convert instruments and samples */

    for (i = 0; i < mod->ins; i++) {
	if (subinstrument_alloc(mod, i, 1) < 0)
	    goto err3;

	hio_seek(f, start + (pp_ins[i] << 4), SEEK_SET);

	sih.type = hio_read8(f);
	hio_read(&sih.dosname, 13, 1, f);
	sih.memseg = hio_read16l(f);
	sih.length = hio_read32l(f);
	sih.loopbeg = hio_read32l(f);
	sih.loopend = hio_read32l(f);
	sih.vol = hio_read8(f);
	sih.rsvd1 = hio_read8(f);
	sih.pack = hio_read8(f);
	sih.flags = hio_read8(f);
	sih.c2spd = hio_read16l(f);
	sih.rsvd2 = hio_read16l(f);
	hio_read(&sih.rsvd3, 4, 1, f);
	sih.int_gp = hio_read16l(f);
	sih.int_512 = hio_read16l(f);
	sih.int_last = hio_read32l(f);
	hio_read(&sih.name, 28, 1, f);
	hio_read(&sih.magic, 4, 1, f);

	mod->xxs[i].len = sih.length;
	mod->xxs[i].lps = sih.loopbeg;
	mod->xxs[i].lpe = sih.loopend;
	if (mod->xxs[i].lpe == 0xffff)
	    mod->xxs[i].lpe = 0;
	mod->xxs[i].flg = mod->xxs[i].lpe > 0 ? XMP_SAMPLE_LOOP : 0;
	mod->xxi[i].sub[0].vol = sih.vol;
	mod->xxi[i].sub[0].pan = 0x80;
	mod->xxi[i].sub[0].sid = i;
	mod->xxi[i].nsm = 1;

	instrument_name(mod, i, sih.name, 12);

	D_(D_INFO "[%2X] %-14.14s %04x %04x %04x %c V%02x %5d\n", i,
		mod->xxi[i].name, mod->xxs[i].len, mod->xxs[i].lps, mod->xxs[i].lpe,
		mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
		mod->xxi[i].sub[0].vol, sih.c2spd);

	sih.c2spd = 8363 * sih.c2spd / 8448;
	c2spd_to_note(sih.c2spd, &mod->xxi[i].sub[0].xpo, &mod->xxi[i].sub[0].fin);
    }

    if (pattern_init(mod) < 0)
	goto err3;

    /* Read and convert patterns */
    D_(D_INFO "Stored patterns: %d", mod->pat);

    for (i = 0; i < mod->pat; i++) {
	if (pattern_tracks_alloc(mod, i, 64) < 0)
	    goto err3;

	if (pp_pat[i] == 0)
	    continue;

	hio_seek(f, start + (pp_pat[i] << 4), SEEK_SET);
	if (broken)
	    hio_seek(f, 2, SEEK_CUR);

	for (r = 0; r < 64; ) {
	    b = hio_read8(f);

	    if (b == S3M_EOR) {
		r++;
		continue;
	    }

	    c = b & S3M_CH_MASK;
	    event = c >= mod->chn ? &dummy : &EVENT (i, c, r);

	    if (b & S3M_NI_FOLLOW) {
		n = hio_read8(f);

		switch (n) {
		case 255:
		    n = 0;
		    break;	/* Empty note */
		case 254:
		    n = XMP_KEY_OFF;
		    break;	/* Key off */
		default:
		    n = 37 + 12 * MSN (n) + LSN (n);
		}

		event->note = n;
		event->ins = hio_read8(f);;
	    }

	    if (b & S3M_VOL_FOLLOWS) {
		event->vol = hio_read8(f) + 1;
	    }

	    if (b & S3M_FX_FOLLOWS) {
		event->fxt = fx[hio_read8(f)];
		event->fxp = hio_read8(f);
		switch (event->fxt) {
		case FX_SPEED:
		    event->fxp = MSN (event->fxp);
		    break;
		case FX_NONE:
		    event->fxp = event->fxt = 0;
		    break;
		}
	    }
	}
    }

    free (pp_ins);
    free (pp_pat);

    /* Read samples */
    D_(D_INFO "Stored samples: %d", mod->smp);

    for (i = 0; i < mod->ins; i++) {
	if (load_sample(m, f, 0, &mod->xxs[i], NULL) < 0)
	    goto err;
    }

    m->quirk |= QUIRK_VSALL | QUIRKS_ST3;
    m->read_event_type = READ_EVENT_ST3;

    return 0;

  err3:
    free(pp_ins);
  err2:
    free(pp_pat);
  err:
    return -1;
}
コード例 #16
0
ファイル: stc_load.c プロジェクト: GCrean/libxmp
static int stc_load(struct module_data *m, HIO_HANDLE * f, const int start)
{
	struct xmp_module *mod = &m->mod;
	struct xmp_event *event /*, *noise*/;
	int i, j;
	uint8 buf[100];
	int pos_ptr, orn_ptr, pat_ptr;
	struct stc_ord stc_ord[256];
	struct stc_pat stc_pat[MAX_PAT];
	int num, flag, orn;
	int *decoded;
	struct spectrum_extra *se;

	LOAD_INIT();

	mod->spd = hio_read8(f);		/* Speed */
	pos_ptr = hio_read16l(f);		/* Positions pointer */
	orn_ptr = hio_read16l(f);		/* Ornaments pointer */
	pat_ptr = hio_read16l(f);		/* Patterns pointer */

	hio_read(buf, 18, 1, f);		/* Title */
	copy_adjust(mod->name, (uint8 *)buf, 18);
	set_type(m, "ZX Spectrum Sound Tracker");

	hio_read16l(f);			/* Size */

	/* Read orders */

	hio_seek(f, pos_ptr, SEEK_SET);
	mod->len = hio_read8(f) + 1;

	for (num = i = 0; i < mod->len; i++) {
		stc_ord[i].pattern = hio_read8(f);
		stc_ord[i].height = hio_read8s(f);
		//printf("%d %d -- ", stc_ord[i].pattern, stc_ord[i].height);

		for (flag = j = 0; j < i; j++) {
			if (stc_ord[i].pattern == stc_ord[j].pattern &&
				stc_ord[i].height == stc_ord[j].height)
			{
				mod->xxo[i] = mod->xxo[j];
				flag = 1;
				break;
			}
		}
		if (!flag) {
			mod->xxo[i] = num++;
		}
		//printf("%d\n", mod->xxo[i]);
	}

	mod->chn = 3;
	mod->pat = num;
	mod->trk = mod->pat * mod->chn;
	mod->ins = 15;
	mod->smp = mod->ins;
	orn = (pat_ptr - orn_ptr) / 33;

	MODULE_INFO();

	/* Read patterns */

	if (pattern_init(mod) < 0)
		return -1;

	hio_seek(f, pat_ptr, SEEK_SET);
	decoded = calloc(mod->pat, sizeof(int));
	D_(D_INFO "Stored patterns: %d ", mod->pat);

	for (i = 0; i < MAX_PAT; i++) {
		if (hio_read8(f) == 0xff)
			break;
		stc_pat[i].ch[0] = hio_read16l(f);
		stc_pat[i].ch[1] = hio_read16l(f);
		stc_pat[i].ch[2] = hio_read16l(f);
	}

	for (i = 0; i < mod->len; i++) {		/* pattern */
		int src = stc_ord[i].pattern - 1;
		int dest = mod->xxo[i];
		int trans = stc_ord[i].height;

		if (decoded[dest])
			continue;

		//printf("%d/%d) Read pattern %d -> %d\n", i, mod->len, src, dest);

		if (pattern_tracks_alloc(mod, dest, 64) < 0)
			return -1;

		for (j = 0; j < 3; j++) {		/* row */
			int row = 0;
			int x;
			int rowinc = 0;
	
			hio_seek(f, stc_pat[src].ch[j], SEEK_SET);

			do {
				for (;;) {
					x = hio_read8(f);

					if (x == 0xff)
						break;
	
//printf("pat %d, channel %d, row %d, x = %02x\n", dest, j, row, x);
					event = &EVENT(dest, j, row);
				
					if (x <= 0x5f) {
						event->note = x + 18 + trans;
						row += 1 + rowinc;
						break;
					}

					if (x <= 0x6f) {
						event->ins = x - 0x5f - 1;
					} else if (x <= 0x7f) {
						/* ornament*/
						event->fxt = FX_SYNTH_0;
						event->fxp = x - 0x70;
					} else if (x == 0x80) {
						event->note = XMP_KEY_OFF;
						row += 1 + rowinc;
						break;
					} else if (x == 0x81) {
						/* ? */
						row += 1 + rowinc;
					} else if (x == 0x82) {
						/* disable ornament/envelope */
						event->fxt = FX_SYNTH_0;
						event->fxp = 0;
						event->f2t = FX_SYNTH_2;
						event->f2p = 0;
					} else if (x <= 0x8e) {
						/* envelope */
						event->fxt = FX_SYNTH_0 +
							x - 0x80;      /* R13 */
						event->fxp = hio_read8(f); /* R11 */
						event->f2t = FX_SYNTH_1;
						event->f2p = hio_read8(f); /* R12 */
					} else {
						rowinc = x - 0xa1;
					}
				}
			} while (x != 0xff);
		}

		decoded[dest] = 1;
	}

	free(decoded);

	/* Read instruments */

	if (instrument_init(mod) < 0)
		return -1;

	hio_seek(f, 27, SEEK_SET);

	D_(D_INFO "Instruments: %d", mod->ins);
	for (i = 0; i < mod->ins; i++) {
		struct spectrum_sample ss;

		memset(&ss, 0, sizeof (struct spectrum_sample));
		if (subinstrument_alloc(mod, i, 1) < 0)
			return -1;
		mod->xxi[i].nsm = 1;
		mod->xxi[i].sub[0].vol = 0x40;
		mod->xxi[i].sub[0].pan = 0x80;
		mod->xxi[i].sub[0].xpo = -1;
		mod->xxi[i].sub[0].sid = i;

		hio_read(buf, 1, 99, f);

		if (buf[97] == 0) {
			ss.loop = 32;
			ss.length = 33;
		} else {
			ss.loop = buf[97] - 1;
			if (ss.loop > 31)
				ss.loop = 31;
			ss.length = buf[97] + buf[98];
			if (ss.length > 32)
				ss.length = 32;
			if (ss.length == 0)
				ss.length = 1;
			if (ss.loop >= ss.length)
				ss.loop = ss.length - 1;

			if (ss.length < 32) {
				ss.length += 33 - (ss.loop + 1);
				ss.loop = 32;
			}
		}

		/* Read sample ticks */

		for (j = 0; j < 31; j++) {
			struct spectrum_stick *sst = &ss.stick[j];
			uint8 *chdata = &buf[1 + j * 3];
			
			memset(sst, 0, sizeof (struct spectrum_stick));

			if (~chdata[1] & 0x80) {
				sst->flags |= SPECTRUM_FLAG_MIXNOISE;
				sst->noise_env_inc = chdata[1] & 0x1f;

				if (sst->noise_env_inc & 0x10)
					sst->noise_env_inc |= 0xf0;
			}

			if (~chdata[1] & 0x40)
				sst->flags |= SPECTRUM_FLAG_MIXTONE;

			sst->vol = chdata[0] & 0x0f;

			sst->tone_inc = (((int)(chdata[0] & 0xf0)) << 4) |
						chdata[2];

			if (~chdata[1] & 0x20)
				sst->tone_inc = -sst->tone_inc;

			sst->flags |= SPECTRUM_FLAG_ENVELOPE;

			/*if (j != 0) {
				reportv(ctx, 1, "               ");
			}
			reportv(ctx, 1, "%02X %c%c%c %c%03x %x\n", j,
				sst->flags & SPECTRUM_FLAG_MIXTONE ? 'T' : 't',
				sst->flags & SPECTRUM_FLAG_MIXNOISE ? 'N' : 'n',
				sst->flags & SPECTRUM_FLAG_ENVELOPE ? 'E' : 'e',
				sst->tone_inc >= 0 ? '+' : '-',
				sst->tone_inc >= 0 ?
					sst->tone_inc : -sst->tone_inc,
				sst->vol);*/
			
		}

		if (load_sample(m, f, SAMPLE_FLAG_SPECTRUM, &mod->xxs[i],
							(char *)&ss) < 0) {
			return -1;
		}
	}
	
	/* Read ornaments */

	hio_seek(f, orn_ptr, SEEK_SET);
	m->extra = calloc(1, sizeof (struct spectrum_extra));
	se = m->extra;

	D_(D_INFO "Ornaments: %d", orn);
	for (i = 0; i < orn; i++) {
		int index;
		struct spectrum_ornament *so;

		index = hio_read8(f);		

		so = &se->ornament[index];
		so->length = 32;
		so->loop = 31;

		for (j = 0; j < 32; j++) {
			so->val[j] = hio_read8s(f);
		}
	}

	for (i = 0; i < 4; i++) {
		mod->xxc[i].pan = 0x80;
		mod->xxc[i].flg = XMP_CHANNEL_SYNTH;
	}
	
	m->synth = &synth_spectrum;

	return 0;
}
コード例 #17
0
ファイル: chip_load.c プロジェクト: EQ4/libxmp
static int chip_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	struct mod_header mh;
	uint8 *tidx;
	int i, j, tnum;

	LOAD_INIT();

	if ((tidx = calloc(1, 1024)) == NULL) {
		goto err;
	}

	hio_read(&mh.name, 20, 1, f);
	hio_read16b(f);

	for (i = 0; i < 31; i++) {
		hio_read(&mh.ins[i].name, 22, 1, f);
		mh.ins[i].size = hio_read16b(f);
		mh.ins[i].finetune = hio_read8(f);
		mh.ins[i].volume = hio_read8(f);
		mh.ins[i].loop_start = hio_read16b(f);
		mh.ins[i].loop_size = hio_read16b(f);
	}

	hio_read(&mh.magic, 4, 1, f);
	mh.len = hio_read8(f);
	mh.restart = hio_read8(f);
	hio_read(tidx, 1024, 1, f);
	hio_read16b(f);

	mod->chn = 4;
	mod->ins = 31;
	mod->smp = mod->ins;
	mod->len = mh.len;
	mod->pat = mh.len;
	mod->rst = mh.restart;

	tnum = 0;
	for (i = 0; i < mod->len; i++) {
		mod->xxo[i] = i;

		for (j = 0; j < 4; j++) {
			int t = tidx[2 * (4 * i + j)];
			if (t > tnum)
				tnum = t;
		}
	}

	mod->trk = tnum + 1;

	strncpy(mod->name, (char *)mh.name, 20);
	set_type(m, "Chiptracker");
	MODULE_INFO();

	if (instrument_init(mod) < 0)
		goto err2;

	for (i = 0; i < mod->ins; i++) {
		struct xmp_instrument *xxi = &mod->xxi[i];
		struct xmp_sample *xxs = &mod->xxs[i];
		struct xmp_subinstrument *sub;

		if (subinstrument_alloc(mod, i, 1) < 0)
			goto err2;

		sub = &xxi->sub[0];

		xxs->len = 2 * mh.ins[i].size;
		xxs->lps = mh.ins[i].loop_start;
		xxs->lpe = xxs->lps + 2 * mh.ins[i].loop_size;
		xxs->flg = mh.ins[i].loop_size > 1 ? XMP_SAMPLE_LOOP : 0;
		sub->fin = (int8) (mh.ins[i].finetune << 4);
		sub->vol = mh.ins[i].volume;
		sub->pan = 0x80;
		sub->sid = i;

		if (xxs->len > 0)
			xxi->nsm = 1;

		instrument_name(mod, i, mh.ins[i].name, 22);
	}

	if (pattern_init(mod) < 0)
		goto err2;

	for (i = 0; i < mod->len; i++) {
		if (pattern_alloc(mod, i) < 0)
			goto err2;
		mod->xxp[i]->rows = 64;

		for (j = 0; j < 4; j++) {
			int t = tidx[2 * (4 * i + j)];
			mod->xxp[i]->index[j] = t;
		}
	}

	/* Load and convert tracks */
	D_(D_INFO "Stored tracks: %d", mod->trk);

	for (i = 0; i < mod->trk; i++) {
		if (track_alloc(mod, i, 64) < 0)
			goto err2;

		for (j = 0; j < 64; j++) {
			struct xmp_event *event = &mod->xxt[i]->event[j];
			uint8 e[4];

			hio_read(e, 1, 4, f);
			if (e[0] && e[0] != 0xa8)
				event->note = 13 + e[0] / 2;
			event->ins = e[1];
			event->fxt = e[2] & 0x0f;
			event->fxp = e[3];
		}
	}

	m->quirk |= QUIRK_MODRNG;

	/* Load samples */

	D_(D_INFO "Stored samples: %d", mod->smp);

	for (i = 0; i < mod->smp; i++) {
		if (mod->xxs[i].len == 0)
			continue;

		if (load_sample(m, f, SAMPLE_FLAG_FULLREP, &mod->xxs[i], NULL) < 0)
			goto err2;
	}

	free(tidx);

	return 0;

    err2:
	free(tidx);
    err:
	return -1;
}
コード例 #18
0
ファイル: hsc_load.c プロジェクト: B0rschti/libxmp-4.3.0
static int hsc_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
    struct xmp_module *mod = &m->mod;
    int pat, i, r, c;
    struct xmp_event *event;
    uint8 *x, *sid, e[2], buf[128 * 12];

    LOAD_INIT();

    hio_read(buf, 1, 128 * 12, f);

    x = buf;
    for (i = 0; i < 128; i++, x += 12) {
	if (x[9] & ~0x3 || x[10] & ~0x3)	/* Test waveform register */
	    break;
	if (x[8] & ~0xf)			/* Test feedback & algorithm */
	    break;
    }

    mod->ins = i;

    hio_seek(f, start + 0, SEEK_SET);

    mod->chn = 9;
    mod->bpm = 135;
    mod->spd = 6;
    mod->smp = mod->ins;

    m->quirk |= QUIRK_LINEAR;

    set_type(m, "HSC-Tracker");

    MODULE_INFO();

    /* Read instruments */
    if (instrument_init(mod) < 0)
	return -1;

    hio_read (buf, 1, 128 * 12, f);
    sid = buf;
    for (i = 0; i < mod->ins; i++, sid += 12) {
	if (subinstrument_alloc(mod, i, 1) < 0)
	    return -1;

	mod->xxi[i].nsm = 1;
	mod->xxi[i].sub[0].vol = 0x40;
	mod->xxi[i].sub[0].fin = (int8)sid[11] / 4;
	mod->xxi[i].sub[0].pan = 0x80;
	mod->xxi[i].sub[0].xpo = 0;
	mod->xxi[i].sub[0].sid = i;
	mod->xxi[i].rls = LSN(sid[7]) * 32;	/* carrier release */

	if (load_sample(m, f, SAMPLE_FLAG_ADLIB | SAMPLE_FLAG_HSC,
					&mod->xxs[i], (char *)sid) < 0)
		return -1;
    }

    /* Read orders */
    for (pat = i = 0; i < 51; i++) {
	hio_read (&mod->xxo[i], 1, 1, f);
	if (mod->xxo[i] & 0x80)
	    break;			/* FIXME: jump line */
	if (mod->xxo[i] > pat)
	    pat = mod->xxo[i];
    }
    hio_seek(f, 50 - i, SEEK_CUR);
    mod->len = i;
    mod->pat = pat + 1;
    mod->trk = mod->pat * mod->chn;

    D_(D_INFO "Module length: %d", mod->len);
    D_(D_INFO "Instruments: %d", mod->ins);
    D_(D_INFO "Stored patterns: %d", mod->pat);

    if (pattern_init(mod) < 0)
	return -1;

    /* Read and convert patterns */
    for (i = 0; i < mod->pat; i++) {
	int ins[9] = { 1, 2, 3, 4, 5, 6, 7, 8, 9 };

	if (pattern_tracks_alloc(mod, i, 64) < 0)
	    return -1;

        for (r = 0; r < mod->xxp[i]->rows; r++) {
            for (c = 0; c < 9; c++) {
	        hio_read (e, 1, 2, f);
	        event = &EVENT (i, c, r);
		if (e[0] & 0x80) {
		    ins[c] = e[1] + 1;
		} else if (e[0] == 0x7f) {
		    event->note = XMP_KEY_OFF;
		} else if (e[0] > 0) {
		    event->note = e[0] + 25;
		    event->ins = ins[c];
		}

		event->fxt = 0;
		event->fxp = 0;

		if (e[1] == 0x01) {
		    event->fxt = 0x0d;
		    event->fxp = 0;
		}
	    }
	}
    }

    for (i = 0; i < mod->chn; i++) {
	mod->xxc[i].pan = 0x80;
	mod->xxc[i].flg = XMP_CHANNEL_SYNTH;
    }

    m->synth = &synth_adlib;

    return 0;
}
コード例 #19
0
ファイル: far_load.c プロジェクト: Nlcke/gideros
static int far_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
    struct xmp_module *mod = &m->mod;
    int i, j, vib = 0;
    struct xmp_event *event;
    struct far_header ffh;
    struct far_header2 ffh2;
    struct far_instrument fih;
    uint8 sample_map[8];

    LOAD_INIT();

    hio_read32b(f);			/* File magic: 'FAR\xfe' */
    hio_read(&ffh.name, 40, 1, f);	/* Song name */
    hio_read(&ffh.crlf, 3, 1, f);	/* 0x0d 0x0a 0x1A */
    ffh.headersize = hio_read16l(f);	/* Remaining header size in bytes */
    ffh.version = hio_read8(f);		/* Version MSN=major, LSN=minor */
    hio_read(&ffh.ch_on, 16, 1, f);	/* Channel on/off switches */
    hio_seek(f, 9, SEEK_CUR);		/* Current editing values */
    ffh.tempo = hio_read8(f);		/* Default tempo */
    hio_read(&ffh.pan, 16, 1, f);	/* Channel pan definitions */
    hio_read32l(f);			/* Grid, mode (for editor) */
    ffh.textlen = hio_read16l(f);	/* Length of embedded text */

    /* Sanity check */
    if (ffh.tempo == 0) {
	return -1;
    }

    hio_seek(f, ffh.textlen, SEEK_CUR);	/* Skip song text */

    hio_read(&ffh2.order, 256, 1, f);	/* Orders */
    ffh2.patterns = hio_read8(f);	/* Number of stored patterns (?) */
    ffh2.songlen = hio_read8(f);	/* Song length in patterns */
    ffh2.restart = hio_read8(f);	/* Restart pos */
    for (i = 0; i < 256; i++) {
	ffh2.patsize[i] = hio_read16l(f); /* Size of each pattern in bytes */
    }

    mod->chn = 16;
    /*mod->pat=ffh2.patterns; (Error in specs? --claudio) */
    mod->len = ffh2.songlen;
    mod->spd = 6;
    mod->bpm = 8 * 60 / ffh.tempo;
    memcpy (mod->xxo, ffh2.order, mod->len);

    for (mod->pat = i = 0; i < 256; i++) {
	if (ffh2.patsize[i])
	    mod->pat = i + 1;
    }

    mod->trk = mod->chn * mod->pat;

    strncpy(mod->name, (char *)ffh.name, 40);
    set_type(m, "Farandole Composer %d.%d", MSN(ffh.version), LSN(ffh.version));

    MODULE_INFO();

    if (pattern_init(mod) < 0)
	return -1;

    /* Read and convert patterns */
    D_(D_INFO "Comment bytes  : %d", ffh.textlen);
    D_(D_INFO "Stored patterns: %d", mod->pat);

    for (i = 0; i < mod->pat; i++) {
	uint8 brk, note, ins, vol, fxb;
	int rows;

	if (pattern_alloc(mod, i) < 0)
	    return -1;

	if (!ffh2.patsize[i])
	    continue;

	rows = (ffh2.patsize[i] - 2) / 64;

	/* Sanity check */
	if (rows <= 0 || rows > 256) {
	    return -1;
	}

	mod->xxp[i]->rows = rows;

	if (tracks_in_pattern_alloc(mod, i) < 0)
	    return -1;

	brk = hio_read8(f) + 1;
	hio_read8(f);

	for (j = 0; j < mod->xxp[i]->rows * mod->chn; j++) {
	    event = &EVENT(i, j % mod->chn, j / mod->chn);

	    if ((j % mod->chn) == 0 && (j / mod->chn) == brk)
		event->f2t = FX_BREAK;
	
	    note = hio_read8(f);
	    ins = hio_read8(f);
	    vol = hio_read8(f);
	    fxb = hio_read8(f);

	    if (note)
		event->note = note + 48;
	    if (event->note || ins)
		event->ins = ins + 1;

	    vol = 16 * LSN(vol) + MSN(vol);

	    if (vol)
		event->vol = vol - 0x10;	/* ? */

	    event->fxt = fx[MSN(fxb)];
	    event->fxp = LSN(fxb);

	    switch (event->fxt) {
	    case NONE:
	        event->fxt = event->fxp = 0;
		break;
	    case FX_FAR_PORTA_UP:
		event->fxt = FX_EXTENDED;
		event->fxp |= (EX_F_PORTA_UP << 4);
		break;
	    case FX_FAR_PORTA_DN:
		event->fxt = FX_EXTENDED;
		event->fxp |= (EX_F_PORTA_DN << 4);
		break;
	    case FX_FAR_RETRIG:
		event->fxt = FX_EXTENDED;
		event->fxp |= (EX_RETRIG << 4);
		break;
	    case FX_FAR_DELAY:
		event->fxt = FX_EXTENDED;
		event->fxp |= (EX_DELAY << 4);
		break;
	    case FX_FAR_SETVIBRATO:
		vib = event->fxp & 0x0f;
		event->fxt = event->fxp = 0;
		break;
	    case FX_VIBRATO:
		event->fxp = (event->fxp << 4) + vib;
		break;
	    case FX_PER_VIBRATO:
		event->fxp = (event->fxp << 4) + vib;
		break;
	    case FX_FAR_VSLIDE_UP:	/* Fine volume slide up */
		event->fxt = FX_EXTENDED;
		event->fxp |= (EX_F_VSLIDE_UP << 4);
		break;
	    case FX_FAR_VSLIDE_DN:	/* Fine volume slide down */
		event->fxt = FX_EXTENDED;
		event->fxp |= (EX_F_VSLIDE_DN << 4);
		break;
	    case FX_SPEED:
		if (event->fxp != 0) {
			event->fxp = 8 * 60 / event->fxp;
		} else {
			event->fxt = 0;
		}
		break;
	    }
	}
    }

    mod->ins = -1;
    hio_read(sample_map, 1, 8, f);
    for (i = 0; i < 64; i++) {
	if (sample_map[i / 8] & (1 << (i % 8)))
		mod->ins = i;
    }
    mod->ins++;

    mod->smp = mod->ins;

    if (instrument_init(mod) < 0)
	return -1;

    /* Read and convert instruments and samples */

    for (i = 0; i < mod->ins; i++) {
	if (!(sample_map[i / 8] & (1 << (i % 8))))
		continue;

	if (subinstrument_alloc(mod, i, 1) < 0)
	    return -1;

	hio_read(&fih.name, 32, 1, f);	/* Instrument name */
	fih.length = hio_read32l(f);	/* Length of sample (up to 64Kb) */
	fih.finetune = hio_read8(f);	/* Finetune (unsuported) */
	fih.volume = hio_read8(f);	/* Volume (unsuported?) */
	fih.loop_start = hio_read32l(f);/* Loop start */
	fih.loopend = hio_read32l(f);	/* Loop end */
	fih.sampletype = hio_read8(f);	/* 1=16 bit sample */
	fih.loopmode = hio_read8(f);

	/* Sanity check */
	if (fih.length > 0x10000 || fih.loop_start > 0x10000 ||
            fih.loopend > 0x10000) {
		return -1;
	}

	mod->xxs[i].len = fih.length;
	mod->xxs[i].lps = fih.loop_start;
	mod->xxs[i].lpe = fih.loopend;
	mod->xxs[i].flg = 0;

	if (mod->xxs[i].len > 0)
		mod->xxi[i].nsm = 1;

	if (fih.sampletype != 0) {
		mod->xxs[i].flg |= XMP_SAMPLE_16BIT;
		mod->xxs[i].len >>= 1;
		mod->xxs[i].lps >>= 1;
		mod->xxs[i].lpe >>= 1;
	}

	mod->xxs[i].flg |= fih.loopmode ? XMP_SAMPLE_LOOP : 0;
	mod->xxi[i].sub[0].vol = 0xff; /* fih.volume; */
	mod->xxi[i].sub[0].sid = i;

	instrument_name(mod, i, fih.name, 32);

	D_(D_INFO "[%2X] %-32.32s %04x %04x %04x %c V%02x",
		i, mod->xxi[i].name, mod->xxs[i].len, mod->xxs[i].lps,
		mod->xxs[i].lpe, fih.loopmode ? 'L' : ' ', mod->xxi[i].sub[0].vol);

	if (load_sample(m, f, 0, &mod->xxs[i], NULL) < 0)
		return -1;
    }
コード例 #20
0
ファイル: asylum_load.c プロジェクト: Nlcke/gideros
static int asylum_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	struct xmp_event *event;
	int i, j;

	LOAD_INIT();

	hio_seek(f, 32, SEEK_CUR);			/* skip magic */
	mod->spd = hio_read8(f);			/* initial speed */
	mod->bpm = hio_read8(f);			/* initial BPM */
	mod->ins = hio_read8(f);			/* number of instruments */
	mod->pat = hio_read8(f);			/* number of patterns */
	mod->len = hio_read8(f);			/* module length */
	hio_read8(f);

	hio_read(mod->xxo, 1, mod->len, f);	/* read orders */
	hio_seek(f, start + 294, SEEK_SET);

	mod->chn = 8;
	mod->smp = mod->ins;
	mod->trk = mod->pat * mod->chn;

	snprintf(mod->type, XMP_NAME_SIZE, "Asylum Music Format v1.0");

	MODULE_INFO();

	if (instrument_init(mod) < 0)
		return -1;

	/* Read and convert instruments and samples */
	for (i = 0; i < mod->ins; i++) {
		uint8 insbuf[37];

		if (subinstrument_alloc(mod, i, 1) < 0)	
			return -1;

		hio_read(insbuf, 1, 37, f);
		instrument_name(mod, i, insbuf, 22);
		mod->xxi[i].sub[0].fin = (int8)(insbuf[22] << 4);
		mod->xxi[i].sub[0].vol = insbuf[23];
		mod->xxi[i].sub[0].xpo = (int8)insbuf[24];
		mod->xxi[i].sub[0].pan = 0x80;
		mod->xxi[i].sub[0].sid = i;

		mod->xxs[i].len = readmem32l(insbuf + 25);
		mod->xxs[i].lps = readmem32l(insbuf + 29);
		mod->xxs[i].lpe = mod->xxs[i].lps + readmem32l(insbuf + 33);
		
		mod->xxs[i].flg = mod->xxs[i].lpe > 2 ? XMP_SAMPLE_LOOP : 0;

		D_(D_INFO "[%2X] %-22.22s %04x %04x %04x %c V%02x %d", i,
		   mod->xxi[i].name, mod->xxs[i].len, mod->xxs[i].lps,
		   mod->xxs[i].lpe,
		   mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
		   mod->xxi[i].sub[0].vol, mod->xxi[i].sub[0].fin);
	}

	hio_seek(f, 37 * (64 - mod->ins), SEEK_CUR);

	D_(D_INFO "Module length: %d", mod->len);

	if (pattern_init(mod) < 0)
		return -1;

	/* Read and convert patterns */
	D_(D_INFO "Stored patterns: %d", mod->pat);

	for (i = 0; i < mod->pat; i++) {
		if (pattern_tracks_alloc(mod, i, 64) < 0)
			return -1;

		for (j = 0; j < 64 * mod->chn; j++) {
			uint8 note;

			event = &EVENT(i, j % mod->chn, j / mod->chn);
			memset(event, 0, sizeof(struct xmp_event));
			note = hio_read8(f);

			if (note != 0) {
				event->note = note + 13;
			}

			event->ins = hio_read8(f);
			event->fxt = hio_read8(f);
			event->fxp = hio_read8(f);
		}
	}

	/* Read samples */
	D_(D_INFO "Stored samples: %d", mod->smp);

	for (i = 0; i < mod->ins; i++) {
		if (mod->xxs[i].len > 1) {
			if (load_sample(m, f, 0, &mod->xxs[i], NULL) < 0)
				return -1;
			mod->xxi[i].nsm = 1;
		}
	}

	return 0;
}
コード例 #21
0
ファイル: perceptron.c プロジェクト: barlik/neural_networks
int main(int argc, char *argv[])
{
	FILE *fp;
	int i, j;
	int cycles;

	int max_cycles;
	int pattern_len; /* x1, x2, ..., xn */
	int pattern_count; /* pocet vstupnych vzoriek */
	int input_count; /* pocet vstupnych vzoriek */
	PERCEPTRON *perceptrons;
	PATTERN *patterns;
	PATTERN *inputs;

	if (argc <= 2)
	{
		fprintf(stderr, "%s <training_file> <input_file> [<max_cyklov>]\n", argv[0]);
		return 0;
	}

	if (argc >= 4)
		max_cycles = atoi(argv[3]);
	else
		max_cycles = MAX_CYCLES;
	

	/* training data */
	fp = fopen(argv[1], "r");
	if (fp == NULL)
		die("Error opening training file");

	fscanf(fp, "%d %d", &pattern_len, &pattern_count);
	patterns = (PATTERN *) malloc(sizeof(PATTERN) * pattern_count);
	for (i = 0; i < pattern_count; i++)
	{
		pattern_init(&patterns[i], pattern_len);
		for (j = 0; j < pattern_len; j++)
			fscanf(fp, "%f", &patterns[i].inputs[j]);
		fscanf(fp, "%f", &patterns[i].result);
	}
	fclose(fp);

	/* input data */
	fp = fopen(argv[2], "r");
	if (fp == NULL)
		die("Error opening input file");

	fscanf(fp, "%d %d", &pattern_len, &input_count);
	inputs = (PATTERN *) malloc(sizeof(PATTERN) * input_count);
	for (i = 0; i < input_count; i++)
	{
		pattern_init(&inputs[i], pattern_len);
		for (j = 0; j < pattern_len; j++)
			fscanf(fp, "%f", &inputs[i].inputs[j]);
		fscanf(fp, "%f", &inputs[i].result);
	}
	fclose(fp);

	/* alocate one perceptron */
	perceptrons = (PERCEPTRON *) malloc(sizeof(PERCEPTRON) * 1);
	perceptron_init(&perceptrons[0], pattern_len);
	
	/* train network */
	cycles = train(&perceptrons[0], inputs, input_count, max_cycles, MAX_ERROR);
	printf("Trenovanie ukoncene po %d cykloch\n", cycles);

	printf("Perceptron:\n");
	for (i = 0; i < pattern_len; i++)
	{
		printf("%f ", perceptrons[0].weights[i]);
	}
	printf(" treshold: %f\n", perceptrons[0].treshold);

	printf("Testovanie vstupov:\n\t (ocakavana/vyhodnotena/rozdiel)\n");

	for (i = 0; i < input_count; i++)
	{
		float eval;
		eval = evaluate(&perceptrons[0], &inputs[i]);
		printf("\t%3d# \t %.0f\t %.0f\t [%.0f]\n", i+1, inputs[i].result, eval, inputs[i].result - eval);
	}

	return 0;
}
コード例 #22
0
ファイル: makeit.c プロジェクト: Starlink/starextract
/*
Manage the whole stuff.
*/
void	makeit()

  {
   checkstruct		*check;
   picstruct		*dfield, *field,*pffield[MAXFLAG], *wfield,*dwfield;
   catstruct		*imacat;
   tabstruct		*imatab;
   patternstruct	*pattern;
   static time_t        thetime1, thetime2;
   struct tm		*tm;
   unsigned int		modeltype;
   int			nflag[MAXFLAG], nparam2[2],
			i, nok, ntab, next, ntabmax, forcextflag,
			nima0,nima1, nweight0,nweight1, npsf0,npsf1, npat,npat0;

   next = 0;
   nok = 1;

/* Processing start date and time */
  dtime = counter_seconds();
  thetimet = time(NULL);
  tm = localtime(&thetimet);
  sprintf(prefs.sdate_start,"%04d-%02d-%02d",
        tm->tm_year+1900, tm->tm_mon+1, tm->tm_mday);
  sprintf(prefs.stime_start,"%02d:%02d:%02d",
        tm->tm_hour, tm->tm_min, tm->tm_sec);

  NFPRINTF(OUTPUT, "");
  QPRINTF(OUTPUT, "----- %s %s started on %s at %s with %d thread%s\n\n",
		BANNER,
		MYVERSION,
		prefs.sdate_start,
		prefs.stime_start,
		prefs.nthreads,
		prefs.nthreads>1? "s":"");

/* Initialize globals variables */
  initglob();

  NFPRINTF(OUTPUT, "Setting catalog parameters");
  readcatparams(prefs.param_name);
  useprefs();			/* update things accor. to prefs parameters */

/* Check if a specific extension should be loaded */
/* Never true for an NDF, although we could through all NDFs in a container, */
/* so we make selectext go away. */
  nima0 = -1;
  forcextflag = 0;

/* Do the same for other data (but do not force single extension mode) */
  nima1 = -1;    /* selectext(prefs.image_name[1]) */
  nweight0 = -1; /* selectext(prefs.wimage_name[0]) */
  nweight1 = -1; /* selectext(prefs.wimage_name[1]) */
  if (prefs.dpsf_flag)
    {
    npsf0 = -1; /* selectext(prefs.psf_name[0]) */
    npsf1 = -1; /* selectext(prefs.psf_name[1]) */
    }
  else
    npsf0 = -1; /* selectext(prefs.psf_name[0]) */
  for (i=0; i<prefs.nfimage_name; i++)
    nflag[i] = -1; /* selectext(prefs.fimage_name[i]) */

  if (prefs.psf_flag)
    {
/*-- Read the first PSF extension to set up stuff such as context parameters */
    NFPRINTF(OUTPUT, "Reading PSF information");
    if (prefs.dpsf_flag)
      {
      thedpsf = psf_load(prefs.psf_name[0],nima0<0? 1 :(npsf0<0? 1:npsf0)); 
      thepsf = psf_load(prefs.psf_name[1], nima1<0? 1 :(npsf1<0? 1:npsf1));
      }
    else
      thepsf = psf_load(prefs.psf_name[0], nima0<0? 1 :(npsf0<0? 1:npsf0)); 
 /*-- Need to check things up because of PSF context parameters */
    updateparamflags();
    useprefs();
    }

  if (prefs.prof_flag)
    {
#ifdef USE_MODEL
    fft_init(prefs.nthreads);
/* Create profiles at full resolution */
    NFPRINTF(OUTPUT, "Preparing profile models");
    modeltype = (FLAG(obj2.prof_offset_flux)? MODEL_BACK : MODEL_NONE)
	|(FLAG(obj2.prof_dirac_flux)? MODEL_DIRAC : MODEL_NONE)
	|(FLAG(obj2.prof_spheroid_flux)?
		(FLAG(obj2.prof_spheroid_sersicn)?
			MODEL_SERSIC : MODEL_DEVAUCOULEURS) : MODEL_NONE)
	|(FLAG(obj2.prof_disk_flux)? MODEL_EXPONENTIAL : MODEL_NONE)
	|(FLAG(obj2.prof_bar_flux)? MODEL_BAR : MODEL_NONE)
	|(FLAG(obj2.prof_arms_flux)? MODEL_ARMS : MODEL_NONE);
    theprofit = profit_init(thepsf, modeltype);
    changecatparamarrays("VECTOR_MODEL", &theprofit->nparam, 1);
    changecatparamarrays("VECTOR_MODELERR", &theprofit->nparam, 1);
    nparam2[0] = nparam2[1] = theprofit->nparam;
    changecatparamarrays("MATRIX_MODELERR", nparam2, 2);
    if (prefs.dprof_flag)
      thedprofit = profit_init(thedpsf, modeltype);
    if (prefs.pattern_flag)
      {
      npat0 = prefs.prof_disk_patternvectorsize;
      if (npat0<prefs.prof_disk_patternmodvectorsize)
        npat0 = prefs.prof_disk_patternmodvectorsize;
      if (npat0<prefs.prof_disk_patternargvectorsize)
        npat0 = prefs.prof_disk_patternargvectorsize;
/*---- Do a copy of the original number of pattern components */
      prefs.prof_disk_patternncomp = npat0;
      pattern = pattern_init(theprofit, prefs.pattern_type, npat0);
      if (FLAG(obj2.prof_disk_patternvector))
        {
        npat = pattern->size[2];
        changecatparamarrays("DISK_PATTERN_VECTOR", &npat, 1);
        }
      if (FLAG(obj2.prof_disk_patternmodvector))
        {
        npat = pattern->ncomp*pattern->nfreq;
        changecatparamarrays("DISK_PATTERNMOD_VECTOR", &npat, 1);
        }
      if (FLAG(obj2.prof_disk_patternargvector))
        {
        npat = pattern->ncomp*pattern->nfreq;
        changecatparamarrays("DISK_PATTERNARG_VECTOR", &npat, 1);
        }
      pattern_end(pattern);
      }
    QPRINTF(OUTPUT, "Fitting model: ");
    for (i=0; i<theprofit->nprof; i++)
      {
      if (i)
        QPRINTF(OUTPUT, "+");
      QPRINTF(OUTPUT, "%s", theprofit->prof[i]->name);
      }
    QPRINTF(OUTPUT, "\n");
    if (FLAG(obj2.prof_concentration)|FLAG(obj2.prof_concentration))
      {
      thepprofit = profit_init(thepsf, MODEL_DIRAC);
      theqprofit = profit_init(thepsf, MODEL_EXPONENTIAL);
      }
#else
    error(EXIT_FAILURE,
		"*Error*: model-fitting is not supported in this build.\n",
			" Please check your configure options");
#endif
    }

  if (prefs.filter_flag)
    {
    NFPRINTF(OUTPUT, "Reading detection filter");
    getfilter(prefs.filter_name);	/* get the detection filter */
    }

  if (FLAG(obj2.sprob))
    {
    NFPRINTF(OUTPUT, "Initializing Neural Network");
    neurinit();
    NFPRINTF(OUTPUT, "Reading Neural Network Weights");
    getnnw(); 
    }

  if (prefs.somfit_flag)
    {
     int	margin;

    thesom = som_load(prefs.som_name);
    if ((margin=(thesom->inputsize[1]+1)/2) > prefs.cleanmargin)
      prefs.cleanmargin = margin;
    if (prefs.somfit_vectorsize>thesom->neurdim)
      {
      prefs.somfit_vectorsize = thesom->neurdim;
      sprintf(gstr,"%d", prefs.somfit_vectorsize);
      warning("Dimensionality of the SOM-fit vector limited to ", gstr);
      }
    }

/* Prepare growth-curve buffer */
  if (prefs.growth_flag)
    initgrowth();

/* Allocate memory for multidimensional catalog parameter arrays */
  alloccatparams();
  useprefs();

/*-- Init the CHECK-images */
  if (prefs.check_flag)
    {
      checkenum	c;
      
      NFPRINTF(OUTPUT, "Initializing check-image(s)");
      for (i=0; i<prefs.ncheck_type; i++)
        if ((c=prefs.check_type[i]) != CHECK_NONE)
          {
            if (prefs.check[c])
              error(EXIT_FAILURE,"*Error*: 2 CHECK_IMAGEs cannot have the same ",
                        " CHECK_IMAGE_TYPE");
            prefs.check[c] = initcheck(prefs.check_name[i], prefs.check_type[i],
                                       next);
            free(prefs.check_name[i]);
          }
    }

  NFPRINTF(OUTPUT, "Initializing catalog");
  initcat();
  
/* Initialize XML data */
  if (prefs.xml_flag || prefs.cat_type==ASCII_VO)
    init_xml(next);

/* Go through all images */
/* for all images in an MEF */

/*---- Initial time measurement*/
  time(&thetime1);
  thecat.currext = nok+1;
  
  dfield = field = wfield = dwfield = NULL;

/*---- Init the Detection and Measurement-images */
  if (prefs.dimage_flag)
  {
      dfield = newfield(prefs.image_name[0], DETECT_FIELD, nok);
      field = newfield(prefs.image_name[1], MEASURE_FIELD, nok);
      if ((field->width!=dfield->width) || (field->height!=dfield->height))
          error(EXIT_FAILURE, "*Error*: Frames have different sizes","");
/*---- Prepare interpolation */
      if (prefs.dweight_flag && prefs.interp_type[0] == INTERP_ALL)
          init_interpolate(dfield, -1, -1);
      if (prefs.interp_type[1] == INTERP_ALL)
          init_interpolate(field, -1, -1);
  }
  else
  {
      field = newfield(prefs.image_name[0], DETECT_FIELD | MEASURE_FIELD, nok);
/*-- Prepare interpolation */
      if ((prefs.dweight_flag || prefs.weight_flag)
          && prefs.interp_type[0] == INTERP_ALL)
          init_interpolate(field, -1, -1);       /* 0.0 or anything else */
  }

/*-- Init the WEIGHT-images */
  if (prefs.dweight_flag || prefs.weight_flag) 
  {
      weightenum	wtype;
      PIXTYPE	interpthresh;

      if (prefs.nweight_type>1)
      {
/*------ Double-weight-map mode */
          if (prefs.weight_type[1] != WEIGHT_NONE)
          {
/*-------- First: the "measurement" weights */
              wfield = newweight(prefs.wimage_name[1],field,prefs.weight_type[1],
                                 nok);
              wtype = prefs.weight_type[1];
              interpthresh = prefs.weight_thresh[1];
/*-------- Convert the interpolation threshold to variance units */
              weight_to_var(wfield, &interpthresh, 1);
              wfield->weight_thresh = interpthresh;
              if (prefs.interp_type[1] != INTERP_NONE)
                  init_interpolate(wfield,
                                   prefs.interp_xtimeout[1], prefs.interp_ytimeout[1]);
          }
/*------ The "detection" weights */
          if (prefs.weight_type[0] != WEIGHT_NONE)
          {
              interpthresh = prefs.weight_thresh[0];
              if (prefs.weight_type[0] == WEIGHT_FROMINTERP)
              {
                  dwfield=newweight(prefs.wimage_name[0],wfield,prefs.weight_type[0], 
                                    nok);
                  weight_to_var(wfield, &interpthresh, 1);
              }
              else
              {
                  dwfield = newweight(prefs.wimage_name[0], dfield?dfield:field,
                                      prefs.weight_type[0], nok);
                  weight_to_var(dwfield, &interpthresh, 1);
              }
              dwfield->weight_thresh = interpthresh;
              if (prefs.interp_type[0] != INTERP_NONE)
                  init_interpolate(dwfield,
                                   prefs.interp_xtimeout[0], prefs.interp_ytimeout[0]);
          }
      }
      else
      {
/*------ Single-weight-map mode */
          wfield = newweight(prefs.wimage_name[0], dfield?dfield:field,
                             prefs.weight_type[0], nok);
          wtype = prefs.weight_type[0];
          interpthresh = prefs.weight_thresh[0];
/*------ Convert the interpolation threshold to variance units */
          weight_to_var(wfield, &interpthresh, 1);
          wfield->weight_thresh = interpthresh;
          if (prefs.interp_type[0] != INTERP_NONE)
              init_interpolate(wfield,
                               prefs.interp_xtimeout[0], prefs.interp_ytimeout[0]);
      }
  }

/*-- Init the FLAG-images */
  for (i=0; i<prefs.nimaflag; i++)
  {
      pffield[i] = newfield(prefs.fimage_name[i], FLAG_FIELD, nok);
      if ((pffield[i]->width!=field->width)
          || (pffield[i]->height!=field->height))
          error(EXIT_FAILURE,
                "*Error*: Incompatible FLAG-map size in ", prefs.fimage_name[i]);
  }

/*-- Compute background maps for `standard' fields */
  QPRINTF(OUTPUT, dfield? "Measurement image:"
          : "Detection+Measurement image: ");
  makeback(field, wfield, prefs.wscale_flag[1]);
  QPRINTF(OUTPUT, (dfield || (dwfield&&dwfield->flags^INTERP_FIELD))? "(M)   "
          "Background: %-10g RMS: %-10g / Threshold: %-10g \n"
          : "(M+D) "
          "Background: %-10g RMS: %-10g / Threshold: %-10g \n",
          field->backmean, field->backsig, (field->flags & DETECT_FIELD)?
          field->dthresh: field->thresh);
  if (dfield)
  {
      QPRINTF(OUTPUT, "Detection image: ");
      makeback(dfield, dwfield? dwfield
                        : (prefs.weight_type[0] == WEIGHT_NONE?NULL:wfield),
                prefs.wscale_flag[0]);
      QPRINTF(OUTPUT, "(D)   "
              "Background: %-10g RMS: %-10g / Threshold: %-10g \n",
              dfield->backmean, dfield->backsig, dfield->dthresh);
  }
  else if (dwfield && dwfield->flags^INTERP_FIELD)
  {
      makeback(field, dwfield, prefs.wscale_flag[0]);
      QPRINTF(OUTPUT, "(D)   "
              "Background: %-10g RMS: %-10g / Threshold: %-10g \n",
              field->backmean, field->backsig, field->dthresh);
  }

/*-- For interpolated weight-maps, copy the background structure */
  if (dwfield && dwfield->flags&(INTERP_FIELD|BACKRMS_FIELD))
      copyback(dwfield->reffield, dwfield);
  if (wfield && wfield->flags&(INTERP_FIELD|BACKRMS_FIELD))
      copyback(wfield->reffield, wfield);

/*-- Prepare learn and/or associations */
  if (prefs.assoc_flag)
      init_assoc(field);                  /* initialize assoc tasks */

/*-- Update the CHECK-images */
  if (prefs.check_flag)
      for (i=0; i<MAXCHECK; i++)
        if ((check=prefs.check[i]))
          reinitcheck(field, check);

    if (!forcextflag && nok>1)
      {
      if (prefs.psf_flag)
        {
/*------ Read other PSF extensions */
        NFPRINTF(OUTPUT, "Reading PSF information");
        psf_end(thepsf, thepsfit);
        if (prefs.dpsf_flag)
          {
          psf_end(thedpsf, thedpsfit);
          thedpsf = psf_load(prefs.psf_name[0], nok);
          thepsf = psf_load(prefs.psf_name[1], nok);
          }
        else
          thepsf = psf_load(prefs.psf_name[0], nok); 
        }

#ifdef USE_MODEL
      if (prefs.prof_flag)
        {
/*------ Create profiles at full resolution */
        profit_end(theprofit);
        theprofit = profit_init(thepsf, modeltype);
        if (prefs.dprof_flag)
          {
          profit_end(thedprofit);
          thedprofit = profit_init(thedpsf, modeltype);
          }
        if (prefs.pattern_flag)
          {
          pattern = pattern_init(theprofit, prefs.pattern_type, npat0);
          pattern_end(pattern);
          }
        if (FLAG(obj2.prof_concentration)|FLAG(obj2.prof_concentration))
          {
          profit_end(thepprofit);
          profit_end(theqprofit);
          thepprofit = profit_init(thepsf, MODEL_DIRAC);
          theqprofit = profit_init(thepsf, MODEL_EXPONENTIAL);
          }
        }
#endif
      }

/*-- Initialize PSF contexts and workspace */
  if (prefs.psf_flag)
  {
      psf_readcontext(thepsf, field);
      psf_init();
      if (prefs.dpsf_flag)
        {
        psf_readcontext(thepsf, dfield);
        psf_init();
        }
  }

/*-- Copy field structures to static ones (for catalog info) */
  if (dfield)
  {
      thefield1 = *field;
      thefield2 = *dfield;
  }
  else
      thefield1 = thefield2 = *field;

  if (wfield)
  {
      thewfield1 = *wfield;
      thewfield2 = dwfield? *dwfield: *wfield;
  }
  else if (dwfield)
      thewfield2 = *dwfield;

  reinitcat(field);

/*-- Start the extraction pipeline */
  NFPRINTF(OUTPUT, "Scanning image");
  scanimage(field, dfield, pffield, prefs.nimaflag, wfield, dwfield);

  NFPRINTF(OUTPUT, "Closing files");

/*-- Finish the current CHECK-image processing */
  if (prefs.check_flag)
      for (i=0; i<MAXCHECK; i++)
        if ((check=prefs.check[i]))
          reendcheck(field, check);

/*-- Final time measurements*/
    if (time(&thetime2)!=-1)
      {
      if (!strftime(thecat.ext_date, 12, "%d/%m/%Y", localtime(&thetime2)))
        error(EXIT_FAILURE, "*Internal Error*: Date string too long ","");
      if (!strftime(thecat.ext_time, 10, "%H:%M:%S", localtime(&thetime2)))
          error(EXIT_FAILURE, "*Internal Error*: Time/date string too long ","");
      thecat.ext_elapsed = difftime(thetime2, thetime1);
      
  }

  reendcat();

/* Update XML data */
    if (prefs.xml_flag || prefs.cat_type==ASCII_VO)
      update_xml(&thecat, dfield? dfield:field, field,
	dwfield? dwfield:wfield, wfield);


/*-- Close ASSOC routines */
  end_assoc(field);

  for (i=0; i<prefs.nimaflag; i++)
      endfield(pffield[i]);
  endfield(field);
  if (dfield)
      endfield(dfield);
  if (wfield)
      endfield(wfield);
  if (dwfield)
      endfield(dwfield);

    QPRINTF(OUTPUT, "      Objects: detected %-8d / sextracted %-8d        \n\n",
	thecat.ndetect, thecat.ntotal);
/* End look around all images in an MEF */

  if (nok<0)
     error(EXIT_FAILURE, "Not enough valid FITS image extensions in ",
           prefs.image_name[0]);

  NFPRINTF(OUTPUT, "Closing files");

/* End CHECK-image processing */
  if (prefs.check_flag)
    for (i=0; i<MAXCHECK; i++)
      {
      if ((check=prefs.check[i]))
        endcheck(check);
      prefs.check[i] = NULL;
      }

  if (prefs.filter_flag)
    endfilter();

  if (prefs.somfit_flag)
    som_end(thesom);

  if (prefs.growth_flag)
    endgrowth();

#ifdef USE_MODEL
  if (prefs.prof_flag)
    {
    profit_end(theprofit);
    if (prefs.dprof_flag)
      profit_end(thedprofit);
    if (FLAG(obj2.prof_concentration)|FLAG(obj2.prof_concentration))
      {
      profit_end(thepprofit);
      profit_end(theqprofit);
      }
    fft_end();
    }
#endif

  if (prefs.psf_flag)
    psf_end(thepsf, thepsfit);

  if (prefs.dpsf_flag)
    psf_end(thedpsf, thedpsfit);

  if (FLAG(obj2.sprob))
    neurclose();

/* Processing end date and time */
  thetimet2 = time(NULL);
  tm = localtime(&thetimet2);
  sprintf(prefs.sdate_end,"%04d-%02d-%02d",
	tm->tm_year+1900, tm->tm_mon+1, tm->tm_mday);
  sprintf(prefs.stime_end,"%02d:%02d:%02d",
	tm->tm_hour, tm->tm_min, tm->tm_sec);
  prefs.time_diff = counter_seconds() - dtime;

/* Write XML */
  if (prefs.xml_flag)
    write_xml(prefs.xml_name);

  endcat((char *)NULL);

  if (prefs.xml_flag || prefs.cat_type==ASCII_VO)
    end_xml();

/* Free FITS headers (now catalogues are closed). */
  if (field->fitsheadsize > 0) {
      free(field->fitshead);
  }

  return;
  }
コード例 #23
0
ファイル: ssmt_load.c プロジェクト: duongbaoduy/libxmp
static int mtp_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	struct xmp_event *event;
	int i, j, k;
	uint8 buffer[25];
	int blocksize;

	LOAD_INIT();

	hio_read(buffer, 6, 1, f);

	if (!memcmp(buffer, "SONGOK", 6))
		set_type(m, "IIgs SoundSmith");
	else if (!memcmp(buffer, "IAN92a", 8))
		set_type(m, "IIgs MegaTracker");
	else
		return -1;

	blocksize = hio_read16l(f);
	mod->spd = hio_read16l(f);
	hio_seek(f, 10, SEEK_CUR);		/* skip 10 reserved bytes */
	
	mod->ins = mod->smp = 15;
	if (instrument_init(mod) < 0)
		return -1;

	for (i = 0; i < mod->ins; i++) {
		if (subinstrument_alloc(mod, i, 1) < 0)
			return -1;

		hio_read(buffer, 1, 22, f);
		if (buffer[0]) {
			buffer[buffer[0] + 1] = 0;
			instrument_name(mod, i, buffer + 1, 22);
		}
		hio_read16l(f);		/* skip 2 reserved bytes */
		mod->xxi[i].sub[0].vol = hio_read8(f) >> 2;
		mod->xxi[i].sub[0].pan = 0x80;
		hio_seek(f, 5, SEEK_CUR);	/* skip 5 bytes */
	}

	mod->len = hio_read8(f) & 0x7f;
	hio_read8(f);
	hio_read(mod->xxo, 1, 128, f);

	MODULE_INFO();

	hio_seek(f, start + 600, SEEK_SET);

	mod->chn = 14;
	mod->pat = blocksize / (14 * 64);
	mod->trk = mod->pat * mod->chn;

	if (pattern_init(mod) < 0)
		return -1;

	/* Read and convert patterns */
	D_(D_INFO "Stored patterns: %d", mod->pat);

	/* Load notes */
	for (i = 0; i < mod->pat; i++) {
		if (pattern_tracks_alloc(mod, i, 64) < 0)
			return -1;

		for (j = 0; j < mod->xxp[i]->rows; j++) {
			for (k = 0; k < mod->chn; k++) {
				event = &EVENT(i, k, j);
				event->note = hio_read8(f);;
				if (event->note)
					event->note += 24;
			}
		}
	}

	/* Load fx1 */
	for (i = 0; i < mod->pat; i++) {
		for (j = 0; j < mod->xxp[i]->rows; j++) {
			for (k = 0; k < mod->chn; k++) {
				uint8 x;
				event = &EVENT(i, k, j);
				x = hio_read8(f);;
				event->ins = x >> 4;

				switch (x & 0x0f) {
				case 0x00:
					event->fxt = FX_ARPEGGIO;
					break;
				case 0x03:
					event->fxt = FX_VOLSET;
					break;
				case 0x05:
					event->fxt = FX_VOLSLIDE_DN;
					break;
				case 0x06:
					event->fxt = FX_VOLSLIDE_UP;
					break;
				case 0x0f:
					event->fxt = FX_SPEED;
					break;
				}
			}
		}
	}

	/* Load fx2 */
	for (i = 0; i < mod->pat; i++) {
		for (j = 0; j < mod->xxp[i]->rows; j++) {
			for (k = 0; k < mod->chn; k++) {
				event = &EVENT(i, k, j);
				event->fxp = hio_read8(f);;

				switch (event->fxt) {
				case FX_VOLSET:
				case FX_VOLSLIDE_DN:
				case FX_VOLSLIDE_UP:
					event->fxp >>= 2;
				}
			}
		}
	}

	/* Read instrument data */
	D_(D_INFO "Instruments    : %d ", mod->ins);

	for (i = 0; i < mod->ins; i++) {
		HIO_HANDLE *s;
		char filename[1024];

		if (!mod->xxi[i].name[0])
			continue;

		strncpy(filename, m->dirname, NAME_SIZE);
		if (*filename)
			strncat(filename, "/", NAME_SIZE);
		strncat(filename, (char *)mod->xxi[i].name, NAME_SIZE);

		if ((s = hio_open_file(filename, "rb")) != NULL) {
			asif_load(m, s, i);
			hio_close(s);
		}

#if 0
		mod->xxs[i].lps = 0;
		mod->xxs[i].lpe = 0;
		mod->xxs[i].flg = mod->xxs[i].lpe > 0 ? XMP_SAMPLE_LOOP : 0;
		mod->xxi[i].sub[0].fin = 0;
		mod->xxi[i].sub[0].pan = 0x80;
#endif

		D_(D_INFO "[%2X] %-22.22s %04x %04x %04x %c V%02x", i,
				mod->xxi[i].name,
				mod->xxs[i].len, mod->xxs[i].lps, mod->xxs[i].lpe,
				mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
				mod->xxi[i].sub[0].vol);
	}

	return 0;
}
コード例 #24
0
ファイル: mfp_load.c プロジェクト: EQ4/libxmp
static int mfp_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
	struct xmp_module *mod = &m->mod;
	int i, j, k, x, y;
	struct xmp_event *event;
	struct stat st;
	char smp_filename[PATH_MAX];
	HIO_HANDLE *s;
	int size1 /*, size2*/;
	int pat_addr, pat_table[128][4];
	uint8 buf[1024], mod_event[4];
	int row;

	LOAD_INIT();

	set_type(m, "Magnetic Fields Packer");
	MODULE_INFO();

	mod->chn = 4;
	mod->ins = mod->smp = 31;

	if (instrument_init(mod) < 0)
		return -1;

	for (i = 0; i < 31; i++) {
		int loop_size;

		if (subinstrument_alloc(mod, i, 1) < 0)
			return -1;
		
		mod->xxs[i].len = 2 * hio_read16b(f);
		mod->xxi[i].sub[0].fin = (int8)(hio_read8(f) << 4);
		mod->xxi[i].sub[0].vol = hio_read8(f);
		mod->xxs[i].lps = 2 * hio_read16b(f);
		loop_size = hio_read16b(f);

		mod->xxs[i].lpe = mod->xxs[i].lps + 2 * loop_size;
		mod->xxs[i].flg = loop_size > 1 ? XMP_SAMPLE_LOOP : 0;
		mod->xxi[i].sub[0].pan = 0x80;
		mod->xxi[i].sub[0].sid = i;
		mod->xxi[i].rls = 0xfff;

		if (mod->xxs[i].len > 0)
			mod->xxi[i].nsm = 1;

               	D_(D_INFO "[%2X] %04x %04x %04x %c V%02x %+d",
                       	i, mod->xxs[i].len, mod->xxs[i].lps,
                       	mod->xxs[i].lpe,
			loop_size > 1 ? 'L' : ' ',
                       	mod->xxi[i].sub[0].vol, mod->xxi[i].sub[0].fin >> 4);
	}

	mod->len = mod->pat = hio_read8(f);
	hio_read8(f);		/* restart */

	for (i = 0; i < 128; i++)
		mod->xxo[i] = hio_read8(f);

#if 0
	for (i = 0; i < 128; i++) {
		mod->xxo[i] = hio_read8(f);
		if (mod->xxo[i] > mod->pat)
			mod->pat = mod->xxo[i];
	}
	mod->pat++;
#endif

	mod->trk = mod->pat * mod->chn;

	/* Read and convert patterns */

	if (pattern_init(mod) < 0)
		return -1;

	size1 = hio_read16b(f);
	/* size2 = */ hio_read16b(f);

	for (i = 0; i < size1; i++) {		/* Read pattern table */
		for (j = 0; j < 4; j++) {
			pat_table[i][j] = hio_read16b(f);
		}
	}

	D_(D_INFO "Stored patterns: %d ", mod->pat);

	pat_addr = hio_tell(f);

	for (i = 0; i < mod->pat; i++) {
		if (pattern_tracks_alloc(mod, i, 64) < 0)
			return -1;

		for (j = 0; j < 4; j++) {
			hio_seek(f, pat_addr + pat_table[i][j], SEEK_SET);

			hio_read(buf, 1, 1024, f);

			for (row = k = 0; k < 4; k++) {
				for (x = 0; x < 4; x++) {
					for (y = 0; y < 4; y++, row++) {
						event = &EVENT(i, j, row);
						memcpy(mod_event, &buf[buf[buf[buf[k] + x] + y] * 2], 4);
						decode_protracker_event(event, mod_event);
					}
				}
			}
		}
	}

	/* Read samples */
	D_(D_INFO "Loading samples: %d", mod->ins);

	/* first check smp.filename */
	if (strlen(m->basename) < 5 || m->basename[3] != '.') {
		fprintf(stderr, "libxmp: invalid filename %s\n", m->basename);
		goto err;
	}

	m->basename[0] = 's';
	m->basename[1] = 'm';
	m->basename[2] = 'p';
	snprintf(smp_filename, PATH_MAX, "%s%s", m->dirname, m->basename);
	if (stat(smp_filename, &st) < 0) {
		/* handle .set filenames like in Kid Chaos*/
		char *x;
		if (strchr(m->basename, '-')) {
			if ((x = strrchr(smp_filename, '-')))
				strcpy(x, ".set");
		}
		if (stat(smp_filename, &st) < 0) {
			fprintf(stderr, "libxmp: missing file %s\n",
								smp_filename);
			goto err;
		}
	}
	if ((s = hio_open(smp_filename, "rb")) == NULL) {
		fprintf(stderr, "libxmp: can't open sample file %s\n",
								smp_filename);
		goto err;
	}

	for (i = 0; i < mod->ins; i++) {
		if (load_sample(m, s, SAMPLE_FLAG_FULLREP,
				&mod->xxs[mod->xxi[i].sub[0].sid], NULL) < 0) {
			free(s);
			return -1;
		}
	}

	hio_close(s);

	m->quirk |= QUIRK_MODRNG;

	return 0;

    err:
	for (i = 0; i < mod->ins; i++) {
		mod->xxi[i].nsm = 0;
		memset(&mod->xxs[i], 0, sizeof(struct xmp_sample));
	}

	return 0;
}
コード例 #25
0
ファイル: stm_load.c プロジェクト: GCrean/libxmp
static int stm_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
    struct xmp_module *mod = &m->mod;
    int i, j;
    struct xmp_event *event;
    struct stm_file_header sfh;
    uint8 b;
    int bmod2stm = 0;

    LOAD_INIT();

    hio_read(&sfh.name, 20, 1, f);		/* ASCIIZ song name */
    hio_read(&sfh.magic, 8, 1, f);		/* '!Scream!' */
    sfh.rsvd1 = hio_read8(f);			/* '\x1a' */
    sfh.type = hio_read8(f);			/* 1=song, 2=module */
    sfh.vermaj = hio_read8(f);			/* Major version number */
    sfh.vermin = hio_read8(f);			/* Minor version number */
    sfh.tempo = hio_read8(f);			/* Playback tempo */
    sfh.patterns = hio_read8(f);		/* Number of patterns */
    sfh.gvol = hio_read8(f);			/* Global volume */
    hio_read(&sfh.rsvd2, 13, 1, f);		/* Reserved */

    for (i = 0; i < 31; i++) {
	hio_read(&sfh.ins[i].name, 12, 1, f);	/* ASCIIZ instrument name */
	sfh.ins[i].id = hio_read8(f);		/* Id=0 */
	sfh.ins[i].idisk = hio_read8(f);	/* Instrument disk */
	sfh.ins[i].rsvd1 = hio_read16l(f);	/* Reserved */
	sfh.ins[i].length = hio_read16l(f);	/* Sample length */
	sfh.ins[i].loopbeg = hio_read16l(f);	/* Loop begin */
	sfh.ins[i].loopend = hio_read16l(f);	/* Loop end */
	sfh.ins[i].volume = hio_read8(f);	/* Playback volume */
	sfh.ins[i].rsvd2 = hio_read8(f);	/* Reserved */
	sfh.ins[i].c2spd = hio_read16l(f);	/* C4 speed */
	sfh.ins[i].rsvd3 = hio_read32l(f);	/* Reserved */
	sfh.ins[i].paralen = hio_read16l(f);	/* Length in paragraphs */
    }

    if (!strncmp ((char *)sfh.magic, "BMOD2STM", 8))
	bmod2stm = 1;

    mod->pat = sfh.patterns;
    mod->trk = mod->pat * mod->chn;
    mod->spd = MSN (sfh.tempo);
    mod->ins = 31;
    mod->smp = mod->ins;
    m->c4rate = C4_NTSC_RATE;

    copy_adjust(mod->name, sfh.name, 20);

    if (bmod2stm) {
	snprintf(mod->type, XMP_NAME_SIZE, "BMOD2STM STM");
    } else {
	snprintf(mod->type, XMP_NAME_SIZE, "Scream Tracker %d.%02d STM",
						sfh.vermaj, sfh.vermin);
    }

    MODULE_INFO();

    if (instrument_init(mod) < 0)
	return -1;

    /* Read and convert instruments and samples */
    for (i = 0; i < mod->ins; i++) {
	if (subinstrument_alloc(mod, i, 1) < 0)
	    return -1;

	mod->xxs[i].len = sfh.ins[i].length;
	mod->xxs[i].lps = sfh.ins[i].loopbeg;
	mod->xxs[i].lpe = sfh.ins[i].loopend;
	if (mod->xxs[i].lpe == 0xffff)
	    mod->xxs[i].lpe = 0;
	mod->xxs[i].flg = mod->xxs[i].lpe > 0 ? XMP_SAMPLE_LOOP : 0;
	mod->xxi[i].sub[0].vol = sfh.ins[i].volume;
	mod->xxi[i].sub[0].pan = 0x80;
	mod->xxi[i].sub[0].sid = i;

	if (mod->xxs[i].len > 0)
		mod->xxi[i].nsm = 1;

	instrument_name(mod, i, sfh.ins[i].name, 12);

	D_(D_INFO "[%2X] %-14.14s %04x %04x %04x %c V%02x %5d", i,
		mod->xxi[i].name, mod->xxs[i].len, mod->xxs[i].lps,
		mod->xxs[i].lpe, mod->xxs[i].flg & XMP_SAMPLE_LOOP ? 'L' : ' ',
		mod->xxi[i].sub[0].vol, sfh.ins[i].c2spd);

	sfh.ins[i].c2spd = 8363 * sfh.ins[i].c2spd / 8448;
	c2spd_to_note (sfh.ins[i].c2spd, &mod->xxi[i].sub[0].xpo, &mod->xxi[i].sub[0].fin);
    }

    hio_read(mod->xxo, 1, 128, f);

    for (i = 0; i < 128; i++)
	if (mod->xxo[i] >= mod->pat)
	    break;

    mod->len = i;

    D_(D_INFO "Module length: %d", mod->len);

    if (pattern_init(mod) < 0)
	return -1;

    /* Read and convert patterns */
    D_(D_INFO "Stored patterns: %d", mod->pat);

    for (i = 0; i < mod->pat; i++) {
	if (pattern_tracks_alloc(mod, i, 64) < 0)
	    return -1;

	for (j = 0; j < 64 * mod->chn; j++) {
	    event = &EVENT (i, j % mod->chn, j / mod->chn);
	    b = hio_read8(f);
	    memset (event, 0, sizeof (struct xmp_event));
	    switch (b) {
	    case 251:
	    case 252:
	    case 253:
		break;
	    case 255:
		b = 0;
	    default:
		event->note = b ? 13 + LSN(b) + 12 * (2 + MSN(b)) : 0;
		b = hio_read8(f);
		event->vol = b & 0x07;
		event->ins = (b & 0xf8) >> 3;
		b = hio_read8(f);
		event->vol += (b & 0xf0) >> 1;
		if (event->vol > 0x40)
		    event->vol = 0;
		else
		    event->vol++;
		event->fxt = fx[LSN(b)];
		event->fxp = hio_read8(f);
		switch (event->fxt) {
		case FX_SPEED:
		    event->fxp = MSN (event->fxp);
		    break;
		case FX_NONE:
		    event->fxp = event->fxt = 0;
		    break;
		}
	    }
	}
    }

    /* Read samples */
    D_(D_INFO "Stored samples: %d", mod->smp);

    for (i = 0; i < mod->ins; i++) {
	if (mod->xxs[i].len > 1) {
	    if (load_sample(m, f, 0, &mod->xxs[i], NULL) < 0)
		return -1;
	} else {
	    mod->xxi[i].nsm = 0;
	}
    }

    m->quirk |= QUIRK_VSALL | QUIRKS_ST3;
    m->read_event_type = READ_EVENT_ST3;

    return 0;
}
コード例 #26
0
static int mod_load(struct module_data *m, HIO_HANDLE *f, const int start)
{
    struct xmp_module *mod = &m->mod;
    int i, j;
    struct xmp_event *event;
    struct mod_header mh;
    uint8 mod_event[4];
    char magic[8];
    int ptkloop = 0;			/* Protracker loop */

    LOAD_INIT();

    mod->ins = 31;
    mod->smp = mod->ins;
    mod->chn = 0;

    m->quirk |= QUIRK_MODRNG;

    hio_read(&mh.name, 20, 1, f);
    for (i = 0; i < 31; i++) {
	hio_read(&mh.ins[i].name, 22, 1, f);	/* Instrument name */
	mh.ins[i].size = hio_read16b(f);	/* Length in 16-bit words */
	mh.ins[i].finetune = hio_read8(f);	/* Finetune (signed nibble) */
	mh.ins[i].volume = hio_read8(f);	/* Linear playback volume */
	mh.ins[i].loop_start = hio_read16b(f);	/* Loop start in 16-bit words */
	mh.ins[i].loop_size = hio_read16b(f);	/* Loop size in 16-bit words */
    }
    mh.len = hio_read8(f);
    mh.restart = hio_read8(f);
    hio_read(&mh.order, 128, 1, f);
    memset(magic, 0, 8);
    hio_read(magic, 4, 1, f);

    if (!memcmp(magic, "M.K.", 4)) {
	mod->chn = 4;
    } else if (!strncmp(magic + 2, "CH", 2) &&
	isdigit((int)magic[0]) && isdigit((int)magic[1])) {
	mod->chn = (*magic - '0') * 10 + magic[1] - '0';
    } else if (!strncmp(magic + 1, "CHN", 3) && isdigit((int)*magic)) {
	mod->chn = *magic - '0';
    } else {
	return -1;
    }

    strncpy(mod->name, (char *) mh.name, 20);

    mod->len = mh.len;
    /* mod->rst = mh.restart; */

    if (mod->rst >= mod->len)
	mod->rst = 0;
    memcpy(mod->xxo, mh.order, 128);

    for (i = 0; i < 128; i++) {
	/* This fixes dragnet.mod (garbage in the order list) */
	if (mod->xxo[i] > 0x7f)
		break;
	if (mod->xxo[i] > mod->pat)
	    mod->pat = mod->xxo[i];
    }
    mod->pat++;

    if (instrument_init(mod) < 0)
	return -1;

    for (i = 0; i < mod->ins; i++) {
	if (subinstrument_alloc(mod, i, 1) < 0)
	    return -1;

	mod->xxs[i].len = 2 * mh.ins[i].size;
	mod->xxs[i].lps = 2 * mh.ins[i].loop_start;
	mod->xxs[i].lpe = mod->xxs[i].lps + 2 * mh.ins[i].loop_size;
	if (mod->xxs[i].lpe > mod->xxs[i].len)
		mod->xxs[i].lpe = mod->xxs[i].len;
	mod->xxs[i].flg = (mh.ins[i].loop_size > 1 && mod->xxs[i].lpe >= 4) ?
		XMP_SAMPLE_LOOP : 0;
	mod->xxi[i].sub[0].fin = (int8)(mh.ins[i].finetune << 4);
	mod->xxi[i].sub[0].vol = mh.ins[i].volume;
	mod->xxi[i].sub[0].pan = 0x80;
	mod->xxi[i].sub[0].sid = i;
	instrument_name(mod, i, mh.ins[i].name, 22);

	if (mod->xxs[i].len > 0)
		mod->xxi[i].nsm = 1;
    }

    mod->trk = mod->chn * mod->pat;

    set_type(m, mod->chn == 4 ? "Protracker" : "Fasttracker");

    MODULE_INFO();

    for (i = 0; i < mod->ins; i++) {
	D_(D_INFO "[%2X] %-22.22s %04x %04x %04x %c V%02x %+d %c\n",
		i, mod->xxi[i].name,
		mod->xxs[i].len, mod->xxs[i].lps, mod->xxs[i].lpe,
		(mh.ins[i].loop_size > 1 && mod->xxs[i].lpe > 8) ?
			'L' : ' ', mod->xxi[i].sub[0].vol,
		mod->xxi[i].sub[0].fin >> 4,
		ptkloop && mod->xxs[i].lps == 0 && mh.ins[i].loop_size > 1 &&
			mod->xxs[i].len > mod->xxs[i].lpe ? '!' : ' ');
    }

    if (pattern_init(mod) < 0)
	return -1;

    /* Load and convert patterns */
    D_(D_INFO "Stored patterns: %d", mod->pat);

    for (i = 0; i < mod->pat; i++) {
	if (pattern_tracks_alloc(mod, i, 64) < 0)
	    return -1;

	for (j = 0; j < (64 * mod->chn); j++) {
	    event = &EVENT (i, j % mod->chn, j / mod->chn);
	    hio_read (mod_event, 1, 4, f);
	    decode_protracker_event(event, mod_event);
	}
    }

    /* Load samples */

    D_(D_INFO "Stored samples: %d", mod->smp);

    for (i = 0; i < mod->smp; i++) {
	int flags;

	if (!mod->xxs[i].len)
	    continue;

	flags = ptkloop ? SAMPLE_FLAG_FULLREP : 0;

	if (load_sample(m, f, flags, &mod->xxs[i], NULL) < 0)
	    return -1;
    }

    if (mod->chn > 4) {
	m->quirk &= ~QUIRK_MODRNG;
	m->quirk |= QUIRKS_FT2;
	m->read_event_type = READ_EVENT_FT2;
	m->quirk |= QUIRK_INVLOOP;
    }

    return 0;
}