mirror of
https://github.com/Wiimpathy/HatariWii.git
synced 2025-02-16 17:29:12 +01:00
222 lines
4.8 KiB
C
222 lines
4.8 KiB
C
/*
|
|
* Hatari - common.c
|
|
*
|
|
* Copyright (C) 2012 by Eero Tamminen
|
|
*
|
|
* This file is distributed under the GNU General Public License, version 2
|
|
* or at your option any later version. Read the file gpl.txt for details.
|
|
*
|
|
* Common functions for gemdos.c and minimal.c testers.
|
|
*/
|
|
#ifdef __PUREC__ /* or AHCC */
|
|
# include <tos.h>
|
|
#else
|
|
# include <osbind.h>
|
|
#endif
|
|
#include <stdio.h>
|
|
#include "common.h"
|
|
|
|
/*------- success / failure ----- */
|
|
|
|
/* anything failing changes 'msg' to failure,
|
|
* write_midi() expects them to be of same lenght.
|
|
*/
|
|
static const char success[] = SUCCESS;
|
|
static const char failure[] = FAILURE;
|
|
static const char *msg = success;
|
|
|
|
/* ------- helper functions ------ */
|
|
|
|
/* device/file opening with error handling */
|
|
static long open_device(const char *path, int attr)
|
|
{
|
|
long handle = Fopen(path, attr);
|
|
if (handle < 0) {
|
|
|
|
printf("ERROR: Fopen(%c: '%s', %d) -> %ld\r\n", 'A'+Dgetdrv(), path, attr, handle);
|
|
msg = failure;
|
|
}
|
|
return handle;
|
|
}
|
|
|
|
/* device/file closing with error handling */
|
|
static void close_device(long handle)
|
|
{
|
|
if (Fclose(handle) != 0) {
|
|
Cconws("ERROR: file close failed\r\n");
|
|
msg = failure;
|
|
}
|
|
}
|
|
|
|
static void print_ioerror(const char *op, int handle, int bufsize, char *buffer, long count)
|
|
{
|
|
if (!count) {
|
|
return;
|
|
}
|
|
printf("ERROR: %s(%d, %d, %p) -> %ld\r\n", op, handle, bufsize, buffer, count);
|
|
msg = failure;
|
|
}
|
|
|
|
/* write given file content to to given device/file with GEMDOS */
|
|
static void write_gemdos_device(const char *from, const char *to)
|
|
{
|
|
long handle1, handle2;
|
|
long count1, count2;
|
|
char buffer[64];
|
|
|
|
handle1 = open_device(from, FO_READ);
|
|
if (handle1 < 0) {
|
|
return;
|
|
}
|
|
handle2 = open_device(to, FO_WRITE);
|
|
if (handle2 < 0) {
|
|
return;
|
|
}
|
|
while (1) {
|
|
/* copy file contents */
|
|
count1 = Fread(handle1, sizeof(buffer), buffer);
|
|
if (count1 <= 0 || count1 > (long)sizeof(buffer)) {
|
|
print_ioerror("Fread", handle1, sizeof(buffer), buffer, count1);
|
|
break;
|
|
}
|
|
count2 = Fwrite(handle2, count1, buffer);
|
|
if (count2 <= 0) {
|
|
print_ioerror("Fwrite", handle2, count1, buffer, count2);
|
|
break;
|
|
}
|
|
}
|
|
close_device(handle1);
|
|
close_device(handle2);
|
|
}
|
|
|
|
/* set given mode to given file */
|
|
static void set_mode(const char *path, int mode)
|
|
{
|
|
/* TODO: AHCC misses FA_SET (1) */
|
|
int result = Fattrib(path, 1, mode);
|
|
if (result != mode) {
|
|
printf("ERROR: Fattrib(%s, 1, %d) -> %d\r\n", path, mode, result);
|
|
msg = failure;
|
|
}
|
|
}
|
|
|
|
/* --------- public functions ---------
|
|
* documented in the header
|
|
*/
|
|
|
|
void write2console(const char *input)
|
|
{
|
|
printf("\r\n%s -> CON: (console)\r\n", input);
|
|
if (Cconos()) {
|
|
write_gemdos_device(input, "CON:");
|
|
} else {
|
|
Cconws("ERROR: 'CON:' not ready!\r\n");
|
|
msg = failure;
|
|
}
|
|
}
|
|
|
|
void write2printer(const char *input)
|
|
{
|
|
printf("\r\n%s -> PRN: (printer)\r\n", input);
|
|
if (Cprnos()) {
|
|
write_gemdos_device(input, "PRN:");
|
|
} else {
|
|
Cconws("ERROR: 'PRN:' not ready!\r\n");
|
|
msg = failure;
|
|
}
|
|
}
|
|
|
|
void write2serial(const char *input)
|
|
{
|
|
printf("\r\n%s -> AUX: (serial)\r\n", input);
|
|
if (Cauxos()) {
|
|
write_gemdos_device(input, "AUX:");
|
|
} else {
|
|
Cconws("ERROR: 'AUX:' not ready!\r\n");
|
|
msg = failure;
|
|
}
|
|
}
|
|
|
|
void copy_file(const char *input, const char *output)
|
|
{
|
|
printf("\r\n%s -> %s\r\n", input, output);
|
|
write_gemdos_device(input, output);
|
|
set_mode(output, FA_READONLY);
|
|
}
|
|
|
|
void truncate_file(const char *readonly)
|
|
{
|
|
long handle;
|
|
printf("\r\nTruncate -> %s\r\n", readonly);
|
|
handle = Fcreate(readonly, 0);
|
|
if (handle >= 0) {
|
|
printf("ERROR: truncate succeeded, Fcreate(\"%s\", 0) -> %ld\r\n", readonly, handle);
|
|
msg = failure;
|
|
close_device(handle);
|
|
}
|
|
set_mode(readonly, 0);
|
|
handle = Fcreate(readonly, 0);
|
|
if (handle >= 0) {
|
|
close_device(handle);
|
|
} else {
|
|
printf("ERROR: truncate failed, Fcreate(\"%s\", 0) -> %ld\r\n", readonly, handle);
|
|
msg = failure;
|
|
}
|
|
}
|
|
|
|
void write_midi(void)
|
|
{
|
|
printf("\r\nResult -> Midi (%s)\r\n", success);
|
|
Vsync(); /* sync screen output before sending result */
|
|
Midiws(sizeof(success)-2, msg);
|
|
Midiws(0, "\n");
|
|
}
|
|
|
|
void clear_screen(void)
|
|
{
|
|
printf("\033EGEMDOS version = 0x%x\r\n", Sversion());
|
|
}
|
|
|
|
static int is_enter(long key)
|
|
{
|
|
int scancode = (key >> 16) & 0xff;
|
|
/* return or enter? */
|
|
if (scancode == 28 || scancode == 114) {
|
|
return 1;
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
void wait_enter(void)
|
|
{
|
|
/* eat buffered keys */
|
|
while (Cconis()) {
|
|
Cconin();
|
|
}
|
|
Cconws("\r\n<press Enter>\r\n");
|
|
while (!is_enter(Cconin()));
|
|
}
|
|
|
|
/* ------- TODO ------ */
|
|
|
|
#if TEST_REDIRECTION
|
|
static void stdin_to_printer(void)
|
|
{
|
|
long handle = open_device("PRN:", FO_WRITE);
|
|
if (handle >= 0) {
|
|
/* TODO: dup & force stdout to printer */
|
|
}
|
|
}
|
|
static void stdin_from_file(const char *path)
|
|
{
|
|
long handle = open_device(path, FO_WRITE);
|
|
if (handle >= 0) {
|
|
/* TODO: dup & force stdin from file */
|
|
}
|
|
}
|
|
static void stdin_stdout_reset(void)
|
|
{
|
|
/* TODO: force stdin & stdout back to normal */
|
|
}
|
|
#endif
|