archie: support for IDE, auto-save for CMOS.
This commit is contained in:
86
menu.cpp
86
menu.cpp
@@ -1222,8 +1222,7 @@ void HandleUI(void)
|
||||
OsdSetTitle(CoreName, OSD_ARROW_RIGHT | OSD_ARROW_LEFT);
|
||||
|
||||
m = 0;
|
||||
menumask = 0x3ff;
|
||||
OsdWrite(m++);
|
||||
menumask = 0xfff;
|
||||
|
||||
strcpy(s, " Floppy 0: ");
|
||||
strncat(s, get_image_name(0) ? get_image_name(0) : "* no disk *",27);
|
||||
@@ -1235,39 +1234,47 @@ void HandleUI(void)
|
||||
|
||||
OsdWrite(m++);
|
||||
|
||||
strcpy(s, " HDD 0: ");
|
||||
strncat(s, archie_get_hdd_name(0) ? archie_get_hdd_name(0) : "* no disk *", 27);
|
||||
OsdWrite(m++, s, menusub == 2);
|
||||
|
||||
strcpy(s, " HDD 1: ");
|
||||
strncat(s, archie_get_hdd_name(1) ? archie_get_hdd_name(1) : "* no disk *", 27);
|
||||
OsdWrite(m++, s, menusub == 3);
|
||||
|
||||
OsdWrite(m++);
|
||||
|
||||
strcpy(s, " OS ROM: ");
|
||||
strcat(s, archie_get_rom_name());
|
||||
OsdWrite(m++, s, menusub == 2);
|
||||
OsdWrite(m++, s, menusub == 4);
|
||||
|
||||
OsdWrite(m++);
|
||||
|
||||
strcpy(s, " Aspect ratio: ");
|
||||
strcat(s, archie_get_ar() ? "16:9" : "4:3");
|
||||
OsdWrite(m++, s, menusub == 3);
|
||||
OsdWrite(m++, s, menusub == 5);
|
||||
|
||||
strcpy(s, " Refresh rate: ");
|
||||
strcat(s, archie_get_60() ? "Variable" : "60Hz");
|
||||
OsdWrite(m++, s, menusub == 4);
|
||||
|
||||
OsdWrite(m++);
|
||||
OsdWrite(m++, s, menusub == 6);
|
||||
|
||||
sprintf(s, " Stereo mix: %s", config_stereo_msg[archie_get_amix()]);
|
||||
OsdWrite(m++, s, menusub == 5);
|
||||
OsdWrite(m++, s, menusub == 7);
|
||||
|
||||
strcpy(s, " 25MHz audio fix: ");
|
||||
strcat(s, archie_get_afix() ? "Enable" : "Disable");
|
||||
OsdWrite(m++, s, menusub == 6);
|
||||
OsdWrite(m++, s, menusub == 8);
|
||||
|
||||
OsdWrite(m++);
|
||||
|
||||
sprintf(s, " Swap joysticks: %s", user_io_get_joyswap() ? "Yes" : "No");
|
||||
OsdWrite(m++, s, menusub == 7);
|
||||
OsdWrite(m++, s, menusub == 9);
|
||||
sprintf(s, " Swap mouse btn 2/3: %s", archie_get_mswap() ? "Yes" : "No");
|
||||
OsdWrite(m++, s, menusub == 8);
|
||||
OsdWrite(m++, s, menusub == 10);
|
||||
|
||||
while(m<15) OsdWrite(m++);
|
||||
|
||||
OsdWrite(15, STD_EXIT, menusub == 9, 0);
|
||||
OsdWrite(15, STD_EXIT, menusub == 11, 0);
|
||||
menustate = MENU_ARCHIE_MAIN2;
|
||||
parentstate = MENU_ARCHIE_MAIN1;
|
||||
|
||||
@@ -1281,69 +1288,75 @@ void HandleUI(void)
|
||||
case MENU_ARCHIE_MAIN2:
|
||||
// menu key closes menu
|
||||
if (menu) menustate = MENU_NONE1;
|
||||
if (recent)
|
||||
if (recent && (menusub <= 3))
|
||||
{
|
||||
if (menusub <= 1)
|
||||
{
|
||||
fs_Options = SCANO_DIR | SCANO_UMOUNT;
|
||||
fs_MenuSelect = MENU_ARCHIE_MAIN_FILE_SELECTED;
|
||||
fs_MenuCancel = MENU_ARCHIE_MAIN1;
|
||||
strcpy(fs_pFileExt, "ADF");
|
||||
if (recent_init(500)) menustate = MENU_RECENT1;
|
||||
}
|
||||
fs_Options = SCANO_DIR | SCANO_UMOUNT;
|
||||
fs_MenuSelect = MENU_ARCHIE_MAIN_FILE_SELECTED;
|
||||
fs_MenuCancel = MENU_ARCHIE_MAIN1;
|
||||
strcpy(fs_pFileExt, (menusub <= 1) ? "ADF" : "HDF");
|
||||
if (recent_init((menusub <= 1) ? 500 : 501)) menustate = MENU_RECENT1;
|
||||
}
|
||||
|
||||
if (select || plus || minus)
|
||||
{
|
||||
switch (menusub) {
|
||||
switch (menusub)
|
||||
{
|
||||
case 0: // Floppy 0
|
||||
case 1: // Floppy 1
|
||||
if (select)
|
||||
{
|
||||
ioctl_index = 0;
|
||||
SelectFile(Selected_F[menusub], "ADF", SCANO_DIR | SCANO_UMOUNT, MENU_ARCHIE_MAIN_FILE_SELECTED, MENU_ARCHIE_MAIN1);
|
||||
SelectFile(Selected_S[menusub], "ADF", SCANO_DIR | SCANO_UMOUNT, MENU_ARCHIE_MAIN_FILE_SELECTED, MENU_ARCHIE_MAIN1);
|
||||
}
|
||||
break;
|
||||
|
||||
case 2: // Load ROM
|
||||
case 2: // HDD 0
|
||||
case 3: // HDD 1
|
||||
if (select)
|
||||
{
|
||||
ioctl_index = 1;
|
||||
SelectFile(Selected_S[menusub], "HDF", SCANO_DIR | SCANO_UMOUNT, MENU_ARCHIE_MAIN_FILE_SELECTED, MENU_ARCHIE_MAIN1);
|
||||
}
|
||||
break;
|
||||
|
||||
case 4: // Load ROM
|
||||
if (select)
|
||||
{
|
||||
SelectFile(Selected_F[menusub], "ROM", 0, MENU_ARCHIE_MAIN_FILE_SELECTED, MENU_ARCHIE_MAIN1);
|
||||
}
|
||||
break;
|
||||
|
||||
case 3:
|
||||
case 5:
|
||||
archie_set_ar(!archie_get_ar());
|
||||
menustate = MENU_ARCHIE_MAIN1;
|
||||
break;
|
||||
|
||||
case 4:
|
||||
case 6:
|
||||
archie_set_60(!archie_get_60());
|
||||
menustate = MENU_ARCHIE_MAIN1;
|
||||
break;
|
||||
|
||||
case 5:
|
||||
case 7:
|
||||
archie_set_amix(archie_get_amix() + (minus ? -1 : 1));
|
||||
menustate = MENU_ARCHIE_MAIN1;
|
||||
break;
|
||||
|
||||
case 6:
|
||||
case 8:
|
||||
archie_set_afix(!archie_get_afix());
|
||||
menustate = MENU_ARCHIE_MAIN1;
|
||||
break;
|
||||
|
||||
case 7:
|
||||
case 9:
|
||||
user_io_set_joyswap(!user_io_get_joyswap());
|
||||
menustate = MENU_ARCHIE_MAIN1;
|
||||
break;
|
||||
|
||||
case 8:
|
||||
case 10:
|
||||
archie_set_mswap(!archie_get_mswap());
|
||||
menustate = MENU_ARCHIE_MAIN1;
|
||||
break;
|
||||
|
||||
case 9: // Exit
|
||||
case 11: // Exit
|
||||
if (select) menustate = MENU_NONE1;
|
||||
break;
|
||||
}
|
||||
@@ -1362,18 +1375,25 @@ void HandleUI(void)
|
||||
break;
|
||||
|
||||
case MENU_ARCHIE_MAIN_FILE_SELECTED:
|
||||
menustate = MENU_ARCHIE_MAIN1;
|
||||
if (menusub <= 1)
|
||||
{
|
||||
memcpy(Selected_F[menusub], selPath, sizeof(Selected_F[menusub]));
|
||||
recent_update(SelectedDir, Selected_F[menusub], SelectedLabel, 500);
|
||||
user_io_file_mount(selPath, menusub);
|
||||
}
|
||||
else if (menusub == 2)
|
||||
else if (menusub <= 3)
|
||||
{
|
||||
memcpy(Selected_F[menusub], selPath, sizeof(Selected_F[menusub]));
|
||||
recent_update(SelectedDir, Selected_F[menusub], SelectedLabel, 501);
|
||||
archie_hdd_mount(selPath, menusub - 2);
|
||||
}
|
||||
else if (menusub == 4)
|
||||
{
|
||||
memcpy(Selected_F[menusub], selPath, sizeof(Selected_F[menusub]));
|
||||
archie_set_rom(selPath);
|
||||
menustate = MENU_NONE1;
|
||||
}
|
||||
menustate = MENU_ARCHIE_MAIN1;
|
||||
break;
|
||||
|
||||
/******************************************************************/
|
||||
|
||||
@@ -1,22 +1,26 @@
|
||||
#include "stdio.h"
|
||||
#include "string.h"
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
|
||||
#include "../../hardware.h"
|
||||
#include "../../fpga_io.h"
|
||||
#include "../../menu.h"
|
||||
#include "archie.h"
|
||||
#include "../../debug.h"
|
||||
#include "../../user_io.h"
|
||||
#include "../../input.h"
|
||||
#include "../../support.h"
|
||||
#include "archie.h"
|
||||
|
||||
#define CONFIG_FILENAME "ARCHIE.CFG"
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned long system_ctrl; // system control word
|
||||
char rom_img[1024]; // rom image file name
|
||||
char rom_img[1024]; // rom image file name
|
||||
char hdd_img[2][1024];
|
||||
} archie_config_t;
|
||||
|
||||
static archie_config_t config;
|
||||
static archie_config_t config = {};
|
||||
|
||||
#define archie_debugf(a, ...) printf("\033[1;31mARCHIE: " a "\033[0m\n", ##__VA_ARGS__)
|
||||
// #define archie_debugf(a, ...)
|
||||
@@ -189,10 +193,91 @@ static void archie_kbd_reset(void)
|
||||
flags = 0;
|
||||
}
|
||||
|
||||
void archie_init(void)
|
||||
#define cmos_name user_io_make_filepath(HomeDir(), "cmos.dat")
|
||||
|
||||
static uint8_t rtc[16] = {};
|
||||
static uint8_t year = 0;
|
||||
static void update_rtc()
|
||||
{
|
||||
time_t t = time(NULL);
|
||||
struct tm tm = *localtime(&t);
|
||||
year = tm.tm_year - 100;
|
||||
rtc[2] = (tm.tm_sec % 10) | ((tm.tm_sec / 10) << 4);
|
||||
rtc[3] = (tm.tm_min % 10) | ((tm.tm_min / 10) << 4);
|
||||
rtc[4] = (tm.tm_hour % 10) | ((tm.tm_hour / 10) << 4);
|
||||
rtc[5] = (tm.tm_mday % 10) | ((tm.tm_mday / 10) << 4) | (year << 6);
|
||||
rtc[6] = ((tm.tm_mon + 1) % 10) | (((tm.tm_mon + 1) / 10) << 4) | (tm.tm_wday << 5);
|
||||
}
|
||||
|
||||
static void load_cmos()
|
||||
{
|
||||
static uint8_t cmos_data[256] = {};
|
||||
if (FileLoad(cmos_name, cmos_data, sizeof(cmos_data)))
|
||||
{
|
||||
update_rtc();
|
||||
memcpy(cmos_data, rtc, 16);
|
||||
cmos_data[0xC0] = year;
|
||||
cmos_data[0xC1] = 20;
|
||||
|
||||
user_io_set_index(3);
|
||||
user_io_set_download(1);
|
||||
user_io_file_tx_data(cmos_data, sizeof(cmos_data));
|
||||
user_io_set_download(0);
|
||||
}
|
||||
}
|
||||
|
||||
static void check_cmos(uint8_t cnt)
|
||||
{
|
||||
static uint8_t old_cnt = 0;
|
||||
static uint32_t cmos_timer = 0;
|
||||
static uint32_t rtc_timer = 0;
|
||||
|
||||
if (!cmos_timer || CheckTimer(cmos_timer))
|
||||
{
|
||||
cmos_timer = GetTimer(1000);
|
||||
if (old_cnt != cnt)
|
||||
{
|
||||
old_cnt = cnt;
|
||||
|
||||
static uint8_t cmos_data[256];
|
||||
user_io_set_index(3);
|
||||
user_io_set_upload(1);
|
||||
user_io_file_rx_data(cmos_data, sizeof(cmos_data));
|
||||
user_io_set_upload(0);
|
||||
memset(cmos_data, 0, 16);
|
||||
cmos_data[0xC0] = 0;
|
||||
cmos_data[0xC1] = 0;
|
||||
|
||||
static uint8_t cmos_old[256];
|
||||
FileLoad(cmos_name, cmos_old, sizeof(cmos_old));
|
||||
memset(cmos_old, 0, 16);
|
||||
cmos_old[0xC0] = 0;
|
||||
cmos_old[0xC1] = 0;
|
||||
|
||||
if (memcmp(cmos_old, cmos_data, 256))
|
||||
{
|
||||
printf("update cmos.dat\n");
|
||||
//hexdump(cmos_data, 256); printf("\n");
|
||||
FileSave(cmos_name, cmos_data, sizeof(cmos_data));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!rtc_timer || CheckTimer(rtc_timer))
|
||||
{
|
||||
rtc_timer = GetTimer(60000);
|
||||
update_rtc();
|
||||
user_io_set_index(3);
|
||||
user_io_set_download(1);
|
||||
user_io_file_tx_data(rtc, 16);
|
||||
user_io_set_download(0);
|
||||
}
|
||||
}
|
||||
|
||||
void archie_init()
|
||||
{
|
||||
archie_debugf("init");
|
||||
user_io_8bit_set_status(1, UIO_STATUS_RESET);
|
||||
user_io_8bit_set_status(UIO_STATUS_RESET, UIO_STATUS_RESET);
|
||||
|
||||
// set config defaults
|
||||
config.system_ctrl = 0;
|
||||
@@ -217,6 +302,15 @@ void archie_init(void)
|
||||
archie_set_60(archie_get_60());
|
||||
archie_set_afix(archie_get_afix());
|
||||
|
||||
if(!config.hdd_img[0][0] || !OpenHardfile(0, config.hdd_img[0]))
|
||||
{
|
||||
memset(config.hdd_img[0], 0, sizeof(config.hdd_img[0]));
|
||||
}
|
||||
|
||||
if (!config.hdd_img[1][0] || !OpenHardfile(1, config.hdd_img[1]))
|
||||
{
|
||||
memset(config.hdd_img[1], 0, sizeof(config.hdd_img[1]));
|
||||
}
|
||||
|
||||
// upload rom file
|
||||
archie_set_rom(config.rom_img);
|
||||
@@ -224,9 +318,9 @@ void archie_init(void)
|
||||
// upload ext file
|
||||
//user_io_file_tx("Archie/RISCOS.EXT", 2);
|
||||
|
||||
user_io_file_tx(user_io_make_filepath(HomeDir(), "CMOS.DAT"), 3);
|
||||
load_cmos();
|
||||
|
||||
user_io_8bit_set_status(0, UIO_STATUS_RESET);
|
||||
user_io_8bit_set_status(~UIO_STATUS_RESET, UIO_STATUS_RESET);
|
||||
|
||||
/*
|
||||
int i;
|
||||
@@ -332,8 +426,38 @@ static void archie_check_queue(void)
|
||||
tx_queue_rptr = QUEUE_NEXT(tx_queue_rptr);
|
||||
}
|
||||
|
||||
static void check_reset()
|
||||
{
|
||||
static uint32_t timer = 0;
|
||||
|
||||
// check the user button
|
||||
if (!user_io_osd_is_visible() && (user_io_user_button() || user_io_get_kbd_reset()))
|
||||
{
|
||||
if (!timer) timer = GetTimer(1000);
|
||||
else if (timer != 1)
|
||||
{
|
||||
if (CheckTimer(timer))
|
||||
{
|
||||
archie_set_rom(config.rom_img);
|
||||
timer = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
timer = 0;
|
||||
}
|
||||
}
|
||||
|
||||
void archie_poll(void)
|
||||
{
|
||||
EnableFpga();
|
||||
uint16_t status = spi_w(0);
|
||||
DisableFpga();
|
||||
HandleHDD(status >> 8, 0);
|
||||
check_cmos(status);
|
||||
check_reset();
|
||||
|
||||
#ifdef HOLD_OFF_TIME
|
||||
if ((kbd_state == STATE_HOLD_OFF) && CheckTimer(hold_off_timer)) {
|
||||
archie_debugf("KBD resume after hold off");
|
||||
@@ -473,3 +597,22 @@ void archie_poll(void)
|
||||
else
|
||||
DisableIO();
|
||||
}
|
||||
|
||||
const char *archie_get_hdd_name(int i)
|
||||
{
|
||||
if (!config.hdd_img[i][0]) return NULL;
|
||||
|
||||
char *p = strrchr(config.hdd_img[i], '/');
|
||||
if (!p) p = config.hdd_img[i]; else p++;
|
||||
|
||||
return p;
|
||||
}
|
||||
|
||||
void archie_hdd_mount(char *filename, int idx)
|
||||
{
|
||||
memset(config.hdd_img[idx], 0, sizeof(config.hdd_img[idx]));
|
||||
if (OpenHardfile(idx, filename))
|
||||
{
|
||||
strcpy(config.hdd_img[idx], filename);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,4 +22,7 @@ int archie_get_60();
|
||||
void archie_set_afix(char i);
|
||||
int archie_get_afix();
|
||||
|
||||
const char *archie_get_hdd_name(int i);
|
||||
void archie_hdd_mount(char *filename, int idx);
|
||||
|
||||
#endif // ARCHIE_H
|
||||
|
||||
@@ -397,7 +397,8 @@ static void ATA_IdentifyDevice(uint8_t* tfr, hdfTYPE *hdf)
|
||||
fpga_spi_fast(CMD_IDE_DATA_WR<<8); // write data command
|
||||
fpga_spi_fast(0);
|
||||
fpga_spi_fast(0);
|
||||
fpga_spi_fast_block_write_be((uint16_t*)sector_buffer, 256);
|
||||
if(is_minimig()) fpga_spi_fast_block_write_be((uint16_t*)sector_buffer, 256);
|
||||
else fpga_spi_fast_block_write((uint16_t*)sector_buffer, 256);
|
||||
DisableFpga();
|
||||
WriteStatus(IDE_STATUS_END | IDE_STATUS_IRQ);
|
||||
}
|
||||
@@ -509,7 +510,8 @@ static void SendSector()
|
||||
fpga_spi_fast(CMD_IDE_DATA_WR << 8); // write data command
|
||||
fpga_spi_fast(0);
|
||||
fpga_spi_fast(0);
|
||||
fpga_spi_fast_block_write_be((uint16_t*)sector_buffer, 256);
|
||||
if (is_minimig()) fpga_spi_fast_block_write_be((uint16_t*)sector_buffer, 256);
|
||||
else fpga_spi_fast_block_write((uint16_t*)sector_buffer, 256);
|
||||
DisableFpga();
|
||||
}
|
||||
|
||||
@@ -519,7 +521,8 @@ static void RecvSector()
|
||||
fpga_spi_fast(CMD_IDE_DATA_RD << 8); // read data command
|
||||
fpga_spi_fast(0);
|
||||
fpga_spi_fast(0);
|
||||
fpga_spi_fast_block_read_be((uint16_t*)sector_buffer, 256);
|
||||
if (is_minimig()) fpga_spi_fast_block_read_be((uint16_t*)sector_buffer, 256);
|
||||
else fpga_spi_fast_block_read((uint16_t*)sector_buffer, 256);
|
||||
DisableFpga();
|
||||
}
|
||||
|
||||
@@ -717,21 +720,44 @@ void HandleHDD(uint8_t c1, uint8_t c2)
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t OpenHardfile(uint8_t unit)
|
||||
uint8_t OpenHardfile(uint8_t unit, const char* filename)
|
||||
{
|
||||
hdfTYPE *hdf = &HDF[unit];
|
||||
hdf->unit = unit;
|
||||
hdf->enabled = 0;
|
||||
if (minimig_config.enable_ide && minimig_config.hardfile[unit].enabled)
|
||||
|
||||
if (is_minimig())
|
||||
{
|
||||
if (minimig_config.enable_ide && minimig_config.hardfile[unit].enabled)
|
||||
{
|
||||
printf("\nChecking HDD %d\n", unit);
|
||||
if (minimig_config.hardfile[unit].filename[0])
|
||||
{
|
||||
if (FileOpenEx(&hdf->file, minimig_config.hardfile[unit].filename, FileCanWrite(minimig_config.hardfile[unit].filename) ? O_RDWR : O_RDONLY))
|
||||
{
|
||||
hdf->enabled = 1;
|
||||
printf("file: \"%s\": ", hdf->file.name);
|
||||
SetHardfileGeometry(hdf, !strcasecmp(".hdf", minimig_config.hardfile[unit].filename + strlen(minimig_config.hardfile[unit].filename) - 4));
|
||||
printf("size: %llu (%llu MB)\n", hdf->file.size, hdf->file.size >> 20);
|
||||
printf("CHS: %u/%u/%u", hdf->cylinders, hdf->heads, hdf->sectors);
|
||||
printf(" (%llu MB), ", ((((uint64_t)hdf->cylinders) * hdf->heads * hdf->sectors) >> 11));
|
||||
printf("Offset: %d\n", hdf->offset);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
printf("HDD %d: not present\n", unit);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("\nChecking HDD %d\n", unit);
|
||||
if (minimig_config.hardfile[unit].filename[0])
|
||||
if (filename[0])
|
||||
{
|
||||
if (FileOpenEx(&hdf->file, minimig_config.hardfile[unit].filename, FileCanWrite(minimig_config.hardfile[unit].filename) ? O_RDWR : O_RDONLY))
|
||||
if (FileOpenEx(&hdf->file, filename, FileCanWrite(filename) ? O_RDWR : O_RDONLY))
|
||||
{
|
||||
hdf->enabled = 1;
|
||||
printf("file: \"%s\": ", hdf->file.name);
|
||||
SetHardfileGeometry(hdf, !strcasecmp(".hdf", minimig_config.hardfile[unit].filename + strlen(minimig_config.hardfile[unit].filename) - 4));
|
||||
SetHardfileGeometry(hdf, 0);
|
||||
printf("size: %llu (%llu MB)\n", hdf->file.size, hdf->file.size >> 20);
|
||||
printf("CHS: %u/%u/%u", hdf->cylinders, hdf->heads, hdf->sectors);
|
||||
printf(" (%llu MB), ", ((((uint64_t)hdf->cylinders) * hdf->heads * hdf->sectors) >> 11));
|
||||
@@ -739,7 +765,6 @@ uint8_t OpenHardfile(uint8_t unit)
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
printf("HDD %d: not present\n", unit);
|
||||
}
|
||||
|
||||
// close if opened earlier.
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
|
||||
// functions
|
||||
void HandleHDD(uint8_t c1, uint8_t c2);
|
||||
uint8_t OpenHardfile(uint8_t unit);
|
||||
uint8_t OpenHardfile(uint8_t unit, const char* filename = 0);
|
||||
int checkHDF(const char* name, struct RigidDiskBlock **rdb);
|
||||
|
||||
#endif // __HDD_H__
|
||||
|
||||
Reference in New Issue
Block a user