]> git.unchartedbackwaters.co.uk Git - francis/winuae.git/commitdiff
Custom ROM config support.
authorToni Wilen <twilen@winuae.net>
Sun, 27 Jan 2019 15:14:07 +0000 (17:14 +0200)
committerToni Wilen <twilen@winuae.net>
Sun, 27 Jan 2019 15:14:07 +0000 (17:14 +0200)
cfgfile.cpp
expansion.cpp
include/memory.h
include/options.h
od-win32/win32gui.cpp

index 9ca3b322f4d15519b9a437e903db11ad588ec82d..d69f5fbfee3d3acf272ceb69d5319d8be362d4e2 100644 (file)
@@ -1515,6 +1515,59 @@ static void cfgfile_write_board_rom(struct uae_prefs *prefs, struct zfile *f, st
        }
 }
 
+static bool cfgfile_readromboard(const TCHAR *option, const TCHAR *value, struct romboard *rbp)
+{
+       TCHAR tmp1[MAX_DPATH];
+       int v;
+       for (int i = 0; i < MAX_ROM_BOARDS; i++) {
+               struct romboard *rb = &rbp[i];
+               if (i > 0)
+                       _stprintf(tmp1, _T("romboard%d_options"), i + 1);
+               else
+                       _tcscpy(tmp1, _T("romboard_options"));
+               if (!_tcsicmp(option, tmp1)) {
+                       TCHAR *endptr;
+                       TCHAR *s, *s1, *s2;
+                       s1 = cfgfile_option_get(value, _T("start"));
+                       s2 = cfgfile_option_get(value, _T("end"));
+                       rb->size = 0;
+                       if (s1 && s2) {
+                               rb->start_address = _tcstol(s1, &endptr, 16);
+                               rb->end_address = _tcstol(s2, &endptr, 16);
+                               if (rb->end_address && rb->end_address > rb->start_address) {
+                                       rb->size = (rb->end_address - rb->start_address + 65535) & ~65535;
+                               }
+                       }
+                       xfree(s1);
+                       xfree(s2);
+                       s1 = cfgfile_option_get(value, _T("file"));
+                       if (s1) {
+                               TCHAR *p = cfgfile_unescape(s1, NULL);
+                               _tcscpy(rb->lf.loadfile, p);
+                               xfree(p);
+                       }
+                       xfree(s1);
+                       s1 = cfgfile_option_get(value, _T("offset"));
+                       if (s1) {
+                               rb->lf.loadoffset = _tcstol(s1, &endptr, 16);
+                       }
+                       xfree(s1);
+                       s1 = cfgfile_option_get(value, _T("fileoffset"));
+                       if (s1) {
+                               rb->lf.fileoffset = _tcstol(s1, &endptr, 16);
+                       }
+                       xfree(s1);
+                       s1 = cfgfile_option_get(value, _T("filesize"));
+                       if (s1) {
+                               rb->lf.filesize = _tcstol(s1, &endptr, 16);
+                       }
+                       xfree(s1);
+                       return true;
+               }
+       }
+       return false;
+}
+
 static bool cfgfile_readramboard(const TCHAR *option, const TCHAR *value, const TCHAR *name, struct ramboard *rbp)
 {
        TCHAR tmp1[MAX_DPATH];
@@ -1598,23 +1651,23 @@ static bool cfgfile_readramboard(const TCHAR *option, const TCHAR *value, const
                        s1 = cfgfile_option_get(value, _T("file"));
                        if (s1) {
                                TCHAR *p = cfgfile_unescape(s1, NULL);
-                               _tcscpy(rb->loadfile, p);
+                               _tcscpy(rb->lf.loadfile, p);
                                xfree(p);
                        }
                        xfree(s1);
                        s1 = cfgfile_option_get(value, _T("offset"));
                        if (s1) {
-                               rb->loadoffset = _tcstol(s1, &endptr, 16);
+                               rb->lf.loadoffset = _tcstol(s1, &endptr, 16);
                        }
                        xfree(s1);
                        s1 = cfgfile_option_get(value, _T("fileoffset"));
                        if (s1) {
-                               rb->fileoffset = _tcstol(s1, &endptr, 16);
+                               rb->lf.fileoffset = _tcstol(s1, &endptr, 16);
                        }
                        xfree(s1);
                        s1 = cfgfile_option_get(value, _T("filesize"));
                        if (s1) {
-                               rb->filesize = _tcstol(s1, &endptr, 16);
+                               rb->lf.filesize = _tcstol(s1, &endptr, 16);
                        }
                        xfree(s1);
                        rb->readonly = cfgfile_option_find(value, _T("read-only"));
@@ -1624,6 +1677,35 @@ static bool cfgfile_readramboard(const TCHAR *option, const TCHAR *value, const
        return false;
 }
 
+static void cfgfile_writeromboard(struct uae_prefs *prefs, struct zfile *f, int num, struct romboard *rb)
+{
+       TCHAR tmp1[MAX_DPATH], tmp2[MAX_DPATH];
+       if (!rb->end_address)
+               return;
+       if (num > 0)
+               _stprintf(tmp1, _T("romboard%d_options"), num + 1);
+       else
+               _tcscpy(tmp1, _T("romboard_options"));
+       tmp2[0] = 0;
+       TCHAR *p = tmp2;
+       _stprintf(p, _T("start=%08x,end=%08x"), rb->start_address, rb->end_address);
+       p += _tcslen(p);
+       if (rb->lf.loadfile[0]) {
+               _tcscat(p, _T(","));
+               p += _tcslen(p);
+               TCHAR *path = cfgfile_escape(rb->lf.loadfile, NULL, true);
+               if (rb->lf.loadoffset || rb->lf.fileoffset || rb->lf.filesize) {
+                       _stprintf(p, _T("offset=%u,fileoffset=%u,filesize=%u,"), rb->lf.loadoffset, rb->lf.fileoffset, rb->lf.filesize);
+                       p += _tcslen(p);
+               }
+               _stprintf(p, _T("file=%s"), path);
+               xfree(path);
+       }
+       if (tmp2[0]) {
+               cfgfile_write(f, tmp1, tmp2);
+       }
+}
+
 static void cfgfile_writeramboard(struct uae_prefs *prefs, struct zfile *f, const TCHAR *name, int num, struct ramboard *rb)
 {
        TCHAR tmp1[MAX_DPATH], tmp2[MAX_DPATH];
@@ -1670,11 +1752,13 @@ static void cfgfile_writeramboard(struct uae_prefs *prefs, struct zfile *f, cons
                _stprintf(p, _T(",write_address=%08x"), rb->write_address);
                p += _tcslen(p);
        }
-       if (rb->loadfile[0]) {
-               if (tmp2[0])
+       if (rb->lf.loadfile[0]) {
+               if (tmp2[0]) {
                        _tcscat(p, _T(","));
-               TCHAR *path = cfgfile_escape(rb->loadfile, NULL, true);
-               _stprintf(p, _T("offset=%u,fileoffset=%u,filesize=%u,file=%s"), rb->loadoffset, rb->fileoffset, rb->filesize, path);
+                       p += _tcslen(p);
+               }
+               TCHAR *path = cfgfile_escape(rb->lf.loadfile, NULL, true);
+               _stprintf(p, _T("offset=%u,fileoffset=%u,filesize=%u,file=%s"), rb->lf.loadoffset, rb->lf.fileoffset, rb->lf.filesize, path);
                xfree(path);
        }
        if (rb->readonly) {
@@ -1763,6 +1847,10 @@ void cfgfile_save_options (struct zfile *f, struct uae_prefs *p, int type)
        if (p->romextident[0])
                cfgfile_write_str (f, _T("kickstart_ext_rom="), p->romextident);
 
+       for (int i = 0; i < MAX_ROM_BOARDS; i++) {
+               cfgfile_writeromboard(p, f, i, &p->romboards[i]);
+       }
+
        for (int i = 0; i < MAX_EXPANSION_BOARDS; i++) {
                cfgfile_write_board_rom(p, f, &p->path_rom, &p->expansionboard[i]);
        }
@@ -5422,6 +5510,10 @@ static int cfgfile_parse_hardware (struct uae_prefs *p, const TCHAR *option, TCH
                return 1;
        }
 
+       if (cfgfile_readromboard(option, value, &p->romboards[0])) {
+               return 1;
+       }
+
        if (cfgfile_readramboard(option, value, _T("fastmem"), &p->fastmem[0])) {
                return 1;
        }
index fde87c3693958cddc6ff57752eb9f0ce18ba92fd..7f55645a8e3effbe2b1dc8c58072b9d1b4ee0b9e 100644 (file)
@@ -980,6 +980,47 @@ static bool expamem_init_cd32fmv (struct autoconfig_info *aci)
 
 /* ********************************************************** */
 
+MEMORY_ARRAY_FUNCTIONS(romboardmem, 0);
+MEMORY_ARRAY_FUNCTIONS(romboardmem, 1);
+MEMORY_ARRAY_FUNCTIONS(romboardmem, 2);
+MEMORY_ARRAY_FUNCTIONS(romboardmem, 3);
+
+static void REGPARAM2 empty_put(uaecptr addr, uae_u32 v)
+{
+}
+
+addrbank romboardmem_bank[MAX_ROM_BOARDS] =
+{
+       {
+               romboardmem0_lget, romboardmem0_wget, romboardmem0_bget,
+               empty_put, empty_put, empty_put,
+               romboardmem0_xlate, romboardmem0_check, NULL, _T("*"), _T("ROM board"),
+               romboardmem0_lget, romboardmem0_wget,
+               ABFLAG_ROM | ABFLAG_THREADSAFE | ABFLAG_CACHE_ENABLE_ALL | ABFLAG_DIRECTACCESS, 0, 0
+       },
+       {
+               romboardmem1_lget, romboardmem1_wget, romboardmem1_bget,
+               empty_put, empty_put, empty_put,
+               romboardmem1_xlate, romboardmem1_check, NULL, _T("*"), _T("ROM board"),
+               romboardmem1_lget, romboardmem1_wget,
+               ABFLAG_ROM | ABFLAG_THREADSAFE | ABFLAG_CACHE_ENABLE_ALL | ABFLAG_DIRECTACCESS, 0, 0
+       },
+       {
+               romboardmem2_lget, romboardmem2_wget, romboardmem2_bget,
+               empty_put, empty_put, empty_put,
+               romboardmem2_xlate, romboardmem2_check, NULL, _T("*"), _T("ROM board"),
+               romboardmem2_lget, romboardmem2_wget,
+               ABFLAG_ROM | ABFLAG_THREADSAFE | ABFLAG_CACHE_ENABLE_ALL | ABFLAG_DIRECTACCESS, 0, 0
+       },
+       {
+               romboardmem3_lget, romboardmem3_wget, romboardmem3_bget,
+               empty_put, empty_put, empty_put,
+               romboardmem3_xlate, romboardmem3_check, NULL, _T("*"), _T("ROM board"),
+               romboardmem3_lget, romboardmem3_wget,
+               ABFLAG_ROM | ABFLAG_THREADSAFE | ABFLAG_CACHE_ENABLE_ALL | ABFLAG_DIRECTACCESS, 0, 0
+       }
+};
+
 /*
 *  Fast Memory
 */
@@ -1477,32 +1518,36 @@ static bool expamem_init_uaeboard(struct autoconfig_info *aci)
        return true;
 }
 
-static void REGPARAM2 empty_put(uaecptr addr, uae_u32 value)
+static void loadboardfile(addrbank *ab, struct boardloadfile *lf)
 {
+       if (!ab->baseaddr)
+               return;
+       if (!lf->loadfile[0])
+               return;
+       struct zfile *zf = zfile_fopen(lf->loadfile, _T("rb"));
+       if (zf) {
+               int size = lf->filesize;
+               if (!size) {
+                       size = ab->allocated_size;
+               }
+               else if (lf->loadoffset + size > ab->allocated_size)
+                       size = ab->allocated_size - lf->loadoffset;
+               if (size > 0) {
+                       int total = zfile_fread(ab->baseaddr + lf->loadoffset, 1, size, zf);
+                       write_log(_T("Expansion file '%s': load %u bytes, offset %u, start addr %08x\n"),
+                               lf->loadfile, total, lf->loadoffset, ab->start + lf->loadoffset);
+               }
+               zfile_fclose(zf);
+       } else {
+               write_log(_T("Couldn't open expansion file '%s'\n"), lf->loadfile);
+       }
 }
 
 static void initramboard(addrbank *ab, struct ramboard *rb)
 {
        if (!ab->baseaddr)
                return;
-       if (rb->loadfile[0]) {
-               struct zfile *zf = zfile_fopen(rb->loadfile, _T("rb"));
-               if (zf) {
-                       int size = rb->filesize;
-                       if (!size) {
-                               size = ab->allocated_size;
-                       } else if (rb->loadoffset + size > ab->allocated_size)
-                               size = ab->allocated_size - rb->loadoffset;
-                       if (size > 0) {
-                               int total = zfile_fread(ab->baseaddr + rb->loadoffset, 1, size, zf);
-                               write_log(_T("Expansion file '%s': load %u bytes, offset %u, start addr %08x\n"),
-                                       rb->loadfile, total, rb->loadoffset, ab->start + rb->loadoffset);
-                       }
-                       zfile_fclose(zf);
-               } else {
-                       write_log(_T("Couldn't open expansion file '%s'\n"), rb->loadfile);
-               }
-       }
+       loadboardfile(ab, &rb->lf);
        if (rb->readonly) {
                ab->lput = empty_put;
                ab->wput = empty_put;
@@ -2215,6 +2260,23 @@ static void allocate_expamem (void)
                currprefs.z3fastmem[i].size = changed_prefs.z3fastmem[i].size;
        }
 
+       for (int i = 0; i < MAX_ROM_BOARDS; i++) {
+               struct romboard *rb = &currprefs.romboards[i];
+               memcpy(rb, &changed_prefs.romboards[i], sizeof(struct romboard));
+               if (romboardmem_bank[i].reserved_size != rb->size) {
+                       mapped_free(&romboardmem_bank[i]);
+                       romboardmem_bank[i].reserved_size = rb->size;
+                       romboardmem_bank[i].mask = romboardmem_bank[i].reserved_size - 1;
+                       romboardmem_bank[i].start = rb->start_address;
+                       if (romboardmem_bank[i].reserved_size && romboardmem_bank[i].start != 0xffffffff) {
+                               mapped_malloc(&romboardmem_bank[i]);
+                               if (romboardmem_bank[i].baseaddr == 0) {
+                                       write_log(_T("Out of memory for romboard card.\n"));
+                               }
+                       }
+               }
+       }
+
        z3chipmem_bank.start = Z3BASE_UAE;
 
        if (currprefs.mbresmem_high_size >= 128 * 1024 * 1024)
@@ -3751,6 +3813,13 @@ void expansion_map(void)
                        initramboard(&z3fastmem_bank[i], rb);
                }
        }
+       for (int i = 0; i < MAX_ROM_BOARDS; i++) {
+               struct romboard *rb = &currprefs.romboards[i];
+               if (rb->size) {
+                       loadboardfile(&romboardmem_bank[i], &rb->lf);
+                       map_banks(&romboardmem_bank[i], rb->start_address >> 16, rb->size >> 16, 0);
+               }
+       }
        if (currprefs.z3chipmem_size) {
                map_banks_z3(&z3chipmem_bank, z3chipmem_bank.start >> 16, currprefs.z3chipmem_size >> 16);
        }
index a8b07edcfbf25b75248053435e49b59432e94013..0a78b2d76ccc50ddcd2883f6990660344fb08c51 100644 (file)
@@ -436,6 +436,7 @@ extern addrbank extendedkickmem_bank;
 extern addrbank extendedkickmem2_bank;
 extern addrbank custmem1_bank;
 extern addrbank custmem2_bank;
+extern addrbank romboardmem_bank[MAX_ROM_BOARDS];
 
 extern void rtarea_init(void);
 extern void rtarea_free(void);
index f55618d37aa013af79ec6c0a3d1b8324898a4830..c33372c0190d51fde3bb5a317db37d28dab1b158 100644 (file)
@@ -407,6 +407,20 @@ struct rtgboardconfig
        int device_order;
        int monitor_id;
 };
+struct boardloadfile
+{
+       uae_u32 loadoffset;
+       uae_u32 fileoffset, filesize;
+       TCHAR loadfile[MAX_DPATH];
+};
+#define MAX_ROM_BOARDS 4
+struct romboard
+{
+       uae_u32 size;
+       uae_u32 start_address;
+       uae_u32 end_address;
+       struct boardloadfile lf;
+};
 #define MAX_RAM_BOARDS 4
 struct ramboard
 {
@@ -422,9 +436,7 @@ struct ramboard
        uae_u32 end_address;
        uae_u32 write_address;
        bool readonly;
-       uae_u32 loadoffset;
-       uae_u32 fileoffset, filesize;
-       TCHAR loadfile[MAX_DPATH];
+       struct boardloadfile lf;
 };
 struct expansion_params
 {
@@ -718,6 +730,7 @@ struct uae_prefs {
        uae_u32 z3autoconfig_start;
        struct ramboard z3fastmem[MAX_RAM_BOARDS];
        struct ramboard fastmem[MAX_RAM_BOARDS];
+       struct romboard romboards[MAX_ROM_BOARDS];
        uae_u32 z3chipmem_size;
        uae_u32 z3chipmem_start;
        uae_u32 chipmem_size;
index 9d61d901093e614f1ab5823fab1adadeade7dbba..be8e6fd892a54436971caddb0c166c7040e2cacd 100644 (file)
@@ -3184,6 +3184,25 @@ int DiskSelection_2 (HWND hDlg, WPARAM wParam, int flag, struct uae_prefs *prefs
                        _tcscpy (workprefs.romextfile, full_path);
                        fullpath (workprefs.romextfile, MAX_DPATH);
                        break;
+               case IDC_CUSTOMROMFILE:
+               {
+                       int v = SendDlgItemMessage(hDlg, IDC_CUSTOMROMSELECT, CB_GETCURSEL, 0, 0);
+                       if (v >= 0 && v < MAX_ROM_BOARDS) {
+                               struct romboard *rb = &workprefs.romboards[v];
+                               _tcscpy(rb->lf.loadfile, full_path);
+                               fullpath(rb->lf.loadfile, MAX_DPATH);
+                               if (rb->start_address) {
+                                       struct zfile *zf = zfile_fopen(rb->lf.loadfile, _T("rb"));
+                                       if (zf) {
+                                               rb->end_address = rb->start_address + zfile_size(zf);
+                                               rb->end_address = ((rb->end_address + 65535) & ~65535) - 1;
+                                               rb->size = rb->end_address - rb->start_address + 1;
+                                               zfile_fclose(zf);
+                                       }
+                               }
+                       }
+                       break;
+               }
                case IDC_FLASHFILE:
                        _tcscpy (workprefs.flashfile, full_path);
                        fullpath(workprefs.flashfile, MAX_DPATH);
@@ -11471,19 +11490,20 @@ static INT_PTR CALLBACK MemoryDlgProc (HWND hDlg, UINT msg, WPARAM wParam, LPARA
        return FALSE;
 }
 
-static void values_to_kickstartdlg (HWND hDlg)
+static int customromselectnum;
+static void values_to_kickstartdlg(HWND hDlg)
 {
        UAEREG *fkey;
 
-       fkey = regcreatetree (NULL, _T("DetectedROMs"));
+       fkey = regcreatetree(NULL, _T("DetectedROMs"));
 
        load_keyring(&workprefs, NULL);
 
-       addromfiles (fkey, hDlg, IDC_ROMFILE, workprefs.romfile,
+       addromfiles(fkey, hDlg, IDC_ROMFILE, workprefs.romfile,
                ROMTYPE_KICK | ROMTYPE_KICKCD32, 0);
-       addromfiles (fkey, hDlg, IDC_ROMFILE2, workprefs.romextfile,
+       addromfiles(fkey, hDlg, IDC_ROMFILE2, workprefs.romextfile,
                ROMTYPE_EXTCD32 | ROMTYPE_EXTCDTV | ROMTYPE_ARCADIABIOS | ROMTYPE_ALG, 0);
-       addromfiles (fkey, hDlg, IDC_CARTFILE, workprefs.cartfile,
+       addromfiles(fkey, hDlg, IDC_CARTFILE, workprefs.cartfile,
                ROMTYPE_FREEZER | ROMTYPE_ARCADIAGAME | ROMTYPE_CD32CART, 0);
 
        regclosetree(fkey);
@@ -11495,11 +11515,45 @@ static void values_to_kickstartdlg (HWND hDlg)
 
        if (workprefs.boot_rom == 1) {
                SendDlgItemMessage(hDlg, IDC_UAEBOARD_TYPE, CB_SETCURSEL, 0, 0);
-       } else {
+       }
+       else {
                SendDlgItemMessage(hDlg, IDC_UAEBOARD_TYPE, CB_SETCURSEL, workprefs.uaeboard + 1, 0);
        }
 }
 
+static void values_to_kickstartdlg2(HWND hDlg)
+{
+       int v = SendDlgItemMessage(hDlg, IDC_CUSTOMROMSELECT, CB_GETCURSEL, 0, 0);
+       if (v >= 0 && v < MAX_ROM_BOARDS) {
+               customromselectnum = v;
+       }
+       SendDlgItemMessage(hDlg, IDC_CUSTOMROMSELECT, CB_RESETCONTENT, 0, 0);
+       for (int i = 0; i < MAX_ROM_BOARDS; i++) {
+               TCHAR tmp[MAX_DPATH];
+               struct romboard *rb = &workprefs.romboards[i];
+               _stprintf(tmp, _T("ROM #%d"), i + 1);
+               if (rb->size)
+                       _stprintf(tmp + _tcslen(tmp), _T(" %08x - %08x"), rb->start_address, rb->end_address - 1);
+               SendDlgItemMessage(hDlg, IDC_CUSTOMROMSELECT, CB_ADDSTRING, 0, (LPARAM)tmp);
+       }
+       if (customromselectnum >= 0 && customromselectnum < MAX_ROM_BOARDS) {
+               struct romboard *rb = &workprefs.romboards[customromselectnum];
+               TCHAR tmp[100];
+               _stprintf(tmp, _T("%08x"), rb->start_address);
+               if (!rb->end_address && !rb->start_address) {
+                       tmp[0] = 0;
+               }
+               SetDlgItemText(hDlg, IDC_ROM_ADDRESS, tmp);
+               _stprintf(tmp, _T("%08x"), rb->end_address);
+               if (!rb->end_address && !rb->start_address) {
+                       tmp[0] = 0;
+               }
+               SetDlgItemText(hDlg, IDC_ROM_ADDRESS2, tmp);
+               SetDlgItemText(hDlg, IDC_CUSTOMROMFILE, rb->lf.loadfile);
+               SendDlgItemMessage(hDlg, IDC_CUSTOMROMSELECT, CB_SETCURSEL, customromselectnum, 0);
+       }
+}
+
 static void values_from_kickstartdlg(HWND hDlg)
 {
        getromfile(hDlg, IDC_ROMFILE, workprefs.romfile, sizeof(workprefs.romfile) / sizeof(TCHAR));
@@ -11517,6 +11571,26 @@ static void values_from_kickstartdlg(HWND hDlg)
        }
 }
 
+static void values_from_kickstartdlg2(HWND hDlg)
+{
+       int v = SendDlgItemMessage(hDlg, IDC_CUSTOMROMSELECT, CB_GETCURSEL, 0, 0);
+       if (v >= 0 && v < MAX_ROM_BOARDS) {
+               struct romboard *rb = &workprefs.romboards[v];
+               TCHAR tmp[100];
+               TCHAR *endptr;
+               GetDlgItemText(hDlg, IDC_ROM_ADDRESS, tmp, sizeof tmp / sizeof(TCHAR));
+               rb->start_address =_tcstoul(tmp, &endptr, 16);
+               rb->start_address &= ~65535;
+               GetDlgItemText(hDlg, IDC_ROM_ADDRESS2, tmp, sizeof tmp / sizeof(TCHAR));
+               rb->end_address = _tcstoul(tmp, &endptr, 16);
+               rb->end_address = ((rb->end_address - 1) & ~65535) | 0xffff;
+               rb->size = 0;
+               if (rb->end_address > rb->start_address) {
+                       rb->size = (rb->end_address - rb->start_address + 65535) & ~65535;
+               }
+       }
+}
+
 static void init_kickstart (HWND hDlg)
 {
        ew (hDlg, IDC_MAPROM, workprefs.cpuboard_type == 0);
@@ -11555,23 +11629,27 @@ static void kickstartfilebuttons (HWND hDlg, WPARAM wParam, TCHAR *path)
        {
        case IDC_KICKCHOOSER:
                DiskSelection(hDlg, IDC_ROMFILE, 6, &workprefs, NULL, path);
-               values_to_kickstartdlg (hDlg);
+               values_to_kickstartdlg(hDlg);
                break;
        case IDC_ROMCHOOSER2:
                DiskSelection(hDlg, IDC_ROMFILE2, 6, &workprefs, NULL, path);
-               values_to_kickstartdlg (hDlg);
+               values_to_kickstartdlg(hDlg);
+               break;
+       case IDC_CUSTOMROMCHOOSER:
+               DiskSelection(hDlg, IDC_CUSTOMROMFILE, 6, &workprefs, NULL, path);
+               values_to_kickstartdlg2(hDlg);
                break;
        case IDC_FLASHCHOOSER:
                DiskSelection(hDlg, IDC_FLASHFILE, 11, &workprefs, NULL, path);
-               values_to_kickstartdlg (hDlg);
+               values_to_kickstartdlg(hDlg);
                break;
        case IDC_RTCCHOOSER:
                DiskSelection(hDlg, IDC_RTCFILE, 19, &workprefs, NULL, path);
-               values_to_kickstartdlg (hDlg);
+               values_to_kickstartdlg(hDlg);
                break;
        case IDC_CARTCHOOSER:
                DiskSelection(hDlg, IDC_CARTFILE, 6, &workprefs, NULL, path);
-               values_to_kickstartdlg (hDlg);
+               values_to_kickstartdlg(hDlg);
                break;
        }
 }
@@ -11590,7 +11668,8 @@ static INT_PTR CALLBACK KickstartDlgProc (HWND hDlg, UINT msg, WPARAM wParam, LP
                        pages[KICKSTART_ID] = hDlg;
                        currentpage = KICKSTART_ID;
                        init_kickstart (hDlg);
-                       values_to_kickstartdlg (hDlg);
+                       values_to_kickstartdlg(hDlg);
+                       values_to_kickstartdlg2(hDlg);
                        setmultiautocomplete (hDlg, ids);
                        setac (hDlg, IDC_FLASHFILE);
                        setac (hDlg, IDC_RTCFILE);
@@ -11617,14 +11696,25 @@ static INT_PTR CALLBACK KickstartDlgProc (HWND hDlg, UINT msg, WPARAM wParam, LP
                if (recursive > 0)
                        break;
                recursive++;
-               if (HIWORD (wParam) == CBN_SELCHANGE || HIWORD (wParam) == CBN_KILLFOCUS)  {
-                       switch (LOWORD (wParam))
+               if (HIWORD(wParam) == CBN_SELCHANGE || HIWORD(wParam) == CBN_KILLFOCUS) {
+                       switch (LOWORD(wParam))
                        {
                        case IDC_ROMFILE:
                        case IDC_ROMFILE2:
                        case IDC_CARTFILE:
                        case IDC_UAEBOARD_TYPE:
-                               values_from_kickstartdlg (hDlg);
+                               values_from_kickstartdlg(hDlg);
+                               break;
+                       case IDC_CUSTOMROMSELECT:
+                               values_to_kickstartdlg2(hDlg);
+                               break;
+                       }
+               } else if (HIWORD(wParam) == EN_CHANGE || HIWORD(wParam) == EN_KILLFOCUS) {
+                       switch (LOWORD(wParam))
+                       {
+                       case IDC_ROM_ADDRESS:
+                       case IDC_ROM_ADDRESS2:
+                               values_from_kickstartdlg2(hDlg);
                                break;
                        }
                }
@@ -12989,7 +13079,8 @@ static void values_to_sounddlg (HWND hDlg)
        CheckRadioButton (hDlg, IDC_SOUND0, IDC_SOUND2, which_button);
 
        CheckDlgButton (hDlg, IDC_SOUND_AUTO, workprefs.sound_auto);
-       CheckDlgButton (hDlg, IDC_SOUND_CDPAULAMIX, workprefs.sound_cdaudio);
+       CheckDlgButton(hDlg, IDC_SOUND_CDPAULAMIX, workprefs.sound_cdaudio);
+       CheckDlgButton(hDlg, IDC_SOUND_VOLCNT, workprefs.sound_volcnt);
 
        if (workprefs.sound_maxbsiz < SOUND_BUFFER_MULTIPLIER)
                workprefs.sound_maxbsiz = 0;
@@ -13072,7 +13163,8 @@ static void values_from_sounddlg (HWND hDlg)
                : ischecked (hDlg, IDC_SOUND1) ? 1 : 3);
 
        workprefs.sound_auto = ischecked (hDlg, IDC_SOUND_AUTO);
-       workprefs.sound_cdaudio = ischecked (hDlg, IDC_SOUND_CDPAULAMIX);
+       workprefs.sound_cdaudio = ischecked(hDlg, IDC_SOUND_CDPAULAMIX);
+       workprefs.sound_volcnt = ischecked(hDlg, IDC_SOUND_VOLCNT);
 
        idx = SendDlgItemMessage (hDlg, IDC_SOUNDSTEREO, CB_GETCURSEL, 0, 0);
        if (idx != CB_ERR)