From: Toni Wilen Date: Sun, 26 Apr 2009 09:35:45 +0000 (+0300) Subject: imported winuaesrc1600b26.zip X-Git-Tag: 2100~84 X-Git-Url: https://git.unchartedbackwaters.co.uk/w/?a=commitdiff_plain;h=e9da7dc5925db8bc9d2a58540fc72e830676cb22;p=francis%2Fwinuae.git imported winuaesrc1600b26.zip --- diff --git a/adide.c b/adide.c new file mode 100644 index 00000000..29f97599 --- /dev/null +++ b/adide.c @@ -0,0 +1,37 @@ + /* + * UAE - The Un*x Amiga Emulator + * + * ADIDE + * + * (c) 2009 Toni Wilen + */ + +#include "sysconfig.h" +#include "sysdeps.h" + +#include "options.h" +#include "gayle.h" + +static struct ide_hdf *idedrive[2]; + +int adide_add_ide_unit (int ch, TCHAR *path, int blocksize, int readonly, + TCHAR *devname, int sectors, int surfaces, int reserved, + int bootpri, TCHAR *filesys) +{ + struct ide_hdf *ide; + + if (ch >= 2) + return -1; + alloc_ide_mem (); + ide = idedrive[ch]; + if (!hdf_hd_open (&ide->hdhfd, path, blocksize, readonly, devname, sectors, surfaces, reserved, bootpri, filesys)) + return -1; + ide->lba48 = ide->hdhfd.size >= 128 * (uae_u64)0x40000000 ? 1 : 0; + write_log (L"IDE%d '%s', CHS=%d,%d,%d. %uM. LBA48=%d\n", + ch, path, ide->hdhfd.cyls, ide->hdhfd.heads, ide->hdhfd.secspertrack, (int)(ide->hdhfd.size / (1024 * 1024)), ide->lba48); + ide->status = 0; + ide->data_offset = 0; + ide->data_size = 0; + //dumphdf (&ide->hdhfd.hfd); + return 1; +} diff --git a/ar.c b/ar.c index cec5746b..361c73c9 100644 --- a/ar.c +++ b/ar.c @@ -1767,7 +1767,7 @@ static void hrtmon_configure(void) do_put_mem_long (&cfg->max_chip, currprefs.chipmem_size); do_put_mem_long (&cfg->mon_size, 0x800000); cfg->ide = currprefs.cs_ide ? 1 : 0; - cfg->a1200 = currprefs.cs_ide == 1 ? 1 : 0; /* type of IDE interface, not Amiga model */ + cfg->a1200 = currprefs.cs_ide == IDE_A600A1200 ? 1 : 0; /* type of IDE interface, not Amiga model */ } int hrtmon_load (void) diff --git a/cfgfile.c b/cfgfile.c index c5a5d844..b5803eee 100644 --- a/cfgfile.c +++ b/cfgfile.c @@ -693,6 +693,7 @@ void cfgfile_save_options (struct zfile *f, struct uae_prefs *p, int type) cfgfile_write_bool (f, L"ntsc", p->ntscmode); cfgfile_write_bool (f, L"genlock", p->genlock); cfgfile_dwrite_bool (f, L"show_leds", p->leds_on_screen & STATUSLINE_CHIPSET); + //cfgfile_dwrite_bool (f, L"show_leds_rtg", p->leds_on_screen & STATUSLINE_RTG); cfgfile_dwrite (f, L"keyboard_leds", L"numlock:%s,capslock:%s,scrolllock:%s", kbleds[p->keyboard_leds[0]], kbleds[p->keyboard_leds[1]], kbleds[p->keyboard_leds[2]]); if (p->chipset_mask & CSMASK_AGA) @@ -720,7 +721,7 @@ void cfgfile_save_options (struct zfile *f, struct uae_prefs *p, int type) cfgfile_dwrite_bool (f, L"cdtvcd", p->cs_cdtvcd); cfgfile_dwrite_bool (f, L"cdtvram", p->cs_cdtvram); cfgfile_dwrite (f, L"cdtvramcard", L"%d", p->cs_cdtvcard); - cfgfile_dwrite_str (f, L"ide", p->cs_ide == 1 ? L"a600/a1200" : (p->cs_ide == 2 ? L"a4000" : L"none")); + cfgfile_dwrite_str (f, L"ide", p->cs_ide == IDE_A600A1200 ? L"a600/a1200" : (p->cs_ide == IDE_A4000 ? L"a4000" : L"none")); cfgfile_dwrite_bool (f, L"a1000ram", p->cs_a1000ram); cfgfile_dwrite (f, L"fatgary", L"%d", p->cs_fatgaryrev); cfgfile_dwrite (f, L"ramsey", L"%d", p->cs_ramseyrev); @@ -917,7 +918,7 @@ static void set_chipset_mask (struct uae_prefs *p, int val) static int cfgfile_parse_host (struct uae_prefs *p, TCHAR *option, TCHAR *value) { - int i; + int i, v; TCHAR *section = 0; TCHAR *tmpp; TCHAR tmpbuf[CONFIG_BLEN]; @@ -1039,7 +1040,6 @@ static int cfgfile_parse_host (struct uae_prefs *p, TCHAR *option, TCHAR *value) || cfgfile_yesno (option, value, L"gfx_vsync_picasso", &p->gfx_pvsync) || cfgfile_yesno (option, value, L"gfx_blacker_than_black", &p->gfx_blackerthanblack) || cfgfile_yesno (option, value, L"gfx_flickerfixer", &p->gfx_scandoubler) - || cfgfile_yesno (option, value, L"show_leds", &p->leds_on_screen) || cfgfile_yesno (option, value, L"synchronize_clock", &p->tod_hack) || cfgfile_yesno (option, value, L"magic_mouse", &p->input_magic_mouse) || cfgfile_yesno (option, value, L"bsdsocket_emu", &p->socket_emu)) @@ -1076,6 +1076,15 @@ static int cfgfile_parse_host (struct uae_prefs *p, TCHAR *option, TCHAR *value) return 1; + if (cfgfile_yesno (option, value, L"show_leds", &v)) { + p->leds_on_screen |= STATUSLINE_CHIPSET; + return 1; + } + if (cfgfile_yesno (option, value, L"show_leds_rtg", &v)) { + p->leds_on_screen |= STATUSLINE_RTG; + return 1; + } + #ifdef GFXFILTER if (_tcscmp (option, L"gfx_filter") == 0) { int i = 0; @@ -3907,7 +3916,7 @@ int built_in_chipset_prefs (struct uae_prefs *p) break; case CP_A600: // A600 p->cs_rtc = 1; - p->cs_ide = 1; + p->cs_ide = IDE_A600A1200; p->cs_pcmcia = 1; p->cs_ksmirror_a8 = 1; p->cs_ciaoverlay = 0; @@ -3921,7 +3930,7 @@ int built_in_chipset_prefs (struct uae_prefs *p) p->cs_agnusbltbusybug = 1; break; case CP_A1200: // A1200 - p->cs_ide = 1; + p->cs_ide = IDE_A600A1200; p->cs_pcmcia = 1; p->cs_ksmirror_a8 = 1; p->cs_ciaoverlay = 0; @@ -3948,7 +3957,7 @@ int built_in_chipset_prefs (struct uae_prefs *p) p->cs_rtc = 2; p->cs_fatgaryrev = 0; p->cs_ramseyrev = 0x0f; - p->cs_ide = 2; + p->cs_ide = IDE_A4000; p->cs_mbdmac = 0; p->cs_ksmirror_a8 = 1; p->cs_ciaoverlay = 0; @@ -3957,7 +3966,7 @@ int built_in_chipset_prefs (struct uae_prefs *p) p->cs_rtc = 2; p->cs_fatgaryrev = 0; p->cs_ramseyrev = 0x0f; - p->cs_ide = 2; + p->cs_ide = IDE_A4000; p->cs_mbdmac = 2; p->cs_ksmirror_a8 = 1; p->cs_ciaoverlay = 0; diff --git a/cia.c b/cia.c index b7891b0f..c12cc221 100644 --- a/cia.c +++ b/cia.c @@ -1204,7 +1204,7 @@ addrbank cia_bank = { STATIC_INLINE isgayle (void) { - return (currprefs.cs_ide == 1 || currprefs.cs_pcmcia); + return (currprefs.cs_ide == IDE_A600A1200 || currprefs.cs_pcmcia); } /* e-clock is 10 CPU cycles, 6 cycles low, 4 high diff --git a/drawing.c b/drawing.c index 1edd21a3..3367446c 100644 --- a/drawing.c +++ b/drawing.c @@ -369,21 +369,28 @@ int get_custom_limits (int *pw, int *ph, int *pdx, int *pdy) if (minfirstline > y1) y1 = minfirstline; + dbl2 = dbl1 = currprefs.gfx_linedbl ? 1 : 0; + if (doublescan > 0 && interlace_seen <= 0) { + dbl1--; + dbl2--; + } + h = y2 - y1; dy = y1 - minfirstline; - if (first_planes_vpos == 0) - h = 0; // no planes enabled during frame + if (first_planes_vpos == 0) { + // no planes enabled during frame + if (ret < 0) + return 1; + h = currprefs.ntscmode ? 200 : 240; + w = 320 << currprefs.gfx_resolution; + dy = 36 / 2; + dx = 58; + } if (dx < 0) dx = 1; - dbl2 = dbl1 = currprefs.gfx_linedbl ? 1 : 0; - if (doublescan > 0 && interlace_seen <= 0) { - dbl1--; - dbl2--; - } - dy = xshift (dy, dbl2); h = xshift (h, dbl1); diff --git a/driveclick.c b/driveclick.c index 7f8f9abc..feb809d3 100644 --- a/driveclick.c +++ b/driveclick.c @@ -216,7 +216,7 @@ void driveclick_reset (void) clickbuffer = NULL; if (!wave_initialized) return; - clickbuffer = xmalloc (sndbufsize); + clickbuffer = xmalloc (paula_sndbufsize); sample_step = (freq << DS_SHIFT) / currprefs.sound_freq; } @@ -305,7 +305,7 @@ static int clickcnt; static void mix (void) { - int total = ((uae_u8*)sndbufpt - (uae_u8*)sndbuffer) / (get_audio_nativechannels () * 2); + int total = ((uae_u8*)paula_sndbufpt - (uae_u8*)paula_sndbuffer) / (get_audio_nativechannels () * 2); if (currprefs.dfxclickvolume > 0) { while (clickcnt < total) { diff --git a/expansion.c b/expansion.c index 255f2e02..00f09ca8 100644 --- a/expansion.c +++ b/expansion.c @@ -26,6 +26,7 @@ #include "cd32_fmv.h" #include "ncr_scsi.h" #include "debug.h" +#include "gayle.h" #define MAX_EXPANSION_BOARDS 8 @@ -1255,15 +1256,15 @@ void expamem_next (void) static void expamem_init_cdtv (void) { - cdtv_init(); + cdtv_init (); } static void expamem_init_a2091 (void) { - a2091_init(); + a2091_init (); } static void expamem_init_a4091 (void) { - ncr_init(); + ncr_init (); } void p96memstart(void) diff --git a/filesys.c b/filesys.c index 99ef96f4..5a5b809c 100644 --- a/filesys.c +++ b/filesys.c @@ -587,7 +587,7 @@ static void initialize_mountinfo(void) ui = &mountinfo.ui[idx]; ui->configureddrive = 1; } - } else if (uci->controller <= HD_CONTROLLER_IDE3 ) { + } else if (uci->controller <= HD_CONTROLLER_IDE3) { gayle_add_ide_unit (uci->controller - HD_CONTROLLER_IDE0, uci->rootdir, uci->blocksize, uci->readonly, uci->devname, uci->sectors, uci->surfaces, uci->reserved, uci->bootpri, uci->filesys); @@ -5482,7 +5482,7 @@ static int rdb_mount (UnitInfo *uip, int unit_no, int partnum, uaecptr parmpacke write_log (L"RDB: RDB filesystem %08X version %d.%d\n", dostype, newversion, newrevision); if (fsnode) { - write_log (L"RDB: %08X in FileSystem.resouce version %d.%d\n", dostype, oldversion, oldrevision); + write_log (L"RDB: %08X in FileSystem.resource version %d.%d\n", dostype, oldversion, oldrevision); } if (newversion * 65536 + newrevision <= oldversion * 65536 + oldrevision && oldversion >= 0) { write_log (L"RDB: FS in FileSystem.resource is newer or same, ignoring RDB filesystem\n"); diff --git a/gayle.c b/gayle.c index 56184ceb..1c0bfef2 100644 --- a/gayle.c +++ b/gayle.c @@ -19,8 +19,8 @@ #include "memory.h" #include "custom.h" #include "newcpu.h" -#include "gayle.h" #include "filesys.h" +#include "gayle.h" #include "savestate.h" #include "uae.h" #include "gui.h" @@ -152,13 +152,16 @@ DE0000 to DEFFFF 64 KB Motherboard resources #define GAYLE_CFG_250NS 0x00 #define GAYLE_CFG_720NS 0x0c -#define MAX_MULTIPLE_SECTORS 128 +#define IDE_GAYLE 0 +#define IDE_ADIDE 1 + +#define MAX_IDE_MULTIPLE_SECTORS 128 struct ide_hdf { struct hd_hardfiledata hdhfd; - uae_u8 secbuf[512 * (MAX_MULTIPLE_SECTORS * 2)]; + uae_u8 secbuf[512 * (MAX_IDE_MULTIPLE_SECTORS * 2)]; int data_offset; int data_size; int data_multi; @@ -168,6 +171,7 @@ struct ide_hdf int irq_delay; int irq; int num; + int type; }; static struct ide_hdf *idedrive[4]; @@ -228,14 +232,14 @@ void rethink_gayle (void) int lev6 = 0; uae_u8 mask; - if (currprefs.cs_ide == 2) { + if (currprefs.cs_ide == IDE_A4000) { if (isideirq ()) gayle_irq |= GAYLE_IRQ_IDE; if ((gayle_irq & GAYLE_IRQ_IDE) && !(intreq & 0x0008)) INTREQ_0 (0x8000 | 0x0008); } - if (currprefs.cs_ide != 1 && !currprefs.cs_pcmcia) + if (currprefs.cs_ide != IDE_A600A1200 && !currprefs.cs_pcmcia) return; if (isideirq ()) gayle_irq |= GAYLE_IRQ_IDE; @@ -428,7 +432,7 @@ static void ide_identify_drive (void) ps (23, L"0.3", 8); /* firmware revision */ _stprintf (tmp, L"UAE-IDE %s", ide->hdhfd.hfd.product_id); ps (27, tmp, 40); /* model */ - pw (47, MAX_MULTIPLE_SECTORS); /* max sectors in multiple mode */ + pw (47, MAX_IDE_MULTIPLE_SECTORS); /* max sectors in multiple mode */ pw (48, 1); pw (49, (1 << 9) | (1 << 8)); /* LBA and DMA supported */ pw (51, 0x200); /* PIO cycles */ @@ -756,7 +760,7 @@ static int get_ide_reg (uaecptr addr) { uaecptr a = addr; addr &= 0xffff; - if (addr >= 0x3020 && addr <= 0x3021 && currprefs.cs_ide == 2) + if (addr >= 0x3020 && addr <= 0x3021 && currprefs.cs_ide == IDE_A4000) return -1; addr &= ~0x2020; addr >>= 2; @@ -784,18 +788,18 @@ static uae_u32 ide_read (uaecptr addr) return 0x7f; return 0xff; } - if (addr >= GAYLE_IRQ_4000 && addr <= GAYLE_IRQ_4000 + 1 && currprefs.cs_ide == 2) { + if (addr >= GAYLE_IRQ_4000 && addr <= GAYLE_IRQ_4000 + 1 && currprefs.cs_ide == IDE_A4000) { uae_u8 v = gayle_irq; gayle_irq = 0; return v; } if (addr >= 0x4000) { if (addr == GAYLE_IRQ_1200) { - if (currprefs.cs_ide == 1) + if (currprefs.cs_ide == IDE_A600A1200) return read_gayle_irq (); return 0; } else if (addr == GAYLE_INT_1200) { - if (currprefs.cs_ide == 1) + if (currprefs.cs_ide == IDE_A600A1200) return read_gayle_int (); return 0; } @@ -871,7 +875,7 @@ static void ide_write (uaecptr addr, uae_u32 val) write_log (L"IDE_WRITE %08X=%02X PC=%X\n", addr, (uae_u32)val & 0xff, M68K_GETPC); if (currprefs.cs_ide <= 0) return; - if (currprefs.cs_ide == 1) { + if (currprefs.cs_ide == IDE_A600A1200) { if (addr == GAYLE_IRQ_1200) { write_gayle_irq (val); return; @@ -937,7 +941,7 @@ static int gayle_read (uaecptr addr) #endif addr &= 0xffff; if (currprefs.cs_pcmcia) { - if (currprefs.cs_ide != 1) { + if (currprefs.cs_ide != IDE_A600A1200) { if (addr == GAYLE_IRQ_1200) { v = read_gayle_irq (); got = 1; @@ -973,7 +977,7 @@ static void gayle_write (uaecptr addr, int val) #endif addr &= 0xffff; if (currprefs.cs_pcmcia) { - if (currprefs.cs_ide != 1) { + if (currprefs.cs_ide != IDE_A600A1200) { if (addr == GAYLE_IRQ_1200) { write_gayle_irq (val); got = 1; @@ -1762,13 +1766,13 @@ void gayle_free_units (void) freepcmcia (1); } -static void alloc_ide_mem (void) +static void alloc_ide_mem (struct ide_hdf **ide, int max) { int i; - for (i = 0; i < 4; i++) { - if (!idedrive[i]) - idedrive[i] = xcalloc (sizeof (struct ide_hdf), 1); + for (i = 0; i < max; i++) { + if (!ide[i]) + ide[i] = xcalloc (sizeof (struct ide_hdf), 1); } } @@ -1800,16 +1804,17 @@ int gayle_add_ide_unit (int ch, TCHAR *path, int blocksize, int readonly, if (ch >= 4) return -1; - alloc_ide_mem (); + alloc_ide_mem (idedrive, 4); ide = idedrive[ch]; if (!hdf_hd_open (&ide->hdhfd, path, blocksize, readonly, devname, sectors, surfaces, reserved, bootpri, filesys)) return -1; ide->lba48 = ide->hdhfd.size >= 128 * (uae_u64)0x40000000 ? 1 : 0; - write_log (L"IDE%d '%s', CHS=%d,%d,%d. %uM. LBA48=%d\n", + write_log (L"GAYLE_IDE%d '%s', CHS=%d,%d,%d. %uM. LBA48=%d\n", ch, path, ide->hdhfd.cyls, ide->hdhfd.heads, ide->hdhfd.secspertrack, (int)(ide->hdhfd.size / (1024 * 1024)), ide->lba48); ide->status = 0; ide->data_offset = 0; ide->data_size = 0; + ide->type = IDE_GAYLE; //dumphdf (&ide->hdhfd.hfd); return 1; } @@ -1831,7 +1836,7 @@ static void initide (void) { int i; - alloc_ide_mem (); + alloc_ide_mem (idedrive, 4); if (savestate_state == STATE_RESTORE) return; ide_error = 1; @@ -1861,7 +1866,7 @@ void gayle_reset (int hardreset) gary_toenb = 0; } _tcscpy (bankname, L"Gayle (low)"); - if (currprefs.cs_ide == 2) + if (currprefs.cs_ide == IDE_A4000) _tcscpy (bankname, L"A4000 IDE"); if (currprefs.cs_mbdmac == 2) { _tcscat (bankname, L" + NCR53C710 SCSI"); @@ -1950,7 +1955,7 @@ uae_u8 *restore_ide (uae_u8 *src) TCHAR *path; struct ide_hdf *ide; - alloc_ide_mem (); + alloc_ide_mem (idedrive, 4); num = restore_u32 (); ide = idedrive[num]; size = restore_u64 (); diff --git a/hardfile.c b/hardfile.c index bbf4d945..26c4a739 100644 --- a/hardfile.c +++ b/hardfile.c @@ -349,11 +349,13 @@ static uae_u32 vhd_checksum (uae_u8 *p, int offset) return ~sum; } -int hdf_open (struct hardfiledata *hfd, const TCHAR *pname) +static int hdf_open2 (struct hardfiledata *hfd, const TCHAR *pname) { uae_u8 tmp[512], tmp2[512]; uae_u32 v; + hfd->adide = 0; + hfd->byteswap = 0; if (!hdf_open_target (hfd, pname)) return 0; if (hdf_read_target (hfd, tmp, 0, 512) != 512) @@ -415,6 +417,25 @@ end: return 0; } +int hdf_open (struct hardfiledata *hfd, const TCHAR *pname) +{ + int v; + uae_u8 buf[512]; + + v = hdf_open2 (hfd, pname); + if (!v) + return v; + memset (buf, 0, sizeof buf); + hdf_read (hfd, buf, 0, sizeof buf); + if (buf[0] == 0x39 && buf[1] == 0x10 && buf[2] == 0xd3 && buf[3] == 0x12) { // AdIDE encoded "CPRM" + hfd->adide = 1; + } + if (!memcmp (buf, "DRKS", 4)) { + hfd->byteswap = 1; + } + return v; +} + void hdf_close (struct hardfiledata *hfd) { hdf_close_target (hfd); @@ -694,7 +715,7 @@ static uae_u64 vhd_write (struct hardfiledata *hfd, uae_u8 *dataptr, uae_u64 off return written; } -int hdf_read (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) +static int hdf_read2 (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) { if (hfd->vhd_type == VHD_DYNAMIC) return vhd_read (hfd, buffer, offset, len); @@ -703,7 +724,139 @@ int hdf_read (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) else return hdf_read_target (hfd, buffer, offset, len); } -int hdf_write (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) + +static void adide_decode (uae_u8 *buffer, int len) +{ + int i; + for (i = 0; i < len; i += 2) { + uae_u8 *b = buffer + i; + uae_u16 w = (b[0] << 8) | (b[1] << 0); + uae_u16 o = 0; + + if (w & 0x8000) + o |= 0x0001; + if (w & 0x0001) + o |= 0x0002; + + if (w & 0x4000) + o |= 0x0004; + if (w & 0x0002) + o |= 0x0008; + + if (w & 0x2000) + o |= 0x0010; + if (w & 0x0004) + o |= 0x0020; + + if (w & 0x1000) + o |= 0x0040; + if (w & 0x0008) + o |= 0x0080; + + if (w & 0x0800) + o |= 0x0100; + if (w & 0x0010) + o |= 0x0200; + + if (w & 0x0400) + o |= 0x0400; + if (w & 0x0020) + o |= 0x0800; + + if (w & 0x0200) + o |= 0x1000; + if (w & 0x0040) + o |= 0x2000; + + if (w & 0x0100) + o |= 0x4000; + if (w & 0x0080) + o |= 0x8000; + + b[0] = o >> 8; + b[1] = o >> 0; + } +} +static void adide_encode (uae_u8 *buffer, int len) +{ + int i; + for (i = 0; i < len; i += 2) { + uae_u8 *b = buffer + i; + uae_u16 w = (b[0] << 8) | (b[1] << 0); + uae_u16 o = 0; + + if (w & 0x0001) + o |= 0x8000; + if (w & 0x0002) + o |= 0x0001; + + if (w & 0x0004) + o |= 0x4000; + if (w & 0x0008) + o |= 0x0002; + + if (w & 0x0010) + o |= 0x2000; + if (w & 0x0020) + o |= 0x0004; + + if (w & 0x0040) + o |= 0x1000; + if (w & 0x0080) + o |= 0x0008; + + if (w & 0x0100) + o |= 0x0800; + if (w & 0x0200) + o |= 0x0010; + + if (w & 0x0400) + o |= 0x0400; + if (w & 0x0800) + o |= 0x0020; + + if (w & 0x1000) + o |= 0x0200; + if (w & 0x2000) + o |= 0x0040; + + if (w & 0x4000) + o |= 0x0100; + if (w & 0x8000) + o |= 0x0080; + + b[0] = o >> 8; + b[1] = o >> 0; + } +} + +static void hdf_byteswap (uae_u8 *b, int len) +{ + int i; + for (i = 0; i < len; i += 2) { + uae_u8 tmp = b[i]; + b[i] = b[i + 1]; + b[i + 1] = tmp; + } +} + +int hdf_read (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) +{ + int v; + + if (!hfd->adide) { + v = hdf_read2 (hfd, buffer, offset, len); + } else { + offset += 512; + v = hdf_read2 (hfd, buffer, offset, len); + adide_decode (buffer, len); + } + if (hfd->byteswap) + hdf_byteswap (buffer, len); + return v; +} + +static int hdf_write2 (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) { if (hfd->vhd_type == VHD_DYNAMIC) return vhd_write (hfd, buffer, offset, len); @@ -713,6 +866,25 @@ int hdf_write (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) return hdf_write_target (hfd, buffer, offset, len); } +int hdf_write (struct hardfiledata *hfd, void *buffer, uae_u64 offset, int len) +{ + int v; + + if (hfd->byteswap) + hdf_byteswap (buffer, len); + if (!hfd->adide) { + v = hdf_write2 (hfd, buffer, offset, len); + } else { + offset += 512; + adide_encode (buffer, len); + v = hdf_write2 (hfd, buffer, offset, len); + adide_decode (buffer, len); + } + if (hfd->byteswap) + hdf_byteswap (buffer, len); + return v; +} + static uae_u64 cmd_readx (struct hardfiledata *hfd, uae_u8 *dataptr, uae_u64 offset, uae_u64 len) { gui_hd_led (hfd->unitnum, 1); diff --git a/include/filesys.h b/include/filesys.h index 6734d585..588b4949 100644 --- a/include/filesys.h +++ b/include/filesys.h @@ -34,6 +34,8 @@ struct hardfiledata { uae_u8 *virtual_rdb; uae_u64 virtual_size; int unitnum; + int byteswap; + int adide; uae_u8 *vhd_header; uae_u32 vhd_bamoffset; diff --git a/include/options.h b/include/options.h index ef1193c8..16ac813a 100644 --- a/include/options.h +++ b/include/options.h @@ -87,6 +87,9 @@ struct uaedev_config_info { enum { CP_GENERIC = 1, CP_CDTV, CP_CD32, CP_A500, CP_A500P, CP_A600, CP_A1000, CP_A1200, CP_A2000, CP_A3000, CP_A3000T, CP_A4000, CP_A4000T }; +#define IDE_A600A1200 1 +#define IDE_A4000 2 + struct uae_prefs { struct strlist *all_lines; diff --git a/memory.c b/memory.c index 3c0d3c3e..6bbb1007 100644 --- a/memory.c +++ b/memory.c @@ -3479,7 +3479,7 @@ void memory_reset (void) if (currprefs.cs_ramseyrev < 0) changed_prefs.cs_ramseyrev = currprefs.cs_ramseyrev = 0x0f; changed_prefs.cs_fatgaryrev = currprefs.cs_fatgaryrev = 0; - if (currprefs.cs_ide != 2) + if (currprefs.cs_ide != IDE_A4000) changed_prefs.cs_ide = currprefs.cs_ide = -1; } } @@ -3516,12 +3516,12 @@ void memory_reset (void) map_banks (&bogomem_bank, 0xC0, t, 0); } if (currprefs.cs_ide || currprefs.cs_pcmcia) { - if (currprefs.cs_ide == 1 || currprefs.cs_pcmcia) { + if (currprefs.cs_ide == IDE_A600A1200 || currprefs.cs_pcmcia) { map_banks (&gayle_bank, 0xD8, 6, 0); map_banks (&gayle2_bank, 0xDD, 2, 0); } gayle_map_pcmcia (); - if (currprefs.cs_ide == 2 || currprefs.cs_mbdmac == 2) + if (currprefs.cs_ide == IDE_A4000 || currprefs.cs_mbdmac == 2) map_banks (&gayle_bank, 0xDD, 1, 0); if (currprefs.cs_ide < 0 && !currprefs.cs_pcmcia) map_banks (&gayle_bank, 0xD8, 6, 0); diff --git a/od-win32/ahidsound.c b/od-win32/ahidsound.c index 45881e13..efac74df 100644 --- a/od-win32/ahidsound.c +++ b/od-win32/ahidsound.c @@ -8,7 +8,8 @@ * Copyright 2000-2002 Bernd Roesch */ -#define NATIVBUFFNUM 4 +#define NATIVEBUFFNUM 4 +#define AMIGASAMPLESIZE 4 #define RECORDBUFFER 50 //survive 9 sec of blocking at 44100 #include "sysconfig.h" @@ -18,10 +19,8 @@ #include #include -#include #include #include -#include #include #include "sysdeps.h" @@ -33,40 +32,42 @@ #include "newcpu.h" #include "traps.h" #include "od-win32/win32.h" -#include "sounddep/sound.h" #include "dxwrap.h" #include "win32.h" #include "parser.h" #include "enforcer.h" #include "ahidsound.h" +#include +#include + +#include + +#include "sounddep/sound.h" + +static struct sound_data sdahi; +static struct sound_data *sdp = &sdahi; + static long samples, playchannel, intcount; static int record_enabled; int ahi_on; -static uae_u8 *sndptrmax; static uae_u8 soundneutral; -static LPSTR lpData,sndptrout; -extern uae_u32 chipmem_mask; -unsigned int *sndbufrecpt; +static unsigned int *sndbufrecpt; static uae_u8 *ahisndbuffer, *sndrecbuffer; -static int ahisndbufsize, *ahisndbufpt, ahitweak;; +static int ahisndbufsize, ahitweak;; +static uae_u8 *ahisndbufpt; +static uae_u8 *sndptrmax; int ahi_pollrate = 40; int sound_freq_ahi, sound_channels_ahi, sound_bits_ahi; -static int vin, devicenum; static int amigablksize; -static DWORD sound_flushes2 = 0; +static DWORD sound_flushes2; extern HWND hAmigaWnd; -static LPDIRECTSOUND lpDS2 = NULL; -static LPDIRECTSOUNDBUFFER lpDSBprimary2 = NULL; -static LPDIRECTSOUNDBUFFER lpDSB2 = NULL; -static LPDIRECTSOUNDNOTIFY lpDSBN2 = NULL; - // for record static LPDIRECTSOUNDCAPTURE lpDS2r = NULL; static LPDIRECTSOUNDCAPTUREBUFFER lpDSBprimary2r = NULL; @@ -149,8 +150,10 @@ void ahi_close_sound (void) return; ahi_on = 0; record_enabled = 0; - ahisndbufpt = (int*)ahisndbuffer; + ahisndbufpt = ahisndbuffer; + close_sound_device (sdp); +#if 0 if (lpDSB2) { hr = IDirectSoundBuffer_Stop (lpDSB2); if(FAILED (hr)) @@ -168,6 +171,7 @@ void ahi_close_sound (void) if (lpDS2) IDirectSound_Release (lpDS2); lpDS2 = NULL; +#endif if (lpDSB2r) IDirectSoundCaptureBuffer_Release (lpDSB2r); @@ -176,11 +180,63 @@ void ahi_close_sound (void) IDirectSound_Release (lpDS2r); lpDS2r = NULL; if (ahisndbuffer) - free (ahisndbuffer); + xfree (ahisndbuffer); ahisndbuffer = NULL; } -void ahi_updatesound(int force) +void ahi_updatesound (int force) +{ + static int doint; + uae_u8 *ptr; + + if (sound_flushes2 == 1) { + intcount = 1; + INTREQ_f (0x8000 | 0x2000); + resume_sound_device (sdp); + } + + if (blocking_sound_device (sdp)) + return; + if (force == 1) { + doint = 1; + } + if (doint) { + INTREQ_f (0x8000 | 0x2000); + intcount += doint; + doint = 0; + } + + ptr = ahisndbuffer; + while (blocking_sound_device (sdp) == 0 && ptr < ahisndbufpt) { + int blocksize = amigablksize * AMIGASAMPLESIZE; + if (currprefs.sound_stereo_swap_ahi) { + int i; + uae_s16 *p = (uae_s16*)ptr; + for (i = 0; i < blocksize / 2; i += 2) { + uae_s16 tmp; + tmp = p[i + 0]; + p[i + 0] = p[i + 1]; + p[i + 1] = tmp; + } + } + send_sound (sdp, (uae_u16*)ptr); + ptr += blocksize; + doint++; + } + if (ptr < ahisndbufpt) { + int diff = ahisndbufpt - ptr; + memmove (ahisndbuffer, ptr, diff); + ahisndbufpt = ahisndbuffer + diff; + sndptrmax = ahisndbuffer + ahisndbufsize - diff; + } else { + ahisndbufpt = ahisndbuffer; + sndptrmax = ahisndbuffer + ahisndbufsize; + } +} + + +#if 0 +void ahi_updatesound (int force) { HRESULT hr; int pos; @@ -255,12 +311,12 @@ void ahi_updatesound(int force) INTREQ_f (0x8000 | 0x2000); } } - +#endif void ahi_finish_sound_buffer (void) { sound_flushes2++; - ahi_updatesound(2); + ahi_updatesound (2); } static WAVEFORMATEX wavfmt; @@ -300,26 +356,49 @@ static int ahi_init_record_win32 (void) return 1; } -void setvolume_ahi (LONG vol) +void setvolume_ahi (int vol) { + set_volume_sound_device (sdp, vol, 0); +#if 0 HRESULT hr; + if (!lpDS2) return; hr = IDirectSoundBuffer_SetVolume (lpDSB2, vol); if (FAILED (hr)) write_log (L"AHI: SetVolume(%d) failed: %s\n", vol, DXError (hr)); +#endif } static int ahi_init_sound_win32 (void) { + int num, ret; +#if 0 HRESULT hr; DSBUFFERDESC sound_buffer; DSCAPS DSCaps; +#endif - if (lpDS2) + ret = 0; + if (!amigablksize) return 0; - enumerate_sound_devices (); + soundneutral = 0; + ahisndbufsize = (amigablksize * AMIGASAMPLESIZE) * NATIVEBUFFNUM; // use 4 native buffer + ahisndbuffer = malloc (ahisndbufsize + 32); + if (!ahisndbuffer) + return 0; + + num = enumerate_sound_devices (); + if (currprefs.win32_soundcard >= num) + currprefs.win32_soundcard = changed_prefs.win32_soundcard = 0; + ret = open_sound_device (sdp, currprefs.win32_soundcard, amigablksize * AMIGASAMPLESIZE, sound_freq_ahi, sound_channels_ahi); + if (!ret) + return 0; + + write_log (L"AHI: Init AHI Sound Rate %d, Channels %d, Bits %d, Buffsize %d\n", + sound_freq_ahi, sound_channels_ahi, sound_bits_ahi, amigablksize); + wavfmt.wFormatTag = WAVE_FORMAT_PCM; wavfmt.nChannels = sound_channels_ahi; wavfmt.nSamplesPerSec = sound_freq_ahi; @@ -328,16 +407,7 @@ static int ahi_init_sound_win32 (void) wavfmt.nAvgBytesPerSec = wavfmt.nBlockAlign * sound_freq_ahi; wavfmt.cbSize = 0; - write_log (L"AHI: Init AHI Sound Rate %d, Channels %d, Bits %d, Buffsize %d\n", - sound_freq_ahi, sound_channels_ahi, sound_bits_ahi, amigablksize); - - if (!amigablksize) - return 0; - soundneutral = 0; - ahisndbufsize = (amigablksize * 4) * NATIVBUFFNUM; // use 4 native buffer - ahisndbuffer = malloc (ahisndbufsize + 32); - if (!ahisndbuffer) - return 0; +#if 0 if (sound_devices[currprefs.win32_soundcard].type != SOUND_DEVICE_DS) hr = DirectSoundCreate (NULL, &lpDS2, NULL); else @@ -381,18 +451,20 @@ static int ahi_init_sound_win32 (void) return 0; } - setvolume_ahi (0); - hr = IDirectSoundBuffer_GetFormat (lpDSBprimary2,&wavfmt,500,0); if (FAILED (hr)) { write_log (L"AHI: GetFormat() failure: %s\n", DXError (hr)); return 0; } +#endif - ahisndbufpt =(int*)ahisndbuffer; + setvolume_ahi (0); + + ahisndbufpt = ahisndbuffer; sndptrmax = ahisndbuffer + ahisndbufsize; - memset (ahisndbuffer, soundneutral, amigablksize * 8); + memset (ahisndbuffer, soundneutral, amigablksize * 8); ahi_on = 1; + intcount = 0; return sound_freq_ahi; } @@ -487,9 +559,19 @@ uae_u32 REGPARAM2 ahi_demux (TrapContext *context) { int i; uaecptr addr = m68k_areg (&context->regs, 0); - for (i = 0; i < amigablksize * 4; i += 4) - *ahisndbufpt++ = get_long (addr + i); - ahi_finish_sound_buffer(); + if (valid_address (addr, amigablksize * AMIGASAMPLESIZE)) { + uae_u8 *src = get_real_address (addr); + for (i = 0; i < amigablksize; i++) { + if (ahisndbufpt >= sndptrmax) + break; + *ahisndbufpt++ = src[1]; + *ahisndbufpt++ = src[0]; + *ahisndbufpt++ = src[3]; + *ahisndbufpt++ = src[2]; + src += 4; + } + } + ahi_finish_sound_buffer (); } return amigablksize; @@ -503,10 +585,10 @@ uae_u32 REGPARAM2 ahi_demux (TrapContext *context) if (!ahi_on) return -2; if (record_enabled == 0) - ahi_init_record_win32(); + ahi_init_record_win32 (); if (record_enabled < 0) return -2; - hr = IDirectSoundCaptureBuffer_GetCurrentPosition(lpDSB2r, &t, &cur_pos); + hr = IDirectSoundCaptureBuffer_GetCurrentPosition (lpDSB2r, &t, &cur_pos); if (FAILED(hr)) return -1; @@ -517,7 +599,7 @@ uae_u32 REGPARAM2 ahi_demux (TrapContext *context) todo = cur_pos + (RECORDBUFFER * t) - cap_pos; if (todo < t) //if no complete buffer ready exit return -1; - hr = IDirectSoundCaptureBuffer_Lock(lpDSB2r, cap_pos, t, &pos1, &byte1, &pos2, &byte2, 0); + hr = IDirectSoundCaptureBuffer_Lock (lpDSB2r, cap_pos, t, &pos1, &byte1, &pos2, &byte2, 0); if (FAILED(hr)) return -1; if ((cap_pos + t) < (t * RECORDBUFFER)) @@ -532,7 +614,7 @@ uae_u32 REGPARAM2 ahi_demux (TrapContext *context) addr += 4; } t *= 4; - IDirectSoundCaptureBuffer_Unlock(lpDSB2r, pos1, byte1, pos2, byte2); + IDirectSoundCaptureBuffer_Unlock (lpDSB2r, pos1, byte1, pos2, byte2); return (todo - t) / t; } @@ -549,7 +631,7 @@ uae_u32 REGPARAM2 ahi_demux (TrapContext *context) case 5: if (!ahi_on) return 0; - ahi_updatesound ( 1 ); + ahi_updatesound (1); return 1; case 10: diff --git a/od-win32/bsdsock.c b/od-win32/bsdsock.c index e01e6a56..243f6802 100644 --- a/od-win32/bsdsock.c +++ b/od-win32/bsdsock.c @@ -538,10 +538,10 @@ static void prephostaddr(SOCKADDR_IN *addr) static void prepamigaaddr(struct sockaddr *realpt, int len) { // little endian address family value to the byte sin_family member - ((TCHAR *)realpt)[1] = *((TCHAR *)realpt); + ((uae_u8*)realpt)[1] = *((uae_u8*)realpt); // set size of address - *((TCHAR *)realpt) = len; + *((uae_u8*)realpt) = len; } @@ -618,7 +618,7 @@ int host_socket(SB, int af, int type, int protocol) uae_u32 host_bind(SB, uae_u32 sd, uae_u32 name, uae_u32 namelen) { - TCHAR buf[MAXADDRLEN]; + uae_char buf[MAXADDRLEN]; uae_u32 success = 0; SOCKET s; diff --git a/od-win32/direct3d.c b/od-win32/direct3d.c index ec1da086..2983f83b 100644 --- a/od-win32/direct3d.c +++ b/od-win32/direct3d.c @@ -970,6 +970,7 @@ static int restoredeviceobjects (void) void D3D_free (void) { + D3D_clear (); invalidatedeviceobjects (); if (d3ddev) { IDirect3DDevice9_Release (d3ddev); @@ -1196,6 +1197,9 @@ void D3D_clear (void) { int i; HRESULT hr; + + if (!d3ddev) + return; hr = IDirect3DDevice9_TestCooperativeLevel (d3ddev); if (FAILED (hr)) return; diff --git a/od-win32/dxwrap.c b/od-win32/dxwrap.c index 032597d6..25efd1ec 100644 --- a/od-win32/dxwrap.c +++ b/od-win32/dxwrap.c @@ -335,7 +335,7 @@ static void createcursorsurface (void) releaser (dxdata.statussurface, IDirectDrawSurface7_Release); dxdata.cursorsurface1 = allocsurface_2 (dxcaps.cursorwidth, dxcaps.cursorheight, TRUE); dxdata.cursorsurface2 = allocsurface_2 (dxcaps.cursorwidth, dxcaps.cursorheight, FALSE); -// dxdata.statussurface = allocsurface_2 (dxdata.statuswidth, dxdata.statusheight, FALSE); + dxdata.statussurface = allocsurface_2 (dxdata.statuswidth, dxdata.statusheight, FALSE); if (dxdata.cursorsurface1) clearsurf (dxdata.cursorsurface1, 0); if (dxdata.cursorsurface2) @@ -742,6 +742,10 @@ int DirectDraw_BlitToPrimaryScale (RECT *dstrect, RECT *srcrect) return 0; } else if (ddrval != DDERR_SURFACEBUSY) { write_log (L"DirectDraw_BlitToPrimary: %s\n", DXError (ddrval)); + if (srcrect) + write_log (L"SRC=%dx%d %dx%d\n", srcrect->left, srcrect->top, srcrect->right, srcrect->bottom); + if (srcrect) + write_log (L"DST=%dx%d %dx%d\n", dstrect->left, dstrect->top, dstrect->right, dstrect->bottom); break; } } @@ -1164,8 +1168,8 @@ int DirectDraw_Start (GUID *guid) } #endif -// dxdata.statuswidth = 800; -// dxdata.statusheight = TD_TOTAL_HEIGHT; + dxdata.statuswidth = 800; + dxdata.statusheight = TD_TOTAL_HEIGHT; dxcaps.cursorwidth = 48; dxcaps.cursorheight = 48; if (!d3ddone) { diff --git a/od-win32/hardfile_win32.c b/od-win32/hardfile_win32.c index 47bea70f..57a5953e 100644 --- a/od-win32/hardfile_win32.c +++ b/od-win32/hardfile_win32.c @@ -109,7 +109,7 @@ static int safetycheck (HANDLE *h, uae_u64 offset, uae_u8 *buf, int blocksize) for (j = 0; j < blocks; j++) { high = (DWORD)(offset >> 32); if (SetFilePointer (h, (DWORD)offset, &high, FILE_BEGIN) == INVALID_FILE_SIZE) { - write_log (L"hd ignored, SetFilePointer failed, error %d\n", GetLastError()); + write_log (L"hd ignored, SetFilePointer failed, error %d\n", GetLastError ()); return 1; } memset (buf, 0xaa, blocksize); @@ -118,6 +118,13 @@ static int safetycheck (HANDLE *h, uae_u64 offset, uae_u8 *buf, int blocksize) write_log (L"hd ignored, read error %d!\n", GetLastError()); return 2; } + if (j == 0 && buf[0] == 0x39 && buf[1] == 0x10 && buf[2] == 0xd3 && buf[3] == 0x12) { + // ADIDE "CPRM" hidden block.. + if (do_rdbdump) + rdbdump (h, offset, buf, blocksize); + write_log (L"hd accepted (adide rdb detected at block %d)\n", j); + return -3; + } if (!memcmp (buf, "RDSK", 4)) { if (do_rdbdump) rdbdump (h, offset, buf, blocksize); @@ -1198,6 +1205,9 @@ TCHAR *hdf_getnameharddrive (int index, int flags, int *sectorsize) case -9: dang = L"Empty"; break; + case -3: + dang = L"CPRM"; + break; case -2: dang = L"SRAM"; break; diff --git a/od-win32/picasso96_win.c b/od-win32/picasso96_win.c index 8593ed2e..0eb34cef 100644 --- a/od-win32/picasso96_win.c +++ b/od-win32/picasso96_win.c @@ -914,7 +914,8 @@ void picasso_refresh (void) setconvert (); /* Make sure that the first time we show a Picasso video mode, we don't blit any crap. - * We can do this by checking if we have an Address yet. */ + * We can do this by checking if we have an Address yet. + */ if (picasso96_state.Address) { unsigned int width, height; @@ -4100,6 +4101,7 @@ static void flushpixels (void) } if (dst == NULL) break; + dst += picasso_vidinfo.offset; if (doskip () && p96skipmode == 2) break; diff --git a/od-win32/picasso96_win.h b/od-win32/picasso96_win.h index 6eec673d..308c8431 100644 --- a/od-win32/picasso96_win.h +++ b/od-win32/picasso96_win.h @@ -565,7 +565,7 @@ extern int picasso_setwincursor (void); * screen. */ struct picasso_vidbuf_description { int width, height, depth; - int rowbytes, pixbytes; + int rowbytes, pixbytes, offset; int extra_mem; /* nonzero if there's a second buffer that must be updated */ uae_u32 rgbformat; uae_u32 selected_rgbformat; diff --git a/od-win32/resources/resource b/od-win32/resources/resource index a8f4d5d1..3ccc5557 100644 --- a/od-win32/resources/resource +++ b/od-win32/resources/resource @@ -255,6 +255,7 @@ #define IDS_SOUND_51 260 #define IDS_AUTOMATIC 261 #define IDI_GAMEPORTS 262 +#define IDS_ALL 262 #define IDD_GAMEPORTS 263 #define IDS_NUMSG_NEEDEXT2 300 #define IDS_NUMSG_NOROMKEY 301 @@ -349,7 +350,6 @@ #define IDC_PORT1_JOYSMODE 1030 #define IDC_MBMEM2 1031 #define IDC_PORT2_JOYS 1031 -#define IDC_PORT4_JOYS 1032 #define IDC_PORT3_JOYS 1032 #define IDC_PARALLEL 1033 #define IDC_JULIAN 1040 diff --git a/od-win32/resources/winuae.rc b/od-win32/resources/winuae.rc index ef57b00d..49996325 100644 --- a/od-win32/resources/winuae.rc +++ b/od-win32/resources/winuae.rc @@ -1257,6 +1257,7 @@ BEGIN IDS_SOUND_CLONED51 "Cloned Stereo (5.1)" IDS_SOUND_51 "5.1 Channels" IDS_AUTOMATIC "Automatic" + IDS_ALL "All" END STRINGTABLE diff --git a/od-win32/sounddep/sound.c b/od-win32/sounddep/sound.c index cfb26c12..fedb61a3 100644 --- a/od-win32/sounddep/sound.c +++ b/od-win32/sounddep/sound.c @@ -18,7 +18,6 @@ #include "events.h" #include "custom.h" #include "gensound.h" -#include "sounddep/sound.h" #include "threaddep/thread.h" #include "avioutput.h" #include "gui.h" @@ -39,40 +38,10 @@ #include -#include - -#define ADJUST_SIZE 30 -#define EXP 2.1 - -#define ADJUST_VSSIZE 15 -#define EXPVS 1.7 - -int sound_debug = 0; -int sound_mode_skip = 0; - -static int have_sound; - -#define SND_MAX_BUFFER2 524288 -#define SND_MAX_BUFFER 8192 - -uae_u16 sndbuffer[SND_MAX_BUFFER]; -uae_u16 *sndbufpt; -int sndbufsize; - -static uae_sem_t sound_sem, sound_init_sem; - -struct sound_device sound_devices[MAX_SOUND_DEVICES]; -struct sound_device record_devices[MAX_SOUND_DEVICES]; -static int num_sound_devices, num_record_devices; +#include "sounddep/sound.h" -struct sound_data +struct sound_dp { - int waiting_for_buffer; - int devicetype; - int obtainedfreq; - int paused; - int mute; - // directsound LPDIRECTSOUND8 lpDS; @@ -86,7 +55,6 @@ struct sound_data int snd_totalmaxoffset_of; int max_sndbufsize; int snd_configsize; - int samplesize; // openal @@ -111,9 +79,33 @@ struct sound_data PaStream *pastream; HANDLE paevent; int opacounter; +}; +#include -}; +#define ADJUST_SIZE 30 +#define EXP 2.1 + +#define ADJUST_VSSIZE 15 +#define EXPVS 1.7 + +int sound_debug = 0; +int sound_mode_skip = 0; + +static int have_sound; + +#define SND_MAX_BUFFER2 524288 +#define SND_MAX_BUFFER 8192 + +uae_u16 paula_sndbuffer[SND_MAX_BUFFER]; +uae_u16 *paula_sndbufpt; +int paula_sndbufsize; + +static uae_sem_t sound_sem, sound_init_sem; + +struct sound_device sound_devices[MAX_SOUND_DEVICES]; +struct sound_device record_devices[MAX_SOUND_DEVICES]; +static int num_sound_devices, num_record_devices; static struct sound_data sdpaula; static struct sound_data *sdp = &sdpaula; @@ -154,37 +146,39 @@ static void clearbuffer_ds (struct sound_data *sd) { void *buffer; DWORD size; + struct sound_dp *s = sd->data; - HRESULT hr = IDirectSoundBuffer_Lock (sd->lpDSBsecondary, 0, sd->dsoundbuf, &buffer, &size, NULL, NULL, 0); + HRESULT hr = IDirectSoundBuffer_Lock (s->lpDSBsecondary, 0, s->dsoundbuf, &buffer, &size, NULL, NULL, 0); if (hr == DSERR_BUFFERLOST) { - IDirectSoundBuffer_Restore (sd->lpDSBsecondary); - hr = IDirectSoundBuffer_Lock (sd->lpDSBsecondary, 0, sd->dsoundbuf, &buffer, &size, NULL, NULL, 0); + IDirectSoundBuffer_Restore (s->lpDSBsecondary); + hr = IDirectSoundBuffer_Lock (s->lpDSBsecondary, 0, s->dsoundbuf, &buffer, &size, NULL, NULL, 0); } if (FAILED (hr)) { - write_log (L"SOUND: failed to Lock sound buffer (clear): %s\n", DXError (hr)); + write_log (L"DSSOUND: failed to Lock sound buffer (clear): %s\n", DXError (hr)); return; } memset (buffer, 0, size); - IDirectSoundBuffer_Unlock (sd->lpDSBsecondary, buffer, size, NULL, 0); + IDirectSoundBuffer_Unlock (s->lpDSBsecondary, buffer, size, NULL, 0); } static void clearbuffer (struct sound_data *sd) { - if (sdp->devicetype == SOUND_DEVICE_DS) - clearbuffer_ds (sdp); + if (sd->devicetype == SOUND_DEVICE_DS) + clearbuffer_ds (sd); } static void pause_audio_ds (struct sound_data *sd) { + struct sound_dp *s = sd->data; HRESULT hr; sd->waiting_for_buffer = 0; - hr = IDirectSoundBuffer_Stop (sd->lpDSBsecondary); + hr = IDirectSoundBuffer_Stop (s->lpDSBsecondary); if (FAILED (hr)) - write_log (L"SOUND: DirectSoundBuffer_Stop failed, %s\n", DXError (hr)); - hr = IDirectSoundBuffer_SetCurrentPosition (sd->lpDSBsecondary, 0); + write_log (L"DSSOUND: DirectSoundBuffer_Stop failed, %s\n", DXError (hr)); + hr = IDirectSoundBuffer_SetCurrentPosition (s->lpDSBsecondary, 0); if (FAILED (hr)) - write_log (L"SOUND: DirectSoundBuffer_SetCurretPosition failed, %s\n", DXError (hr)); + write_log (L"DSSOUND: DirectSoundBuffer_SetCurretPosition failed, %s\n", DXError (hr)); clearbuffer (sd); } static void resume_audio_ds (struct sound_data *sd) @@ -195,37 +189,42 @@ static void resume_audio_ds (struct sound_data *sd) } static void pause_audio_pa (struct sound_data *sd) { - PaError err = Pa_StopStream (sd->pastream); + struct sound_dp *s = sd->data; + PaError err = Pa_StopStream (s->pastream); if (err != paNoError) - write_log (L"SOUND: Pa_StopStream() error %d (%s)\n", err, Pa_GetErrorText (err)); + write_log (L"PASOUND: Pa_StopStream() error %d (%s)\n", err, Pa_GetErrorText (err)); } static void resume_audio_pa (struct sound_data *sd) { - PaError err = Pa_StartStream (sd->pastream); + struct sound_dp *s = sd->data; + PaError err = Pa_StartStream (s->pastream); if (err != paNoError) - write_log (L"SOUND: Pa_StartStream() error %d (%s)\n", err, Pa_GetErrorText (err)); + write_log (L"PASOUND: Pa_StartStream() error %d (%s)\n", err, Pa_GetErrorText (err)); sd->paused = 0; } static void pause_audio_al (struct sound_data *sd) { + struct sound_dp *s = sd->data; sd->waiting_for_buffer = 0; - alSourcePause (sd->al_Source); + alSourcePause (s->al_Source); } static void resume_audio_al (struct sound_data *sd) { + struct sound_dp *s = sd->data; sd->waiting_for_buffer = 1; - sd->al_offset = 0; + s->al_offset = 0; } static int restore_ds (struct sound_data *sd, DWORD hr) { + struct sound_dp *s = sd->data; if (hr != DSERR_BUFFERLOST) return 0; if (sound_debug) - write_log (L"SOUND: sound buffer lost\n"); - hr = IDirectSoundBuffer_Restore (sd->lpDSBsecondary); + write_log (L"DSSOUND: sound buffer lost\n"); + hr = IDirectSoundBuffer_Restore (s->lpDSBsecondary); if (FAILED (hr)) { - write_log (L"SOUND: restore failed %s\n", DXError (hr)); + write_log (L"DSSOUND: restore failed %s\n", DXError (hr)); return 1; } pause_audio_ds (sd); @@ -247,49 +246,57 @@ static double getqpf (void) static void close_audio_ds (struct sound_data *sd) { - if (sd->lpDSBsecondary) - IDirectSound_Release (sd->lpDSBsecondary); - sd->lpDSBsecondary = 0; + struct sound_dp *s = sd->data; + if (s->lpDSBsecondary) + IDirectSound_Release (s->lpDSBsecondary); + s->lpDSBsecondary = 0; #ifdef USE_PRIMARY_BUFFER - if (sd->lpDSBprimary) - IDirectSound_Release (sd->lpDSBprimary); - sd->lpDSBprimary = 0; + if (s->lpDSBprimary) + IDirectSound_Release (s->lpDSBprimary); + s->lpDSBprimary = 0; #endif - if (sd->lpDS) { - IDirectSound_Release (sd->lpDS); - write_log (L"SOUND: DirectSound driver freed\n"); + if (s->lpDS) { + IDirectSound_Release (s->lpDS); + write_log (L"DSSOUND: DirectSound driver freed\n"); } - sd->lpDS = 0; + s->lpDS = 0; } extern HWND hMainWnd; extern void setvolume_ahi (LONG); -void set_volume (int volume, int mute) + +void set_volume_sound_device (struct sound_data *sd, int volume, int mute) { - struct sound_data *sd = sdp; + struct sound_dp *s = sd->data; if (sd->devicetype == SOUND_DEVICE_AL) { float vol = 0.0; if (volume < 100 && !mute) vol = (100 - volume) / 100.0; - alSourcef (sd->al_Source, AL_GAIN, vol); + alSourcef (s->al_Source, AL_GAIN, vol); } else if (sd->devicetype == SOUND_DEVICE_DS) { HRESULT hr; LONG vol = DSBVOLUME_MIN; if (volume < 100 && !mute) vol = (LONG)((DSBVOLUME_MIN / 2) + (-DSBVOLUME_MIN / 2) * log (1 + (2.718281828 - 1) * (1 - volume / 100.0))); - hr = IDirectSoundBuffer_SetVolume (sd->lpDSBsecondary, vol); + hr = IDirectSoundBuffer_SetVolume (s->lpDSBsecondary, vol); if (FAILED (hr)) - write_log (L"SOUND: SetVolume(%d) failed: %s\n", vol, DXError (hr)); - setvolume_ahi (vol); + write_log (L"DSSOUND: SetVolume(%d) failed: %s\n", vol, DXError (hr)); } } +void set_volume (int volume, int mute) +{ + set_volume_sound_device (sdp, volume, mute); + setvolume_ahi (volume); +} + static void recalc_offsets (struct sound_data *sd) { - sd->snd_writeoffset = sd->max_sndbufsize * 5 / 8; - sd->snd_maxoffset = sd->max_sndbufsize; - sd->snd_totalmaxoffset_of = sd->max_sndbufsize + (sd->dsoundbuf - sd->max_sndbufsize) * 3 / 9; - sd->snd_totalmaxoffset_uf = sd->max_sndbufsize + (sd->dsoundbuf - sd->max_sndbufsize) * 7 / 9; + struct sound_dp *s = sd->data; + s->snd_writeoffset = s->max_sndbufsize * 5 / 8; + s->snd_maxoffset = s->max_sndbufsize; + s->snd_totalmaxoffset_of = s->max_sndbufsize + (s->dsoundbuf - s->max_sndbufsize) * 3 / 9; + s->snd_totalmaxoffset_uf = s->max_sndbufsize + (s->dsoundbuf - s->max_sndbufsize) * 7 / 9; } const static GUID KSDATAFORMAT_SUBTYPE_PCM = {0x00000001,0x0000,0x0010, @@ -308,6 +315,7 @@ DWORD fillsupportedmodes (LPDIRECTSOUND8 lpDS, int freq, struct dsaudiomodes *ds HRESULT hr; int ch, round, mode, skip; DWORD rn[4]; + struct sound_dp *s = sdp->data; mode = 2; dsam[0].ch = 1; @@ -347,7 +355,7 @@ DWORD fillsupportedmodes (LPDIRECTSOUND8 lpDS, int freq, struct dsaudiomodes *ds wavfmt.dwChannelMask = rn[round]; memset (&sound_buffer, 0, sizeof (sound_buffer)); sound_buffer.dwSize = sizeof (sound_buffer); - sound_buffer.dwBufferBytes = sdp->dsoundbuf; + sound_buffer.dwBufferBytes = s->dsoundbuf; sound_buffer.lpwfxFormat = &wavfmt.Format; sound_buffer.dwFlags = DSBCAPS_GETCURRENTPOSITION2 | DSBCAPS_GLOBALFOCUS; sound_buffer.dwFlags |= DSBCAPS_CTRLVOLUME; @@ -365,13 +373,14 @@ DWORD fillsupportedmodes (LPDIRECTSOUND8 lpDS, int freq, struct dsaudiomodes *ds } -static void finish_sound_buffer_pa (struct sound_data *sd) +static void finish_sound_buffer_pa (struct sound_data *sd, uae_u16 *sndbuffer) { - while (sd->opacounter == sd->pacounter && sd->pastream && !sd->paused) - WaitForSingleObject (sd->paevent, 10); - ResetEvent (sd->paevent); - sd->opacounter = sd->pacounter; - memcpy (sd->pasoundbuffer[sd->patoggle], sndbuffer, sndbufsize); + struct sound_dp *s = sd->data; + while (s->opacounter == s->pacounter && s->pastream && !sd->paused) + WaitForSingleObject (s->paevent, 10); + ResetEvent (s->paevent); + s->opacounter = s->pacounter; + memcpy (s->pasoundbuffer[s->patoggle], sndbuffer, sd->sndbufsize); } static int portAudioCallback (const void *inputBuffer, void *outputBuffer, @@ -381,49 +390,54 @@ static int portAudioCallback (const void *inputBuffer, void *outputBuffer, void *userData) { struct sound_data *sd = userData; + struct sound_dp *s = sd->data; - if (framesPerBuffer != sndbufsize / (get_audio_nativechannels () * 2)) { - write_log (L"%d <> %d\n", framesPerBuffer, sndbufsize / (get_audio_nativechannels () * 2)); + if (framesPerBuffer != sd->sndbufsize / (sd->channels * 2)) { + write_log (L"%d <> %d\n", framesPerBuffer, sd->sndbufsize / (sd->channels * 2)); } else { - memcpy (outputBuffer, sd->pasoundbuffer[sd->patoggle], sndbufsize); + memcpy (outputBuffer, s->pasoundbuffer[s->patoggle], sd->sndbufsize); } - sd->patoggle ^= 1; - sd->pacounter++; - SetEvent (sd->paevent); + s->patoggle ^= 1; + s->pacounter++; + SetEvent (s->paevent); return paContinue; } static void close_audio_pa (struct sound_data *sd) { + struct sound_dp *s = sd->data; int i; - if (sd->pastream) - Pa_CloseStream (sd->pastream); - sd->pastream = NULL; + if (s->pastream) + Pa_CloseStream (s->pastream); + s->pastream = NULL; for (i = 0; i < 2; i++) { - xfree (sd->pasoundbuffer[i]); - sd->pasoundbuffer[i] = NULL; + xfree (s->pasoundbuffer[i]); + s->pasoundbuffer[i] = NULL; } - if (sd->paevent) { - SetEvent (sd->paevent); - CloseHandle (sd->paevent); + if (s->paevent) { + SetEvent (s->paevent); + CloseHandle (s->paevent); } - sd->paevent = NULL; + s->paevent = NULL; } -static int open_audio_pa (struct sound_data *sd, int size) +static int open_audio_pa (struct sound_data *sd, int index) { + struct sound_dp *s = sd->data; int i; - int freq = currprefs.sound_freq; - int ch = get_audio_nativechannels (); - int dev = sound_devices[currprefs.win32_soundcard].panum; + int freq = sd->freq; + int ch = sd->channels; + int size; + int dev = sound_devices[index].panum; const PaDeviceInfo *di; PaStreamParameters p; PaError err; - sd->paframesperbuffer = size; - sndbufsize = size * ch * 2; - sdp->devicetype = SOUND_DEVICE_PA; + size = sd->sndbufsize; + s->paframesperbuffer = size; + sd->sndbufsize = size * ch * 2; + sd->devicetype = SOUND_DEVICE_PA; memset (&p, 0, sizeof p); p.channelCount = ch; p.device = dev; @@ -440,7 +454,7 @@ static int open_audio_pa (struct sound_data *sd, int size) freq = 48000; err = Pa_IsFormatSupported (NULL, &p, freq); if (err == paFormatIsSupported) { - currprefs.sound_freq = changed_prefs.sound_freq = freq; + sd->freq = freq; break; } } @@ -448,96 +462,100 @@ static int open_audio_pa (struct sound_data *sd, int size) freq = di->defaultSampleRate; err = Pa_IsFormatSupported (NULL, &p, freq); if (err == paFormatIsSupported) { - currprefs.sound_freq = changed_prefs.sound_freq = freq; + sd->freq = freq; break; } } - write_log (L"SOUND: sound format not supported\n"); + write_log (L"PASOUND: sound format not supported\n"); goto end; } - err = Pa_OpenStream (&sd->pastream, NULL, &p, freq, sd->paframesperbuffer, paNoFlag, portAudioCallback, sd); + err = Pa_OpenStream (&s->pastream, NULL, &p, freq, s->paframesperbuffer, paNoFlag, portAudioCallback, sd); if (err != paNoError) { - write_log (L"SOUND: Pa_OpenStream() error %d (%s)\n", err, Pa_GetErrorText (err)); + write_log (L"PASOUND: Pa_OpenStream() error %d (%s)\n", err, Pa_GetErrorText (err)); goto end; } - sd->paevent = CreateEvent (NULL, FALSE, FALSE, NULL); + s->paevent = CreateEvent (NULL, FALSE, FALSE, NULL); for (i = 0; i < 2; i++) - sd->pasoundbuffer[i] = xcalloc (sndbufsize, 1); + s->pasoundbuffer[i] = xcalloc (sd->sndbufsize, 1); return 1; end: - sd->pastream = NULL; + s->pastream = NULL; close_audio_pa (sd); return 0; } static void close_audio_al (struct sound_data *sd) { + struct sound_dp *s = sd->data; int i; - alDeleteSources (1, &sd->al_Source); - sd->al_Source = 0; - alDeleteBuffers (AL_BUFFERS, sd->al_Buffers); + alDeleteSources (1, &s->al_Source); + s->al_Source = 0; + alDeleteBuffers (AL_BUFFERS, s->al_Buffers); alcMakeContextCurrent (NULL); - if (sd->al_ctx) - alcDestroyContext (sd->al_ctx); - sd->al_ctx = NULL; - if (sd->al_dev) - alcCloseDevice (sd->al_dev); - sd->al_dev = NULL; + if (s->al_ctx) + alcDestroyContext (s->al_ctx); + s->al_ctx = NULL; + if (s->al_dev) + alcCloseDevice (s->al_dev); + s->al_dev = NULL; for (i = 0; i < AL_BUFFERS; i++) { - sd->al_Buffers[i] = 0; + s->al_Buffers[i] = 0; } - xfree (sd->al_bigbuffer); - sd->al_bigbuffer = NULL; + xfree (s->al_bigbuffer); + s->al_bigbuffer = NULL; } -static int open_audio_al (struct sound_data *sd, int size) +static int open_audio_al (struct sound_data *sd, int index) { - int freq = currprefs.sound_freq; - int ch = get_audio_nativechannels (); + struct sound_dp *s = sd->data; + int freq = sd->freq; + int ch = sd->channels; char *name; + int size; + size = sd->sndbufsize; sd->devicetype = SOUND_DEVICE_AL; size *= ch * 2; - sndbufsize = size / 8; - if (sndbufsize > SND_MAX_BUFFER) - sndbufsize = SND_MAX_BUFFER; - sd->al_bufsize = size; - sd->al_bigbuffer = xcalloc (sd->al_bufsize, 1); - name = ua (sound_devices[currprefs.win32_soundcard].alname); - sd->al_dev = alcOpenDevice (name); + sd->sndbufsize = size / 8; + if (sd->sndbufsize > SND_MAX_BUFFER) + sd->sndbufsize = SND_MAX_BUFFER; + s->al_bufsize = size; + s->al_bigbuffer = xcalloc (s->al_bufsize, 1); + name = ua (sound_devices[index].alname); + s->al_dev = alcOpenDevice (name); xfree (name); - if (!sd->al_dev) + if (!s->al_dev) goto error; - sd->al_ctx = alcCreateContext (sd->al_dev, NULL); - if (!sd->al_ctx) + s->al_ctx = alcCreateContext (s->al_dev, NULL); + if (!s->al_ctx) goto error; - alcMakeContextCurrent (sd->al_ctx); - alGenBuffers (AL_BUFFERS, sd->al_Buffers); - alGenSources (1, &sd->al_Source); - sd->al_toggle = 0; - sd->al_format = 0; + alcMakeContextCurrent (s->al_ctx); + alGenBuffers (AL_BUFFERS, s->al_Buffers); + alGenSources (1, &s->al_Source); + s->al_toggle = 0; + s->al_format = 0; switch (ch) { case 1: - sd->al_format = AL_FORMAT_MONO16; + s->al_format = AL_FORMAT_MONO16; break; case 2: - sd->al_format = AL_FORMAT_STEREO16; + s->al_format = AL_FORMAT_STEREO16; break; case 4: - sd->al_format = alGetEnumValue ("AL_FORMAT_QUAD16"); + s->al_format = alGetEnumValue ("AL_FORMAT_QUAD16"); break; case 6: - sd->al_format = alGetEnumValue ("AL_FORMAT_51CHN16"); + s->al_format = alGetEnumValue ("AL_FORMAT_51CHN16"); break; } - if (sd->al_format == 0) + if (s->al_format == 0) goto error; - write_log (L"SOUND: %08X,CH=%d,FREQ=%d '%s' buffer %d (%d)\n", - sd->al_format, ch, freq, sound_devices[currprefs.win32_soundcard].alname, - sndbufsize, sd->al_bufsize); + write_log (L"ALSOUND: %08X,CH=%d,FREQ=%d '%s' buffer %d (%d)\n", + s->al_format, ch, freq, sound_devices[index].alname, + sd->sndbufsize, s->al_bufsize); return 1; error: @@ -545,61 +563,63 @@ error: return 0; } -static int open_audio_ds (struct sound_data *sd, int size) +static int open_audio_ds (struct sound_data *sd, int index) { + struct sound_dp *s = sd->data; HRESULT hr; DSBUFFERDESC sound_buffer; DSCAPS DSCaps; WAVEFORMATEXTENSIBLE wavfmt; LPDIRECTSOUNDBUFFER pdsb; - int freq = currprefs.sound_freq; - int ch = get_audio_nativechannels (); + int freq = sd->freq; + int ch = sd->channels; int round, i; DWORD speakerconfig; + int size; sd->devicetype = SOUND_DEVICE_DS; - size *= ch * 2; - sd->snd_configsize = size; - sndbufsize = size / 32; - if (sndbufsize > SND_MAX_BUFFER) - sndbufsize = SND_MAX_BUFFER; + size = sd->sndbufsize * ch * 2; + s->snd_configsize = size; + sd->sndbufsize = size / 32; + if (sd->sndbufsize > SND_MAX_BUFFER) + sd->sndbufsize = SND_MAX_BUFFER; - sd->max_sndbufsize = size * 4; - if (sd->max_sndbufsize > SND_MAX_BUFFER2) - sd->max_sndbufsize = SND_MAX_BUFFER2; - sd->dsoundbuf = sd->max_sndbufsize * 2; + s->max_sndbufsize = size * 4; + if (s->max_sndbufsize > SND_MAX_BUFFER2) + s->max_sndbufsize = SND_MAX_BUFFER2; + s->dsoundbuf = s->max_sndbufsize * 2; - if (sd->dsoundbuf < DSBSIZE_MIN) - sd->dsoundbuf = DSBSIZE_MIN; - if (sd->dsoundbuf > DSBSIZE_MAX) - sd->dsoundbuf = DSBSIZE_MAX; + if (s->dsoundbuf < DSBSIZE_MIN) + s->dsoundbuf = DSBSIZE_MIN; + if (s->dsoundbuf > DSBSIZE_MAX) + s->dsoundbuf = DSBSIZE_MAX; - if (sd->max_sndbufsize * 2 > sd->dsoundbuf) - sd->max_sndbufsize = sd->dsoundbuf / 2; + if (s->max_sndbufsize * 2 > s->dsoundbuf) + s->max_sndbufsize = s->dsoundbuf / 2; recalc_offsets (sd); - hr = DirectSoundCreate8 (&sound_devices[currprefs.win32_soundcard].guid, &sd->lpDS, NULL); + hr = DirectSoundCreate8 (&sound_devices[index].guid, &s->lpDS, NULL); if (FAILED (hr)) { - write_log (L"SOUND: DirectSoundCreate8() failure: %s\n", DXError (hr)); + write_log (L"DSSOUND: DirectSoundCreate8() failure: %s\n", DXError (hr)); return 0; } - hr = IDirectSound_SetCooperativeLevel (sd->lpDS, hMainWnd, DSSCL_PRIORITY); + hr = IDirectSound_SetCooperativeLevel (s->lpDS, hMainWnd, DSSCL_PRIORITY); if (FAILED (hr)) { - write_log (L"SOUND: Can't set cooperativelevel: %s\n", DXError (hr)); + write_log (L"DSSOUND: Can't set cooperativelevel: %s\n", DXError (hr)); goto error; } memset (&DSCaps, 0, sizeof (DSCaps)); DSCaps.dwSize = sizeof (DSCaps); - hr = IDirectSound_GetCaps (sd->lpDS, &DSCaps); + hr = IDirectSound_GetCaps (s->lpDS, &DSCaps); if (FAILED(hr)) { - write_log (L"SOUND: Error getting DirectSound capabilities: %s\n", DXError (hr)); + write_log (L"DSSOUND: Error getting DirectSound capabilities: %s\n", DXError (hr)); goto error; } if (DSCaps.dwFlags & DSCAPS_EMULDRIVER) { - write_log (L"SOUND: Emulated DirectSound driver detected, don't complain if sound quality is crap :)\n"); + write_log (L"DSSOUND: Emulated DirectSound driver detected, don't complain if sound quality is crap :)\n"); } if (DSCaps.dwFlags & DSCAPS_CONTINUOUSRATE) { int minfreq = DSCaps.dwMinSecondarySampleRate; @@ -607,17 +627,17 @@ static int open_audio_ds (struct sound_data *sd, int size) if (minfreq > freq && freq < 22050) { freq = minfreq; changed_prefs.sound_freq = currprefs.sound_freq = freq; - write_log (L"SOUND: minimum supported frequency: %d\n", minfreq); + write_log (L"DSSOUND: minimum supported frequency: %d\n", minfreq); } if (maxfreq < freq && freq > 44100) { freq = maxfreq; changed_prefs.sound_freq = currprefs.sound_freq = freq; - write_log (L"SOUND: maximum supported frequency: %d\n", maxfreq); + write_log (L"DSSOUND: maximum supported frequency: %d\n", maxfreq); } } - speakerconfig = fillsupportedmodes (sd->lpDS, freq, supportedmodes); - write_log (L"SOUND: %08X ", speakerconfig); + speakerconfig = fillsupportedmodes (s->lpDS, freq, supportedmodes); + write_log (L"DSSOUND: %08X ", speakerconfig); for (i = 0; supportedmodes[i].ch; i++) write_log (L"%d:%08X ", supportedmodes[i].ch, supportedmodes[i].ksmode); write_log (L"\n"); @@ -646,40 +666,39 @@ static int open_audio_ds (struct sound_data *sd, int size) wavfmt.Format.nBlockAlign = wavfmt.Format.wBitsPerSample / 8 * wavfmt.Format.nChannels; wavfmt.Format.nAvgBytesPerSec = wavfmt.Format.nBlockAlign * wavfmt.Format.nSamplesPerSec; - sd->samplesize = ch * 2; - write_log (L"SOUND: %08X,CH=%d,FREQ=%d '%s' buffer %d (%d), dist %d\n", - ksmode, ch, freq, sound_devices[currprefs.win32_soundcard].name, - sd->max_sndbufsize / sd->samplesize, sd->max_sndbufsize, sd->snd_configsize / sd->samplesize); + write_log (L"DSSOUND: %08X,CH=%d,FREQ=%d '%s' buffer %d (%d), dist %d\n", + ksmode, ch, freq, sound_devices[index].name, + s->max_sndbufsize / sd->samplesize, s->max_sndbufsize, s->snd_configsize / sd->samplesize); memset (&sound_buffer, 0, sizeof (sound_buffer)); sound_buffer.dwSize = sizeof (sound_buffer); - sound_buffer.dwBufferBytes = sd->dsoundbuf; + sound_buffer.dwBufferBytes = s->dsoundbuf; sound_buffer.lpwfxFormat = &wavfmt.Format; sound_buffer.dwFlags = DSBCAPS_GETCURRENTPOSITION2 | DSBCAPS_GLOBALFOCUS; sound_buffer.dwFlags |= DSBCAPS_CTRLVOLUME | (ch >= 4 ? DSBCAPS_LOCHARDWARE : DSBCAPS_LOCSOFTWARE); sound_buffer.guid3DAlgorithm = GUID_NULL; - hr = IDirectSound_CreateSoundBuffer (sd->lpDS, &sound_buffer, &pdsb, NULL); + hr = IDirectSound_CreateSoundBuffer (s->lpDS, &sound_buffer, &pdsb, NULL); if (SUCCEEDED (hr)) break; if (sound_buffer.dwFlags & DSBCAPS_LOCHARDWARE) { HRESULT hr2 = hr; sound_buffer.dwFlags &= ~DSBCAPS_LOCHARDWARE; sound_buffer.dwFlags |= DSBCAPS_LOCSOFTWARE; - hr = IDirectSound_CreateSoundBuffer (sd->lpDS, &sound_buffer, &pdsb, NULL); + hr = IDirectSound_CreateSoundBuffer (s->lpDS, &sound_buffer, &pdsb, NULL); if (SUCCEEDED(hr)) { - //write_log (L"SOUND: Couldn't use hardware buffer (switched to software): %s\n", DXError (hr2)); + //write_log (L"DSSOUND: Couldn't use hardware buffer (switched to software): %s\n", DXError (hr2)); break; } } - write_log (L"SOUND: Secondary CreateSoundBuffer() failure: %s\n", DXError (hr)); + write_log (L"DSSOUND: Secondary CreateSoundBuffer() failure: %s\n", DXError (hr)); } if (pdsb == NULL) goto error; - hr = IDirectSound_QueryInterface (pdsb, &IID_IDirectSoundBuffer8, (LPVOID*)&sd->lpDSBsecondary); + hr = IDirectSound_QueryInterface (pdsb, &IID_IDirectSoundBuffer8, (LPVOID*)&s->lpDSBsecondary); if (FAILED (hr)) { - write_log (L"SOUND: Secondary QueryInterface() failure: %s\n", DXError (hr)); + write_log (L"DSSOUND: Secondary QueryInterface() failure: %s\n", DXError (hr)); goto error; } IDirectSound_Release (pdsb); @@ -692,9 +711,61 @@ error: return 0; } +int open_sound_device (struct sound_data *sd, int index, int bufsize, int freq, int channels) +{ + int ret = 0; + struct sound_dp *sdp = xcalloc (sizeof (struct sound_dp), 1); + sd->data = sdp; + sd->sndbufsize = bufsize; + sd->freq = freq; + sd->channels = channels; + sd->samplesize = channels * 2; + sd->paused = 1; + if (sound_devices[index].type == SOUND_DEVICE_AL) + ret = open_audio_al (sd, index); + else if (sound_devices[index].type == SOUND_DEVICE_DS) + ret = open_audio_ds (sd, index); + else if (sound_devices[index].type == SOUND_DEVICE_PA) + ret = open_audio_pa (sd, index); + return ret; +} +void close_sound_device (struct sound_data *sd) +{ + pause_sound_device (sd); + if (sd->devicetype == SOUND_DEVICE_AL) + close_audio_al (sd); + else if (sd->devicetype == SOUND_DEVICE_DS) + close_audio_ds (sd); + else if (sd->devicetype == SOUND_DEVICE_PA) + close_audio_pa (sd); + xfree (sd->data); + sd->data = NULL; +} +void pause_sound_device (struct sound_data *sd) +{ + sd->paused = 1; + if (sd->devicetype == SOUND_DEVICE_AL) + pause_audio_al (sd); + else if (sd->devicetype == SOUND_DEVICE_DS) + pause_audio_ds (sd); + else if (sd->devicetype == SOUND_DEVICE_PA) + pause_audio_pa (sd); +} +void resume_sound_device (struct sound_data *sd) +{ + if (sd->devicetype == SOUND_DEVICE_AL) + resume_audio_al (sd); + else if (sd->devicetype == SOUND_DEVICE_DS) + resume_audio_ds (sd); + else if (sd->devicetype == SOUND_DEVICE_PA) + resume_audio_pa (sd); + sd->paused = 0; +} + + static int open_sound (void) { - int ret; + int ret = 0, num; int size = currprefs.sound_maxbsiz; if (!currprefs.produce_sound) @@ -710,13 +781,10 @@ static int open_sound (void) if (size < 512) size = 512; - enumerate_sound_devices (); - if (sound_devices[currprefs.win32_soundcard].type == SOUND_DEVICE_AL) - ret = open_audio_al (sdp, size); - else if (sound_devices[currprefs.win32_soundcard].type == SOUND_DEVICE_DS) - ret = open_audio_ds (sdp, size); - else if (sound_devices[currprefs.win32_soundcard].type == SOUND_DEVICE_PA) - ret = open_audio_pa (sdp, size); + num = enumerate_sound_devices (); + if (currprefs.win32_soundcard >= num) + currprefs.win32_soundcard = changed_prefs.win32_soundcard = 0; + ret = open_sound_device (sdp, currprefs.win32_soundcard, size, currprefs.sound_freq, get_audio_nativechannels ()); if (!ret) return 0; @@ -732,7 +800,8 @@ static int open_sound (void) have_sound = 1; sound_available = 1; update_sound (fake_vblank_hz); - sndbufpt = sndbuffer; + paula_sndbufsize = sdp->sndbufsize; + paula_sndbufpt = paula_sndbuffer; driveclick_init (); return 1; @@ -744,13 +813,7 @@ void close_sound (void) gui_data.sndbuf_status = 3; if (! have_sound) return; - pause_sound (); - if (sdp->devicetype == SOUND_DEVICE_AL) - close_audio_al (sdp); - else if (sdp->devicetype == SOUND_DEVICE_DS) - close_audio_ds (sdp); - else if (sdp->devicetype == SOUND_DEVICE_PA) - close_audio_pa (sdp); + close_sound_device (sdp); have_sound = 0; } @@ -776,15 +839,9 @@ void pause_sound (void) { if (sdp->paused) return; - sdp->paused = 1; if (!have_sound) return; - if (sdp->devicetype == SOUND_DEVICE_AL) - pause_audio_al (sdp); - else if (sdp->devicetype == SOUND_DEVICE_DS) - pause_audio_ds (sdp); - else if (sdp->devicetype == SOUND_DEVICE_PA) - pause_audio_pa (sdp); + pause_sound_device (sdp); } void resume_sound (void) @@ -793,12 +850,7 @@ void resume_sound (void) return; if (!have_sound) return; - if (sdp->devicetype == SOUND_DEVICE_AL) - resume_audio_al (sdp); - else if (sdp->devicetype == SOUND_DEVICE_DS) - resume_audio_ds (sdp); - else if (sdp->devicetype == SOUND_DEVICE_PA) - resume_audio_pa (sdp); + resume_sound_device (sdp); } void reset_sound (void) @@ -838,10 +890,11 @@ void sound_setadjust (double v) #define SND_STATUSCNT 10 -#define cf(x) if ((x) >= sd->dsoundbuf) (x) -= sd->dsoundbuf; +#define cf(x) if ((x) >= s->dsoundbuf) (x) -= s->dsoundbuf; static void restart_sound_buffer2 (struct sound_data *sd) { + struct sound_dp *s = sd->data; DWORD playpos, safed; HRESULT hr; @@ -849,15 +902,15 @@ static void restart_sound_buffer2 (struct sound_data *sd) return; if (sdp->waiting_for_buffer != -1) return; - hr = IDirectSoundBuffer_GetCurrentPosition (sd->lpDSBsecondary, &playpos, &safed); + hr = IDirectSoundBuffer_GetCurrentPosition (s->lpDSBsecondary, &playpos, &safed); if (FAILED (hr)) { - write_log (L"SOUND: DirectSoundBuffer_GetCurrentPosition failed, %s\n", DXError (hr)); + write_log (L"DSSOUND: DirectSoundBuffer_GetCurrentPosition failed, %s\n", DXError (hr)); return; } - sd->writepos = safed + sd->snd_writeoffset; - if (sd->writepos < 0) - sd->writepos += sd->dsoundbuf; - cf (sd->writepos); + s->writepos = safed + s->snd_writeoffset; + if (s->writepos < 0) + s->writepos += s->dsoundbuf; + cf (s->writepos); } void restart_sound_buffer (void) @@ -867,22 +920,24 @@ void restart_sound_buffer (void) static int alcheck (struct sound_data *sd, int v) { + struct sound_dp *s = sd->data; int err = alGetError (); if (err != AL_NO_ERROR) { int v1, v2, v3; - alGetSourcei (sd->al_Source, AL_BUFFERS_PROCESSED, &v1); - alGetSourcei (sd->al_Source, AL_BUFFERS_QUEUED, &v2); - alGetSourcei (sd->al_Source, AL_SOURCE_STATE, &v3); + alGetSourcei (s->al_Source, AL_BUFFERS_PROCESSED, &v1); + alGetSourcei (s->al_Source, AL_BUFFERS_QUEUED, &v2); + alGetSourcei (s->al_Source, AL_SOURCE_STATE, &v3); write_log (L"OpenAL %d: error %d. PROC=%d QUEUE=%d STATE=%d\n", v, err, v1, v2, v3); write_log (L" %d %08x %08x %08x %d %d\n", - sd->al_toggle, sd->al_Buffers[sd->al_toggle], sd->al_format, sd->al_bigbuffer, sd->al_bufsize, currprefs.sound_freq); + s->al_toggle, s->al_Buffers[s->al_toggle], s->al_format, s->al_bigbuffer, s->al_bufsize, sd->freq); return 1; } return 0; } -static void finish_sound_buffer_al (struct sound_data *sd) +static void finish_sound_buffer_al (struct sound_data *sd, uae_u16 *sndbuffer) { + struct sound_dp *s = sd->data; static int tfprev; static int statuscnt; int v, v2; @@ -893,50 +948,52 @@ static void finish_sound_buffer_al (struct sound_data *sd) if (savestate_state) return; - if (statuscnt > 0) { - statuscnt--; - if (statuscnt == 0) + if (sd == sdp) { + if (statuscnt > 0) { + statuscnt--; + if (statuscnt == 0) + gui_data.sndbuf_status = 0; + } + if (gui_data.sndbuf_status == 3) gui_data.sndbuf_status = 0; } - if (gui_data.sndbuf_status == 3) - gui_data.sndbuf_status = 0; alGetError (); - memcpy (sd->al_bigbuffer + sd->al_offset, sndbuffer, sndbufsize); - sd->al_offset += sndbufsize; - if (sd->al_offset >= sd->al_bufsize) { + memcpy (s->al_bigbuffer + s->al_offset, sndbuffer, sd->sndbufsize); + s->al_offset += sd->sndbufsize; + if (s->al_offset >= s->al_bufsize) { ALuint tmp; - alGetSourcei (sd->al_Source, AL_BUFFERS_PROCESSED, &v); + alGetSourcei (s->al_Source, AL_BUFFERS_PROCESSED, &v); while (v == 0 && sd->waiting_for_buffer < 0) { sleep_millis (1); - alGetSourcei (sd->al_Source, AL_SOURCE_STATE, &v); + alGetSourcei (s->al_Source, AL_SOURCE_STATE, &v); if (v != AL_PLAYING) break; - alGetSourcei (sd->al_Source, AL_BUFFERS_PROCESSED, &v); + alGetSourcei (s->al_Source, AL_BUFFERS_PROCESSED, &v); } - alSourceUnqueueBuffers (sd->al_Source, 1, &tmp); + alSourceUnqueueBuffers (s->al_Source, 1, &tmp); alGetError (); // write_log (L" %d %08x %08x %08x %d %d\n", // al_toggle, al_Buffers[al_toggle], al_format, al_bigbuffer, al_bufsize, currprefs.sound_freq); - alBufferData (sd->al_Buffers[sd->al_toggle], sd->al_format, sd->al_bigbuffer, sd->al_bufsize, currprefs.sound_freq); + alBufferData (s->al_Buffers[s->al_toggle], s->al_format, s->al_bigbuffer, s->al_bufsize, sd->freq); alcheck (sd, 4); - alSourceQueueBuffers (sd->al_Source, 1, &sd->al_Buffers[sd->al_toggle]); + alSourceQueueBuffers (s->al_Source, 1, &s->al_Buffers[s->al_toggle]); alcheck (sd, 2); - sd->al_toggle++; - if (sd->al_toggle >= AL_BUFFERS) - sd->al_toggle = 0; + s->al_toggle++; + if (s->al_toggle >= AL_BUFFERS) + s->al_toggle = 0; - alGetSourcei (sd->al_Source, AL_BUFFERS_QUEUED, &v2); + alGetSourcei (s->al_Source, AL_BUFFERS_QUEUED, &v2); alcheck (sd, 5); - alGetSourcei (sd->al_Source, AL_SOURCE_STATE, &v); + alGetSourcei (s->al_Source, AL_SOURCE_STATE, &v); alcheck (sd, 3); if (v != AL_PLAYING && v2 >= AL_BUFFERS) { if (sd->waiting_for_buffer > 0) { write_log (L"AL SOUND PLAY!\n"); - alSourcePlay (sd->al_Source); + alSourcePlay (s->al_Source); sd->waiting_for_buffer = -1; tfprev = timeframes + 10; tfprev = (tfprev / 10) * 10; @@ -948,17 +1005,18 @@ static void finish_sound_buffer_al (struct sound_data *sd) sd->waiting_for_buffer = 1; } } - sd->al_offset = 0; + s->al_offset = 0; } alcheck (sd, 1); - alGetSourcei (sd->al_Source, AL_SOURCE_STATE, &v); + alGetSourcei (s->al_Source, AL_SOURCE_STATE, &v); alcheck (sd, 6); - if (v == AL_PLAYING) { - alGetSourcei (sd->al_Source, AL_BYTE_OFFSET, &v); + + if (v == AL_PLAYING && sd == sdp) { + alGetSourcei (s->al_Source, AL_BYTE_OFFSET, &v); alcheck (sd, 7); - v -= sd->al_offset; - gui_data.sndbuf = 100 * v / sndbufsize; + v -= s->al_offset; + gui_data.sndbuf = 100 * v / sd->sndbufsize; m = gui_data.sndbuf / 100.0; if (isvsync ()) { @@ -994,8 +1052,71 @@ static void finish_sound_buffer_al (struct sound_data *sd) alcheck (sd, 0); } -static void finish_sound_buffer_ds (struct sound_data *sd) +int blocking_sound_device (struct sound_data *sd) +{ + struct sound_dp *s = sd->data; + + if (sd->devicetype == SOUND_DEVICE_DS) { + HRESULT hr; + DWORD playpos, safepos; + int diff; + + hr = IDirectSoundBuffer_GetCurrentPosition (s->lpDSBsecondary, &playpos, &safepos); + if (FAILED (hr)) { + restore_ds (sd, hr); + write_log (L"DSSOUND: GetCurrentPosition failed: %s\n", DXError (hr)); + return -1; + } + if (s->writepos >= safepos) + diff = s->writepos - safepos; + else + diff = s->dsoundbuf - safepos + s->writepos; + if (diff > s->snd_maxoffset) + return 1; + return 0; + + } else if (sd->devicetype == SOUND_DEVICE_AL) { + int v = 0; + alGetError (); + alGetSourcei (s->al_Source, AL_BUFFERS_QUEUED, &v); + if (alGetError () != AL_NO_ERROR) + return -1; + if (v < AL_BUFFERS) + return 0; + return 1; + } + return -1; +} + +int get_offset_sound_device (struct sound_data *sd) +{ + struct sound_dp *s = sd->data; + + if (sd->devicetype == SOUND_DEVICE_DS) { + HRESULT hr; + DWORD playpos, safedist, status; + + hr = IDirectSoundBuffer_GetStatus (s->lpDSBsecondary, &status); + hr = IDirectSoundBuffer_GetCurrentPosition (s->lpDSBsecondary, &playpos, &safedist); + if (FAILED (hr)) + return -1; + playpos -= s->writepos; + if (playpos < 0) + playpos += s->dsoundbuf; + return playpos; + } else if (sd->devicetype == SOUND_DEVICE_AL) { + int v; + alGetError (); + alGetSourcei (s->al_Source, AL_BYTE_OFFSET, &v); + if (alGetError () == AL_NO_ERROR) + return v; + } + return -1; +} + +static void finish_sound_buffer_ds (struct sound_data *sd, uae_u16 *sndbuffer) { + struct sound_dp *s = sd->data; static int tfprev; DWORD playpos, safepos, status; HRESULT hr; @@ -1006,13 +1127,15 @@ static void finish_sound_buffer_ds (struct sound_data *sd) double vdiff, m, skipmode; static int statuscnt; - if (statuscnt > 0) { - statuscnt--; - if (statuscnt == 0) + if (sd == sdp) { + if (statuscnt > 0) { + statuscnt--; + if (statuscnt == 0) + gui_data.sndbuf_status = 0; + } + if (gui_data.sndbuf_status == 3) gui_data.sndbuf_status = 0; } - if (gui_data.sndbuf_status == 3) - gui_data.sndbuf_status = 0; if (!sd->waiting_for_buffer) return; @@ -1020,16 +1143,16 @@ static void finish_sound_buffer_ds (struct sound_data *sd) return; if (sd->waiting_for_buffer == 1) { - hr = IDirectSoundBuffer_Play (sd->lpDSBsecondary, 0, 0, DSBPLAY_LOOPING); + hr = IDirectSoundBuffer_Play (s->lpDSBsecondary, 0, 0, DSBPLAY_LOOPING); if (FAILED (hr)) { - write_log (L"SOUND: Play failed: %s\n", DXError (hr)); + write_log (L"DSSOUND: Play failed: %s\n", DXError (hr)); restore_ds (sd, DSERR_BUFFERLOST); sd->waiting_for_buffer = 0; return; } - hr = IDirectSoundBuffer_SetCurrentPosition (sd->lpDSBsecondary, 0); + hr = IDirectSoundBuffer_SetCurrentPosition (s->lpDSBsecondary, 0); if (FAILED (hr)) { - write_log (L"SOUND: 1st SetCurrentPosition failed: %s\n", DXError (hr)); + write_log (L"DSSOUND: 1st SetCurrentPosition failed: %s\n", DXError (hr)); restore_ds (sd, DSERR_BUFFERLOST); sd->waiting_for_buffer = 0; return; @@ -1037,74 +1160,74 @@ static void finish_sound_buffer_ds (struct sound_data *sd) /* there are crappy drivers that return PLAYCURSOR = WRITECURSOR = 0 without this.. */ counter = 5000; for (;;) { - hr = IDirectSoundBuffer_GetCurrentPosition (sd->lpDSBsecondary, &playpos, &sd->safedist); + hr = IDirectSoundBuffer_GetCurrentPosition (s->lpDSBsecondary, &playpos, &s->safedist); if (playpos > 0) break; sleep_millis (1); counter--; if (counter < 0) { - write_log (L"SOUND: stuck?!?!\n"); + write_log (L"DSSOUND: stuck?!?!\n"); break; } } - write_log (L"SOUND: %d = (%d - %d)\n", (sd->safedist - playpos) / sd->samplesize, sd->safedist / sd->samplesize, playpos / sd->samplesize); + write_log (L"DSSOUND: %d = (%d - %d)\n", (s->safedist - playpos) / sd->samplesize, s->safedist / sd->samplesize, playpos / sd->samplesize); recalc_offsets (sd); - sd->safedist -= playpos; - if (sd->safedist < 64) - sd->safedist = 64; - cf (sd->safedist); + s->safedist -= playpos; + if (s->safedist < 64) + s->safedist = 64; + cf (s->safedist); #if 0 - snd_totalmaxoffset_uf += sd->safedist; + snd_totalmaxoffset_uf += s->safedist; cf (snd_totalmaxoffset_uf); - snd_totalmaxoffset_of += sd->safedist; + snd_totalmaxoffset_of += s->safedist; cf (snd_totalmaxoffset_of); - snd_maxoffset += sd->safedist; + snd_maxoffset += s->safedist; cf (snd_maxoffset); - snd_writeoffset += sd->safedist; + snd_writeoffset += s->safedist; cf (snd_writeoffset); #endif sd->waiting_for_buffer = -1; restart_sound_buffer2 (sd); - write_log (L"SOUND: bs=%d w=%d max=%d tof=%d tuf=%d\n", - sndbufsize / sd->samplesize, sd->snd_writeoffset / sd->samplesize, - sd->snd_maxoffset / sd->samplesize, sd->snd_totalmaxoffset_of / sd->samplesize, - sd->snd_totalmaxoffset_uf / sd->samplesize); + write_log (L"DSSOUND: bs=%d w=%d max=%d tof=%d tuf=%d\n", + sd->sndbufsize / sd->samplesize, s->snd_writeoffset / sd->samplesize, + s->snd_maxoffset / sd->samplesize, s->snd_totalmaxoffset_of / sd->samplesize, + s->snd_totalmaxoffset_uf / sd->samplesize); tfprev = timeframes + 10; tfprev = (tfprev / 10) * 10; } counter = 5000; - hr = IDirectSoundBuffer_GetStatus (sd->lpDSBsecondary, &status); + hr = IDirectSoundBuffer_GetStatus (s->lpDSBsecondary, &status); if (FAILED (hr)) { - write_log (L"SOUND: GetStatus() failed: %s\n", DXError (hr)); + write_log (L"DSSOUND: GetStatus() failed: %s\n", DXError (hr)); restore_ds (sd, DSERR_BUFFERLOST); return; } if (status & DSBSTATUS_BUFFERLOST) { - write_log (L"SOUND: buffer lost\n"); + write_log (L"DSSOUND: buffer lost\n"); restore_ds (sd, DSERR_BUFFERLOST); return; } if ((status & (DSBSTATUS_PLAYING | DSBSTATUS_LOOPING)) != (DSBSTATUS_PLAYING | DSBSTATUS_LOOPING)) { - write_log (L"SOUND: status = %08X\n", status); + write_log (L"DSSOUND: status = %08X\n", status); restore_ds (sd, DSERR_BUFFERLOST); return; } for (;;) { - hr = IDirectSoundBuffer_GetCurrentPosition (sd->lpDSBsecondary, &playpos, &safepos); + hr = IDirectSoundBuffer_GetCurrentPosition (s->lpDSBsecondary, &playpos, &safepos); if (FAILED (hr)) { restore_ds (sd, hr); - write_log (L"SOUND: GetCurrentPosition failed: %s\n", DXError (hr)); + write_log (L"DSSOUND: GetCurrentPosition failed: %s\n", DXError (hr)); return; } - if (sd->writepos >= safepos) - diff = sd->writepos - safepos; + if (s->writepos >= safepos) + diff = s->writepos - safepos; else - diff = sd->dsoundbuf - safepos + sd->writepos; + diff = s->dsoundbuf - safepos + s->writepos; - if (diff < sndbufsize || diff > sd->snd_totalmaxoffset_uf) { + if (diff < sd->sndbufsize || diff > s->snd_totalmaxoffset_uf) { #if 0 - hr = IDirectSoundBuffer_Lock (lpDSBsecondary, sd->writepos, sndbufsize, &b1, &s1, &b2, &s2, 0); + hr = IDirectSoundBuffer_Lock (lpDSBsecondary, s->writepos, sndbufsize, &b1, &s1, &b2, &s2, 0); if (SUCCEEDED(hr)) { memset (b1, 0, s1); if (b2) @@ -1114,30 +1237,30 @@ static void finish_sound_buffer_ds (struct sound_data *sd) #endif gui_data.sndbuf_status = -1; statuscnt = SND_STATUSCNT; - if (diff > sd->snd_totalmaxoffset_uf) - sd->writepos += sd->dsoundbuf - diff; - sd->writepos += sndbufsize; - cf (sd->writepos); - diff = sd->safedist; + if (diff > s->snd_totalmaxoffset_uf) + s->writepos += s->dsoundbuf - diff; + s->writepos += sd->sndbufsize; + cf (s->writepos); + diff = s->safedist; break; } - if (diff > sd->snd_totalmaxoffset_of) { + if (diff > s->snd_totalmaxoffset_of) { gui_data.sndbuf_status = 2; statuscnt = SND_STATUSCNT; restart_sound_buffer2 (sd); - diff = sd->snd_writeoffset; - write_log (L"SOUND: underflow (%d %d)\n", diff / sd->samplesize, sd->snd_totalmaxoffset_of / sd->samplesize); + diff = s->snd_writeoffset; + write_log (L"DSSOUND: underflow (%d %d)\n", diff / sd->samplesize, s->snd_totalmaxoffset_of / sd->samplesize); break; } - if (diff > sd->snd_maxoffset) { + if (diff > s->snd_maxoffset) { gui_data.sndbuf_status = 1; statuscnt = SND_STATUSCNT; sleep_millis (1); counter--; if (counter < 0) { - write_log (L"SOUND: sound system got stuck!?\n"); + write_log (L"DSSOUND: sound system got stuck!?\n"); restore_ds (sd, DSERR_BUFFERLOST); return; } @@ -1146,56 +1269,58 @@ static void finish_sound_buffer_ds (struct sound_data *sd) break; } - hr = IDirectSoundBuffer_Lock (sd->lpDSBsecondary, sd->writepos, sndbufsize, &b1, &s1, &b2, &s2, 0); + hr = IDirectSoundBuffer_Lock (s->lpDSBsecondary, s->writepos, sd->sndbufsize, &b1, &s1, &b2, &s2, 0); if (restore_ds (sd, hr)) return; if (FAILED (hr)) { - write_log (L"SOUND: lock failed: %s (%d %d)\n", DXError (hr), sd->writepos / sd->samplesize, sndbufsize / sd->samplesize); + write_log (L"DSSOUND: lock failed: %s (%d %d)\n", DXError (hr), s->writepos / sd->samplesize, sd->sndbufsize / sd->samplesize); return; } memcpy (b1, sndbuffer, s1); if (b2) memcpy (b2, (uae_u8*)sndbuffer + s1, s2); - IDirectSoundBuffer_Unlock (sd->lpDSBsecondary, b1, s1, b2, s2); + IDirectSoundBuffer_Unlock (s->lpDSBsecondary, b1, s1, b2, s2); - vdiff = diff - sd->snd_writeoffset; - m = 100.0 * vdiff / sd->max_sndbufsize; + if (sd == sdp) { + vdiff = diff - s->snd_writeoffset; + m = 100.0 * vdiff / s->max_sndbufsize; - if (isvsync ()) { + if (isvsync ()) { - skipmode = pow (m < 0 ? -m : m, EXP) / 8; - if (m < 0) - skipmode = -skipmode; - if (skipmode < -ADJUST_VSSIZE) - skipmode = -ADJUST_VSSIZE; - if (skipmode > ADJUST_VSSIZE) - skipmode = ADJUST_VSSIZE; + skipmode = pow (m < 0 ? -m : m, EXP) / 8; + if (m < 0) + skipmode = -skipmode; + if (skipmode < -ADJUST_VSSIZE) + skipmode = -ADJUST_VSSIZE; + if (skipmode > ADJUST_VSSIZE) + skipmode = ADJUST_VSSIZE; - } else { + } else { - skipmode = pow (m < 0 ? -m : m, EXP) / 2; - if (m < 0) - skipmode = -skipmode; - if (skipmode < -ADJUST_SIZE) - skipmode = -ADJUST_SIZE; - if (skipmode > ADJUST_SIZE) - skipmode = ADJUST_SIZE; + skipmode = pow (m < 0 ? -m : m, EXP) / 2; + if (m < 0) + skipmode = -skipmode; + if (skipmode < -ADJUST_SIZE) + skipmode = -ADJUST_SIZE; + if (skipmode > ADJUST_SIZE) + skipmode = ADJUST_SIZE; - } + } - if (tfprev != timeframes) { - if (sound_debug && !(tfprev % 10)) - write_log (L"b=%4d,%5d,%5d,%5d d=%5d vd=%5.0f s=%+02.1f\n", - sndbufsize / sd->samplesize, sd->snd_configsize / sd->samplesize, sd->max_sndbufsize / sd->samplesize, - sd->dsoundbuf / sd->samplesize, diff / sd->samplesize, vdiff, skipmode); - tfprev = timeframes; - if (!avioutput_audio) - sound_setadjust (skipmode); - gui_data.sndbuf = vdiff * 1000 / (sd->snd_maxoffset - sd->snd_writeoffset); + if (tfprev != timeframes) { + if (sound_debug && !(tfprev % 10)) + write_log (L"b=%4d,%5d,%5d,%5d d=%5d vd=%5.0f s=%+02.1f\n", + sd->sndbufsize / sd->samplesize, s->snd_configsize / sd->samplesize, s->max_sndbufsize / sd->samplesize, + s->dsoundbuf / sd->samplesize, diff / sd->samplesize, vdiff, skipmode); + tfprev = timeframes; + if (!avioutput_audio) + sound_setadjust (skipmode); + gui_data.sndbuf = vdiff * 1000 / (s->snd_maxoffset - s->snd_writeoffset); + } } - sd->writepos += sndbufsize; - cf (sd->writepos); + s->writepos += sd->sndbufsize; + cf (s->writepos); } static void channelswap (uae_s16 *sndbuffer, int len) @@ -1222,34 +1347,38 @@ static void channelswap6 (uae_s16 *sndbuffer, int len) } } +void send_sound (struct sound_data *sd, uae_u16 *sndbuffer) +{ + if (sd->devicetype == SOUND_DEVICE_AL) + finish_sound_buffer_al (sd, sndbuffer); + else if (sd->devicetype == SOUND_DEVICE_DS) + finish_sound_buffer_ds (sd, sndbuffer); + else if (sd->devicetype == SOUND_DEVICE_PA) + finish_sound_buffer_pa (sd, sndbuffer); +} + void finish_sound_buffer (void) { if (turbo_emulation) return; if (currprefs.sound_stereo_swap_paula) { if (get_audio_nativechannels () == 2 || get_audio_nativechannels () == 4) - channelswap ((uae_s16*)sndbuffer, sndbufsize / 2); + channelswap ((uae_s16*)paula_sndbuffer, sdp->sndbufsize / 2); else if (get_audio_nativechannels() == 6) - channelswap6 ((uae_s16*)sndbuffer, sndbufsize / 2); + channelswap6 ((uae_s16*)paula_sndbuffer, sdp->sndbufsize / 2); } #ifdef DRIVESOUND - driveclick_mix ((uae_s16*)sndbuffer, sndbufsize / 2); + driveclick_mix ((uae_s16*)paula_sndbuffer, sdp->sndbufsize / 2); #endif #ifdef AVIOUTPUT if (avioutput_audio) - AVIOutput_WriteAudio ((uae_u8*)sndbuffer, sndbufsize); + AVIOutput_WriteAudio ((uae_u8*)paula_sndbuffer, sdp->sndbufsize); if (avioutput_enabled && (!avioutput_framelimiter || avioutput_nosoundoutput)) return; #endif if (!have_sound) return; - - if (sdp->devicetype == SOUND_DEVICE_AL) - finish_sound_buffer_al (sdp); - else if (sdp->devicetype == SOUND_DEVICE_DS) - finish_sound_buffer_ds (sdp); - else if (sdp->devicetype == SOUND_DEVICE_PA) - finish_sound_buffer_pa (sdp); + send_sound (sdp, paula_sndbuffer); } static BOOL CALLBACK DSEnumProc (LPGUID lpGUID, LPCTSTR lpszDesc, LPCTSTR lpszDrvName, LPVOID lpContext) @@ -1458,8 +1587,6 @@ int enumerate_sound_devices (void) break; } } - if (currprefs.win32_soundcard >= num_sound_devices) - currprefs.win32_soundcard = 0; return num_sound_devices; } diff --git a/od-win32/sounddep/sound.h b/od-win32/sounddep/sound.h index d57f31bf..017c8f53 100644 --- a/od-win32/sounddep/sound.h +++ b/od-win32/sounddep/sound.h @@ -7,9 +7,9 @@ */ extern int sound_fd; -extern uae_u16 sndbuffer[]; -extern uae_u16 *sndbufpt; -extern int sndbufsize; +extern uae_u16 paula_sndbuffer[]; +extern uae_u16 *paula_sndbufpt; +extern int paula_sndbufsize; extern void finish_sound_buffer (void); extern void restart_sound_buffer (void); extern int init_sound (void); @@ -27,36 +27,61 @@ extern void sound_volume (int); extern void set_volume (int, int); extern void master_sound_volume (int); +struct sound_data +{ + int waiting_for_buffer; + int devicetype; + int obtainedfreq; + int paused; + int mute; + int channels; + int freq; + int samplesize; + int sndbufsize; + void *data; +}; + + +void send_sound (struct sound_data *sd, uae_u16 *sndbuffer); +int open_sound_device (struct sound_data *sd, int index, int bufsize, int freq, int channels); +void close_sound_device (struct sound_data *sd); +void pause_sound_device (struct sound_data *sd); +void resume_sound_device (struct sound_data *sd); +void set_volume_sound_device (struct sound_data *sd, int volume, int mute); +int get_offset_sound_device (struct sound_data *sd); +int blocking_sound_device (struct sound_data *sd); + + STATIC_INLINE void check_sound_buffers (void) { if (currprefs.sound_stereo == SND_4CH_CLONEDSTEREO) { - ((uae_u16*)sndbufpt)[0] = ((uae_u16*)sndbufpt)[-2]; - ((uae_u16*)sndbufpt)[1] = ((uae_u16*)sndbufpt)[-1]; - sndbufpt = (uae_u16 *)(((uae_u8 *)sndbufpt) + 2 * 2); + ((uae_u16*)paula_sndbufpt)[0] = ((uae_u16*)paula_sndbufpt)[-2]; + ((uae_u16*)paula_sndbufpt)[1] = ((uae_u16*)paula_sndbufpt)[-1]; + paula_sndbufpt = (uae_u16 *)(((uae_u8 *)paula_sndbufpt) + 2 * 2); } else if (currprefs.sound_stereo == SND_6CH_CLONEDSTEREO) { - uae_s16 *p = ((uae_s16*)sndbufpt); + uae_s16 *p = ((uae_s16*)paula_sndbufpt); uae_s32 sum; p[2] = p[-2]; p[3] = p[-1]; sum = (uae_s32)(p[-2]) + (uae_s32)(p[-1]) + (uae_s32)(p[2]) + (uae_s32)(p[3]); p[0] = sum >> 3; p[1] = sum >> 3; - sndbufpt = (uae_u16 *)(((uae_u8 *)sndbufpt) + 4 * 2); + paula_sndbufpt = (uae_u16 *)(((uae_u8 *)paula_sndbufpt) + 4 * 2); } - if ((char *)sndbufpt - (char *)sndbuffer >= sndbufsize) { + if ((char *)paula_sndbufpt - (char *)paula_sndbuffer >= paula_sndbufsize) { finish_sound_buffer (); - sndbufpt = sndbuffer; + paula_sndbufpt = paula_sndbuffer; } } STATIC_INLINE void clear_sound_buffers (void) { - memset (sndbuffer, 0, sndbufsize); - sndbufpt = sndbuffer; + memset (paula_sndbuffer, 0, paula_sndbufsize); + paula_sndbufpt = paula_sndbuffer; } -#define PUT_SOUND_BYTE(b) do { *(uae_u8 *)sndbufpt = b; sndbufpt = (uae_u16 *)(((uae_u8 *)sndbufpt) + 1); } while (0) -#define PUT_SOUND_WORD(b) do { *(uae_u16 *)sndbufpt = b; sndbufpt = (uae_u16 *)(((uae_u8 *)sndbufpt) + 2); } while (0) +#define PUT_SOUND_BYTE(b) do { *(uae_u8 *)paula_sndbufpt = b; paula_sndbufpt = (uae_u16 *)(((uae_u8 *)paula_sndbufpt) + 1); } while (0) +#define PUT_SOUND_WORD(b) do { *(uae_u16 *)paula_sndbufpt = b; paula_sndbufpt = (uae_u16 *)(((uae_u8 *)paula_sndbufpt) + 2); } while (0) #define PUT_SOUND_BYTE_LEFT(b) PUT_SOUND_BYTE(b) #define PUT_SOUND_WORD_LEFT(b) do { if (currprefs.sound_filter) b = filter (b, &sound_filter_state[0]); PUT_SOUND_WORD(b); } while (0) #define PUT_SOUND_BYTE_RIGHT(b) PUT_SOUND_BYTE(b) diff --git a/od-win32/srcrelease.cmd b/od-win32/srcrelease.cmd index cbb802eb..ae4d1d5e 100644 --- a/od-win32/srcrelease.cmd +++ b/od-win32/srcrelease.cmd @@ -1,7 +1,7 @@ cd c:\projects\winuae_bak rm -rf bak mkdir bak -copy c:\projects\winuae\src\ c:\projects\winuae_bak\bak\ /s +copy /s c:\projects\winuae\src\* c:\projects\winuae_bak\bak\ copy d:\amiga\text\winuaechangelog.txt c:\projects\winuae_bak\bak\od-win32 copy d:\amiga\amiga\filesys.asm c:\projects\winuae_bak\bak @@ -106,6 +106,11 @@ rm -rf debug rm -rf release cd .. +cd uaeunp +rm -rf debug +rm -rf release +cd .. + cd .. zip -9 -r winuaesrc * diff --git a/od-win32/win32.c b/od-win32/win32.c index 6a2a7b20..7a556794 100644 --- a/od-win32/win32.c +++ b/od-win32/win32.c @@ -2212,20 +2212,35 @@ int target_parse_option (struct uae_prefs *p, TCHAR *option, TCHAR *value) return 1; if (cfgfile_string (option, value, L"soundcardname", tmpbuf, sizeof tmpbuf / sizeof (TCHAR))) { - int i; + int i, num; + + num = p->win32_soundcard; + p->win32_soundcard = -1; for (i = 0; sound_devices[i].cfgname; i++) { + if (i < num) + continue; if (!_tcscmp (sound_devices[i].cfgname, tmpbuf)) { p->win32_soundcard = i; break; } } + if (p->win32_soundcard < 0) { + for (i = 0; sound_devices[i].cfgname; i++) { + if (!_tcscmp (sound_devices[i].cfgname, tmpbuf)) { + p->win32_soundcard = i; + break; + } + } + } + if (p->win32_soundcard < 0) + p->win32_soundcard = num; return 1; } if (cfgfile_yesno (option, value, L"aspi", &v)) { p->win32_uaescsimode = 0; if (v) - p->win32_uaescsimode = get_aspi(0); + p->win32_uaescsimode = get_aspi (0); if (p->win32_uaescsimode < UAESCSI_ASPI_FIRST) p->win32_uaescsimode = UAESCSI_ADAPTECASPI; return 1; diff --git a/od-win32/win32.h b/od-win32/win32.h index dc6335c6..55ad3132 100644 --- a/od-win32/win32.h +++ b/od-win32/win32.h @@ -17,8 +17,8 @@ #define WINUAEPUBLICBETA 1 -#define WINUAEBETA L"25" -#define WINUAEDATE MAKEBD(2009, 4, 20) +#define WINUAEBETA L"26" +#define WINUAEDATE MAKEBD(2009, 4, 26) #define WINUAEEXTRA L"" #define WINUAEREV L"" diff --git a/od-win32/win32_scale2x.c b/od-win32/win32_scale2x.c index 78de8ff2..6ccf44e2 100644 --- a/od-win32/win32_scale2x.c +++ b/od-win32/win32_scale2x.c @@ -21,7 +21,7 @@ struct uae_filter uaefilters[] = { UAE_FILTER_DIRECT3D, 0, 1, L"Direct3D", L"direct3d", 1, 0, 0, 0, 0 }, - { UAE_FILTER_OPENGL, 0, 1, L"OpenGL", L"opengl", 1, 0, 0, 0, 0 }, + { UAE_FILTER_OPENGL, 0, 1, L"OpenGL (unsupported)", L"opengl", 1, 0, 0, 0, 0 }, { UAE_FILTER_SCALE2X, 0, 2, L"Scale2X", L"scale2x", 0, 0, UAE_FILTER_MODE_16_16 | UAE_FILTER_MODE_32_32, 0, 0 }, @@ -95,14 +95,16 @@ static void sizeoffset (RECT *dr, RECT *zr, int w, int h) void getfilterrect2 (RECT *sr, RECT *dr, RECT *zr, int dst_width, int dst_height, int aw, int ah, int scale, int temp_width, int temp_height) { - int aws, ahs; + int aws, ahs, ahs2, hdiff; int xs, ys; int xmult, ymult; int v; + ahs2 = ah * scale; ah = vblscale (ah); aws = aw * scale; ahs = ah * scale; + hdiff = (ahs2 - ahs) / 2; SetRect (sr, 0, 0, dst_width, dst_height); SetRect (zr, 0, 0, 0, 0); @@ -110,6 +112,7 @@ void getfilterrect2 (RECT *sr, RECT *dr, RECT *zr, int dst_width, int dst_height dr->top = (temp_height - ahs) / 2; dr->left -= (dst_width - aws) / 2; dr->top -= (dst_height - ahs) / 2; + dr->top -= hdiff; dr->right = dr->left + dst_width; dr->bottom = dr->top + dst_height; @@ -180,7 +183,8 @@ void getfilterrect2 (RECT *sr, RECT *dr, RECT *zr, int dst_width, int dst_height SetRect (sr, 0, 0, cw * scale, ch * scale); dr->left = (temp_width - aws) /2; - dr->top = (temp_height - ahs) / 2; + dr->top = (temp_height - ahs) / 2; + dr->top -= hdiff; dr->right = dr->left + cw * scale; dr->bottom = dr->top + ch * scale; OffsetRect (zr, cx * scale, cy * scale); @@ -196,6 +200,7 @@ void getfilterrect2 (RECT *sr, RECT *dr, RECT *zr, int dst_width, int dst_height dr->left = (temp_width - aws) /2; dr->top = (temp_height - ahs) / 2; + dr->top -= hdiff; dr->right = dr->left + dst_width * scale; dr->bottom = dr->top + dst_height * scale; diff --git a/od-win32/win32gfx.c b/od-win32/win32gfx.c index 77edfefd..7417752e 100644 --- a/od-win32/win32gfx.c +++ b/od-win32/win32gfx.c @@ -784,8 +784,6 @@ static int p96_double_buffer_firstx, p96_double_buffer_lastx; static int p96_double_buffer_first, p96_double_buffer_last; static int p96_double_buffer_needs_flushing = 0; -#include "statusline.h" -extern uae_u32 p96rc[256], p96gc[256], p96bc[256]; static void DX_Blit96 (int x, int y, int w, int h) { RECT dr, sr; @@ -832,26 +830,48 @@ static void DX_Blit96 (int x, int y, int w, int h) SetRect (&sr, x, y, x + w, y + h); DirectDraw_BlitToPrimary (&sr); } - if (0 && (currprefs.leds_on_screen & STATUSLINE_RTG)) { - DDSURFACEDESC2 desc; - RECT sr, dr; - int dst_width = currentmode->native_width; - int dst_height = currentmode->native_height; - SetRect (&sr, 0, 0, dxdata.statuswidth, dxdata.statusheight); - SetRect (&dr, dst_width - dxdata.statuswidth, dst_height - dxdata.statusheight, dst_width, dst_height); - DirectDraw_BlitRect (dxdata.statussurface, &sr, NULL, &dr); - if (locksurface (dxdata.statussurface, &desc)) { - int sy, yy; - yy = 0; - for (sy = dst_height - dxdata.statusheight; sy < dst_height; sy++) { - uae_u8 *buf = (uae_u8*)desc.lpSurface + yy * desc.lPitch; - draw_status_line_single (buf, currentmode->current_depth / 8, yy, dst_width, p96rc, p96gc, p96bc); - yy++; - } - unlocksurface (dxdata.statussurface); +} + +#include "statusline.h" +extern uae_u32 p96rc[256], p96gc[256], p96bc[256]; +static void RTGleds (void) +{ + DDSURFACEDESC2 desc; + RECT sr, dr; + int dst_width = currentmode->native_width; + int dst_height = currentmode->native_height; + int width; + + if (!(currprefs.leds_on_screen & STATUSLINE_RTG)) + return; + + width = dxdata.statuswidth; + if (dst_width < width) + width = dst_width; + SetRect (&sr, 0, 0, width, dxdata.statusheight); + SetRect (&dr, dst_width - width, dst_height - dxdata.statusheight, dst_width, dst_height); + + picasso_putcursor (dr.left, dr.top, + dr.right - dr.left, dr.bottom - dr.top); + DX_Blit96 (dr.left, dr.top, + dr.right - dr.left, dr.bottom - dr.top); + + DirectDraw_BlitRect (dxdata.statussurface, &sr, dxdata.secondary, &dr); + if (locksurface (dxdata.statussurface, &desc)) { + int sy, yy; + yy = 0; + for (sy = dst_height - dxdata.statusheight; sy < dst_height; sy++) { + uae_u8 *buf = (uae_u8*)desc.lpSurface + yy * desc.lPitch; + draw_status_line_single (buf, currentmode->current_depth / 8, yy, dst_width, p96rc, p96gc, p96bc); + yy++; } - DirectDraw_BlitRect (dxdata.primary, &dr, dxdata.statussurface, &sr); + unlocksurface (dxdata.statussurface); } + DirectDraw_BlitRect (dxdata.secondary, &dr, dxdata.statussurface, &sr); + + picasso_clearcursor (); + + DirectDraw_BlitToPrimary (&dr); } void gfx_unlock_picasso (void) @@ -872,6 +892,8 @@ void gfx_unlock_picasso (void) picasso_clearcursor (); p96_double_buffer_needs_flushing = 0; } + if (currprefs.leds_on_screen & STATUSLINE_RTG) + RTGleds (); } static void close_hwnds (void) @@ -1003,8 +1025,9 @@ static void update_gfxparams (void) if ((currprefs.win32_rtgscaleifsmall || currprefs.win32_rtgallowscaling) && (picasso96_state.Width != currentmode->native_width || picasso96_state.Height != currentmode->native_height)) scalepicasso = -1; } else if (isfullscreen () > 0) { - if (currprefs.gfx_size.width > picasso96_state.Width && currprefs.gfx_size.height > picasso96_state.Height) { - if (currprefs.win32_rtgscaleifsmall && !currprefs.win32_rtgmatchdepth) + //if (currprefs.gfx_size.width > picasso96_state.Width && currprefs.gfx_size.height > picasso96_state.Height) { + if (currentmode->native_width > picasso96_state.Width && currentmode->native_height > picasso96_state.Height) { + if (currprefs.win32_rtgscaleifsmall && !currprefs.win32_rtgmatchdepth) // can't scale to different color depth scalepicasso = 1; } } else if (isfullscreen () == 0) { @@ -1031,6 +1054,8 @@ static int open_windows (int full) in_sizemove = 0; updatewinfsmode (&currprefs); + D3D_free (); + OGL_free (); if (!DirectDraw_Start (displayGUID)) return 0; write_log (L"DirectDraw GUID=%s\n", outGUID (displayGUID)); @@ -1109,8 +1134,8 @@ int check_prefs_changed_gfx (void) c |= currprefs.win32_notaskbarbutton != changed_prefs.win32_notaskbarbutton ? 32 : 0; c |= currprefs.win32_borderless != changed_prefs.win32_borderless ? 32 : 0; c |= currprefs.win32_rtgmatchdepth != changed_prefs.win32_rtgmatchdepth ? 2 : 0; - c |= currprefs.win32_rtgscaleifsmall != changed_prefs.win32_rtgscaleifsmall ? (8 | 64) : 0; - c |= currprefs.win32_rtgallowscaling != changed_prefs.win32_rtgallowscaling ? (8 | 64) : 0; + c |= currprefs.win32_rtgscaleifsmall != changed_prefs.win32_rtgscaleifsmall ? (2 | 8 | 64) : 0; + c |= currprefs.win32_rtgallowscaling != changed_prefs.win32_rtgallowscaling ? (2 | 8 | 64) : 0; c |= currprefs.win32_rtgscaleaspectratio != changed_prefs.win32_rtgscaleaspectratio ? (8 | 64) : 0; c |= currprefs.win32_rtgvblankrate != changed_prefs.win32_rtgvblankrate ? 8 : 0; @@ -2278,6 +2303,7 @@ static BOOL doInit (void) picasso_vidinfo.height = currentmode->current_height; picasso_vidinfo.width = currentmode->current_width; picasso_vidinfo.depth = currentmode->current_depth; + picasso_vidinfo.offset = 0; #endif xfree (gfxvidinfo.realbufmem); diff --git a/od-win32/win32gui.c b/od-win32/win32gui.c index dedf717b..4d9cf146 100644 --- a/od-win32/win32gui.c +++ b/od-win32/win32gui.c @@ -5496,6 +5496,20 @@ static void enable_for_memorydlg (HWND hDlg) ew (hDlg, IDC_RTG_VBLANKRATE, rtg2); } +static int manybits (int v, int mask) +{ + int i, cnt; + + cnt = 0; + for (i = 0; i < 32; i++) { + if (((1 << i) & mask) & v) + cnt++; + } + if (cnt > 1) + return 1; + return 0; +} + static void values_to_memorydlg (HWND hDlg) { uae_u32 mem_size = 0; @@ -5592,20 +5606,23 @@ static void values_to_memorydlg (HWND hDlg) SetDlgItemText (hDlg, IDC_P96RAM, memsize_names[msi_gfx[mem_size]]); SendDlgItemMessage (hDlg, IDC_RTG_8BIT, CB_SETCURSEL, (workprefs.picasso96_modeflags & RGBFF_CLUT) ? 1 : 0, 0); SendDlgItemMessage (hDlg, IDC_RTG_16BIT, CB_SETCURSEL, - (workprefs.picasso96_modeflags & RGBFF_R5G6B5PC) ? 1 : - (workprefs.picasso96_modeflags & RGBFF_R5G5B5PC) ? 2 : - (workprefs.picasso96_modeflags & RGBFF_R5G6B5) ? 3 : - (workprefs.picasso96_modeflags & RGBFF_R5G5B5) ? 4 : - (workprefs.picasso96_modeflags & RGBFF_B5G6R5PC) ? 5 : - (workprefs.picasso96_modeflags & RGBFF_B5G5R5PC) ? 6 : 0, 0); + (manybits (workprefs.picasso96_modeflags, RGBFF_R5G6B5PC | RGBFF_R5G6B5PC | RGBFF_R5G6B5 | RGBFF_R5G5B5 | RGBFF_B5G6R5PC | RGBFF_B5G5R5PC)) ? 1 : + (workprefs.picasso96_modeflags & RGBFF_R5G6B5PC) ? 2 : + (workprefs.picasso96_modeflags & RGBFF_R5G5B5PC) ? 3 : + (workprefs.picasso96_modeflags & RGBFF_R5G6B5) ? 4 : + (workprefs.picasso96_modeflags & RGBFF_R5G5B5) ? 5 : + (workprefs.picasso96_modeflags & RGBFF_B5G6R5PC) ? 6 : + (workprefs.picasso96_modeflags & RGBFF_B5G5R5PC) ? 7 : 0, 0); SendDlgItemMessage (hDlg, IDC_RTG_24BIT, CB_SETCURSEL, - (workprefs.picasso96_modeflags & RGBFF_R8G8B8) ? 1 : - (workprefs.picasso96_modeflags & RGBFF_B8G8R8) ? 2 : 0, 0); + (manybits (workprefs.picasso96_modeflags, RGBFF_R8G8B8 | RGBFF_B8G8R8)) ? 1 : + (workprefs.picasso96_modeflags & RGBFF_R8G8B8) ? 2 : + (workprefs.picasso96_modeflags & RGBFF_B8G8R8) ? 3 : 0, 0); SendDlgItemMessage (hDlg, IDC_RTG_32BIT, CB_SETCURSEL, - (workprefs.picasso96_modeflags & RGBFF_A8R8G8B8) ? 1 : - (workprefs.picasso96_modeflags & RGBFF_A8B8G8R8) ? 2 : - (workprefs.picasso96_modeflags & RGBFF_R8G8B8A8) ? 3 : - (workprefs.picasso96_modeflags & RGBFF_B8G8R8A8) ? 4 : 0, 0); + (manybits (workprefs.picasso96_modeflags, RGBFF_A8R8G8B8 | RGBFF_A8B8G8R8 | RGBFF_R8G8B8A8 | RGBFF_B8G8R8A8)) ? 1 : + (workprefs.picasso96_modeflags & RGBFF_A8R8G8B8) ? 2 : + (workprefs.picasso96_modeflags & RGBFF_A8B8G8R8) ? 3 : + (workprefs.picasso96_modeflags & RGBFF_R8G8B8A8) ? 4 : + (workprefs.picasso96_modeflags & RGBFF_B8G8R8A8) ? 5 : 0, 0); if (workprefs.win32_rtgvblankrate <= 0 || workprefs.win32_rtgvblankrate == 50 || workprefs.win32_rtgvblankrate == 60 || @@ -5720,11 +5737,13 @@ static INT_PTR CALLBACK MemoryDlgProc (HWND hDlg, UINT msg, WPARAM wParam, LPARA case WM_INITDIALOG: pages[MEMORY_ID] = hDlg; currentpage = MEMORY_ID; + WIN32GUI_LoadUIString(IDS_ALL, tmp, sizeof tmp / sizeof (TCHAR)); SendDlgItemMessage (hDlg, IDC_RTG_8BIT, CB_RESETCONTENT, 0, 0); SendDlgItemMessage (hDlg, IDC_RTG_8BIT, CB_ADDSTRING, 0, (LPARAM)L"(8bit)"); SendDlgItemMessage (hDlg, IDC_RTG_8BIT, CB_ADDSTRING, 0, (LPARAM)L"8-bit (*)"); SendDlgItemMessage (hDlg, IDC_RTG_16BIT, CB_RESETCONTENT, 0, 0); SendDlgItemMessage (hDlg, IDC_RTG_16BIT, CB_ADDSTRING, 0, (LPARAM)L"(15/16bit)"); + SendDlgItemMessage (hDlg, IDC_RTG_16BIT, CB_ADDSTRING, 0, (LPARAM)tmp); SendDlgItemMessage (hDlg, IDC_RTG_16BIT, CB_ADDSTRING, 0, (LPARAM)L"R5G6B5PC (*)"); SendDlgItemMessage (hDlg, IDC_RTG_16BIT, CB_ADDSTRING, 0, (LPARAM)L"R5G5B5PC"); SendDlgItemMessage (hDlg, IDC_RTG_16BIT, CB_ADDSTRING, 0, (LPARAM)L"R5G6B5"); @@ -5733,10 +5752,12 @@ static INT_PTR CALLBACK MemoryDlgProc (HWND hDlg, UINT msg, WPARAM wParam, LPARA SendDlgItemMessage (hDlg, IDC_RTG_16BIT, CB_ADDSTRING, 0, (LPARAM)L"B5G5R5PC"); SendDlgItemMessage (hDlg, IDC_RTG_24BIT, CB_RESETCONTENT, 0, 0); SendDlgItemMessage (hDlg, IDC_RTG_24BIT, CB_ADDSTRING, 0, (LPARAM)L"(24bit)"); + SendDlgItemMessage (hDlg, IDC_RTG_24BIT, CB_ADDSTRING, 0, (LPARAM)tmp); SendDlgItemMessage (hDlg, IDC_RTG_24BIT, CB_ADDSTRING, 0, (LPARAM)L"R8G8B8"); SendDlgItemMessage (hDlg, IDC_RTG_24BIT, CB_ADDSTRING, 0, (LPARAM)L"B8G8R8"); SendDlgItemMessage (hDlg, IDC_RTG_32BIT, CB_RESETCONTENT, 0, 0); SendDlgItemMessage (hDlg, IDC_RTG_32BIT, CB_ADDSTRING, 0, (LPARAM)L"(32bit)"); + SendDlgItemMessage (hDlg, IDC_RTG_32BIT, CB_ADDSTRING, 0, (LPARAM)tmp); SendDlgItemMessage (hDlg, IDC_RTG_32BIT, CB_ADDSTRING, 0, (LPARAM)L"A8R8G8B8"); SendDlgItemMessage (hDlg, IDC_RTG_32BIT, CB_ADDSTRING, 0, (LPARAM)L"A8B8G8R8"); SendDlgItemMessage (hDlg, IDC_RTG_32BIT, CB_ADDSTRING, 0, (LPARAM)L"R8G8B8A8"); @@ -5847,16 +5868,18 @@ static INT_PTR CALLBACK MemoryDlgProc (HWND hDlg, UINT msg, WPARAM wParam, LPARA if (v != CB_ERR) { mask &= ~(RGBFF_R5G6B5PC | RGBFF_R5G5B5PC | RGBFF_R5G6B5 | RGBFF_R5G5B5 | RGBFF_B5G6R5PC | RGBFF_B5G5R5PC); if (v == 1) - mask |= RGBFF_R5G6B5PC; + mask |= RGBFF_R5G6B5PC | RGBFF_R5G6B5PC | RGBFF_R5G5B5PC | RGBFF_R5G6B5 | RGBFF_R5G5B5 | RGBFF_B5G6R5PC | RGBFF_B5G5R5PC; if (v == 2) - mask |= RGBFF_R5G5B5PC; + mask |= RGBFF_R5G6B5PC; if (v == 3) - mask |= RGBFF_R5G6B5; + mask |= RGBFF_R5G5B5PC; if (v == 4) - mask |= RGBFF_R5G5B5; + mask |= RGBFF_R5G6B5; if (v == 5) - mask |= RGBFF_B5G6R5PC; + mask |= RGBFF_R5G5B5; if (v == 6) + mask |= RGBFF_B5G6R5PC; + if (v == 7) mask |= RGBFF_B5G5R5PC; } break; @@ -5865,8 +5888,10 @@ static INT_PTR CALLBACK MemoryDlgProc (HWND hDlg, UINT msg, WPARAM wParam, LPARA if (v != CB_ERR) { mask &= ~(RGBFF_R8G8B8 | RGBFF_B8G8R8); if (v == 1) - mask |= RGBFF_R8G8B8; + mask |= RGBFF_R8G8B8 | RGBFF_B8G8R8; if (v == 2) + mask |= RGBFF_R8G8B8; + if (v == 3) mask |= RGBFF_B8G8R8; } break; @@ -5875,12 +5900,14 @@ static INT_PTR CALLBACK MemoryDlgProc (HWND hDlg, UINT msg, WPARAM wParam, LPARA if (v != CB_ERR) { mask &= ~(RGBFF_A8R8G8B8 | RGBFF_A8B8G8R8 | RGBFF_R8G8B8A8 | RGBFF_B8G8R8A8); if (v == 1) - mask |= RGBFF_A8R8G8B8; + mask |= RGBFF_A8R8G8B8 | RGBFF_A8B8G8R8 | RGBFF_R8G8B8A8 | RGBFF_B8G8R8A8; if (v == 2) - mask |= RGBFF_A8B8G8R8; + mask |= RGBFF_A8R8G8B8; if (v == 3) - mask |= RGBFF_R8G8B8A8; + mask |= RGBFF_A8B8G8R8; if (v == 4) + mask |= RGBFF_R8G8B8A8; + if (v == 5) mask |= RGBFF_B8G8R8A8; } break; @@ -7498,23 +7525,33 @@ static void sethfdostype (HWND hDlg, int idx) static void hardfile_testrdb (HWND hDlg, struct hfdlg_vals *hdf) { void *f = zfile_fopen (hdf->filename, L"rb", ZFD_NORMAL); - uae_u8 tmp[8] = { 0 }; + uae_u8 tmp[8]; + int i; + if (!f) return; - zfile_fread (tmp, 1, sizeof (tmp), f); - zfile_fclose (f); - if (!memcmp (tmp + 2, "CIS", 3)) - hdf->controller = HD_CONTROLLER_PCMCIA_SRAM; - if (!memcmp (tmp, "RDSK\0\0\0", 7)) { - hdf->sectors = 0; - hdf->surfaces = 0; - hdf->reserved = 0; - hdf->fsfilename[0] = 0; - hdf->bootpri = 0; - hdf->autoboot = 1; - hdf->donotmount = 0; - hdf->devicename[0] = 0; + for (i = 0; i < 16; i++) { + zfile_fseek (f, i * 512, SEEK_SET); + memset (tmp, 0, sizeof tmp); + zfile_fread (tmp, 1, sizeof tmp, f); + if (i == 0 && !memcmp (tmp + 2, "CIS", 3)) { + hdf->controller = HD_CONTROLLER_PCMCIA_SRAM; + break; + } + if (!memcmp (tmp, "RDSK\0\0\0", 7) || (tmp[0] == 0x53 && tmp[1] == 0x10 && tmp[2] == 0x9b && tmp[3] == 0x13 && tmp[4] == 0 && tmp[5] == 0)) { + // RDSK or ADIDE "encoded" RDSK + hdf->sectors = 0; + hdf->surfaces = 0; + hdf->reserved = 0; + hdf->fsfilename[0] = 0; + hdf->bootpri = 0; + hdf->autoboot = 1; + hdf->donotmount = 0; + hdf->devicename[0] = 0; + break; + } } + zfile_fclose (f); sethardfile (hDlg); } @@ -7533,8 +7570,14 @@ static void updatehdfinfo (HWND hDlg, int force) hfd.readonly = 1; hfd.blocksize = 512; if (hdf_open (&hfd, current_hfdlg.filename)) { - hdf_read (&hfd, id, 0, 512); - bsize = hfd.virtsize; + for (i = 0; i < 16; i++) { + hdf_read (&hfd, id, i * 512, 512); + bsize = hfd.virtsize; + if (!memcmp (id, "RDSK", 4)) + break; + } + if (i == 16) + hdf_read (&hfd, id, 0, 512); hdf_close (&hfd); } } diff --git a/od-win32/winuaechangelog.txt b/od-win32/winuaechangelog.txt index f4885892..dd1a71ae 100644 --- a/od-win32/winuaechangelog.txt +++ b/od-win32/winuaechangelog.txt @@ -1,4 +1,26 @@ +Beta 26: + +- added transparent support for ICD AdIDE "bit swapped" disks and + hardfiles. Each 16-bit data word has bits swapped, bit 0 = 15, + bit 1 = 0, bit 2 = 14, bit 3 = 1 and so on (reason is most likely + PCB cost) Listed as "CPRM" in "Add Harddrive" list because first + (which is normally hidden) block starts with ascii string "CPRM" +- wrong sound device was selected if configuration was loaded and + DS, OpenAL or PortAudio had 100% identical device names +- bsdsocket not too common connection issue fixed (b15) +- sound card index in config file > number of sound devices = very + slow emulation +- added "All" option to RTG RGB format selection menus (make sure + "ENV:Picasso96/ShowModes" contains "All" or only single format per + color depth is available in screen mode dialogs) +- autoscale: show blank display using previous scaling instead of + defaulting to non-scaling +- NTSC vertical centering fixed in scaled modes +- D3D and OGL mode was not properly closed when switching to + windowed/fullwindow RTG mode (old graphics was visible depending + on screen/scaling etc..) + Beta 25: - Picasso96 crash in some specific cases when 8bit->16/32 or 16->32 @@ -11,7 +33,7 @@ Beta 25: - input was disabled when in "mouse driver" mode and focus was lost and regained - DXSDK update, D3D support requires March 2009 DX runtime or newer -- D3D fullscreen flickering fixed +- D3D fullscreen "border" flickering fixed Beta 24: