Fail* directories reorganized, Code-cleanup (-> coding-style), Typos+comments fixed.
git-svn-id: https://www4.informatik.uni-erlangen.de/i4svn/danceos/trunk/devel/fail@1321 8c4709b5-6ec9-48aa-a5cd-a96041d1645a
This commit is contained in:
55
simulators/bochs/misc/Makefile.in
Normal file
55
simulators/bochs/misc/Makefile.in
Normal file
@ -0,0 +1,55 @@
|
||||
# Copyright (C) 2001 MandrakeSoft S.A.
|
||||
#
|
||||
# MandrakeSoft S.A.
|
||||
# 43, rue d'Aboukir
|
||||
# 75002 Paris - France
|
||||
# http://www.linux-mandrake.com/
|
||||
# http://www.mandrakesoft.com/
|
||||
#
|
||||
# This library is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU Lesser General Public
|
||||
# License as published by the Free Software Foundation; either
|
||||
# version 2 of the License, or (at your option) any later version.
|
||||
#
|
||||
# This library is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
# Lesser General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Lesser General Public
|
||||
# License along with this library; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
|
||||
@SUFFIX_LINE@
|
||||
|
||||
|
||||
SHELL = /bin/sh
|
||||
|
||||
@SET_MAKE@
|
||||
|
||||
CC = @CC@
|
||||
CXX = @CXX@
|
||||
CFLAGS = @CFLAGS@ @GUI_CFLAGS@
|
||||
CXXFLAGS = @CXXFLAGS@ @GUI_CXXFLAGS@
|
||||
|
||||
LDFLAGS = @LDFLAGS@
|
||||
LIBS = @LIBS@
|
||||
RANLIB = @RANLIB@
|
||||
|
||||
|
||||
.@CPP_SUFFIX@.o:
|
||||
$(CXX) @DASH@c $(CXXFLAGS) @CXXFP@$< @OFP@$@
|
||||
|
||||
|
||||
all: make_cmos_image
|
||||
|
||||
make_cmos_image@EXE@: make_cmos_image.o
|
||||
@LINK@ make_cmos_image.o
|
||||
|
||||
clean:
|
||||
@RMCOMMAND@ *.o
|
||||
@RMCOMMAND@ make_cmos_image@EXE@
|
||||
|
||||
dist-clean: clean
|
||||
@RMCOMMAND@ Makefile
|
||||
381
simulators/bochs/misc/bxcommit.c
Normal file
381
simulators/bochs/misc/bxcommit.c
Normal file
@ -0,0 +1,381 @@
|
||||
/*
|
||||
* misc/bximage.c
|
||||
* $Id$
|
||||
*
|
||||
* Commits a redolog file in a flat file for bochs images.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
#ifndef _MSC_VER
|
||||
#include <unistd.h>
|
||||
#else
|
||||
#include <io.h>
|
||||
#endif
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
#include <assert.h>
|
||||
#ifdef WIN32
|
||||
# include <conio.h>
|
||||
#endif
|
||||
#include "config.h"
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#if !BX_HAVE_SNPRINTF
|
||||
#include <stdarg.h>
|
||||
/* XXX use real snprintf */
|
||||
/* if they don't have snprintf, just use sprintf */
|
||||
int snprintf(char *s, size_t maxlen, const char *format, ...)
|
||||
{
|
||||
va_list arg;
|
||||
int done;
|
||||
|
||||
va_start(arg, format);
|
||||
done = vsprintf(s, format, arg);
|
||||
va_end(arg);
|
||||
|
||||
return done;
|
||||
}
|
||||
#endif /* !BX_HAVE_SNPRINTF */
|
||||
|
||||
#include "../osdep.h"
|
||||
|
||||
#define HDIMAGE_HEADERS_ONLY 1
|
||||
#include "../iodev/hdimage.h"
|
||||
|
||||
char *EOF_ERR = "ERROR: End of input";
|
||||
char *rcsid = "$Id$";
|
||||
char *divider = "========================================================================";
|
||||
|
||||
void myexit(int code)
|
||||
{
|
||||
#ifdef WIN32
|
||||
printf("\nPress any key to continue\n");
|
||||
getch();
|
||||
#endif
|
||||
exit(code);
|
||||
}
|
||||
|
||||
/* stolen from main.cc */
|
||||
void bx_center_print(FILE *file, char *line, int maxwidth)
|
||||
{
|
||||
int imax;
|
||||
int i;
|
||||
imax = (maxwidth - strlen(line)) >> 1;
|
||||
for (i=0; i<imax; i++) fputc(' ', file);
|
||||
fputs(line, file);
|
||||
}
|
||||
|
||||
void print_banner()
|
||||
{
|
||||
printf("%s\n", divider);
|
||||
bx_center_print(stdout, "bxcommit\n", 72);
|
||||
bx_center_print(stdout, "Undoable Disk Image Commit Tool for Bochs\n", 72);
|
||||
bx_center_print(stdout, rcsid, 72);
|
||||
printf("\n%s\n", divider);
|
||||
}
|
||||
|
||||
/* this is how we crash */
|
||||
void fatal(const char *c)
|
||||
{
|
||||
printf("%s\n", c);
|
||||
myexit(1);
|
||||
}
|
||||
|
||||
/* remove leading spaces, newline junk at end. returns pointer to
|
||||
cleaned string, which is between s0 and the null */
|
||||
char *clean_string(char *s0)
|
||||
{
|
||||
char *s = s0;
|
||||
char *ptr;
|
||||
/* find first nonblank */
|
||||
while (isspace(*s))
|
||||
s++;
|
||||
/* truncate string at first non-alphanumeric */
|
||||
ptr = s;
|
||||
while (isprint(*ptr))
|
||||
ptr++;
|
||||
*ptr = 0;
|
||||
return s;
|
||||
}
|
||||
|
||||
/* returns 0 on success, -1 on failure. The value goes into out. */
|
||||
int ask_int(const char *prompt, int min, int max, int the_default, int *out)
|
||||
{
|
||||
int n = max + 1;
|
||||
char buffer[1024];
|
||||
char *clean;
|
||||
int illegal;
|
||||
while (1) {
|
||||
printf("%s", prompt);
|
||||
printf("[%d] ", the_default);
|
||||
if (!fgets(buffer, sizeof(buffer), stdin))
|
||||
return -1;
|
||||
clean = clean_string(buffer);
|
||||
if (strlen(clean) < 1) {
|
||||
// empty line, use the default
|
||||
*out = the_default;
|
||||
return 0;
|
||||
}
|
||||
illegal = (1 != sscanf(buffer, "%d", &n));
|
||||
if (illegal || n<min || n>max) {
|
||||
printf ("Your choice (%s) was not an integer between %d and %d.\n\n",
|
||||
clean, min, max);
|
||||
} else {
|
||||
// choice is okay
|
||||
*out = n;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int ask_menu(const char *prompt, int n_choices, char *choice[], int the_default, int *out)
|
||||
{
|
||||
char buffer[1024];
|
||||
char *clean;
|
||||
int i;
|
||||
*out = -1;
|
||||
while (1) {
|
||||
printf("%s", prompt);
|
||||
printf("[%s] ", choice[the_default]);
|
||||
if (!fgets(buffer, sizeof(buffer), stdin))
|
||||
return -1;
|
||||
clean = clean_string(buffer);
|
||||
if (strlen(clean) < 1) {
|
||||
// empty line, use the default
|
||||
*out = the_default;
|
||||
return 0;
|
||||
}
|
||||
for (i=0; i<n_choices; i++) {
|
||||
if (!strcmp(choice[i], clean)) {
|
||||
// matched, return the choice number
|
||||
*out = i;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
printf ("Your choice (%s) did not match any of the choices:\n", clean);
|
||||
for (i=0; i<n_choices; i++) {
|
||||
if (i>0) printf(", ");
|
||||
printf("%s", choice[i]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
|
||||
int ask_yn(const char *prompt, int the_default, int *out)
|
||||
{
|
||||
char buffer[16];
|
||||
char *clean;
|
||||
*out = -1;
|
||||
while (1) {
|
||||
printf("%s", prompt);
|
||||
printf("[%s] ", the_default?"yes":"no");
|
||||
if (!fgets(buffer, sizeof(buffer), stdin))
|
||||
return -1;
|
||||
clean = clean_string(buffer);
|
||||
if (strlen(clean) < 1) {
|
||||
// empty line, use the default
|
||||
*out = the_default;
|
||||
return 0;
|
||||
}
|
||||
switch (tolower(clean[0])) {
|
||||
case 'y': *out=1; return 0;
|
||||
case 'n': *out=0; return 0;
|
||||
}
|
||||
printf("Please type either yes or no.\n");
|
||||
}
|
||||
}
|
||||
|
||||
int ask_string(const char *prompt, char *the_default, char *out)
|
||||
{
|
||||
char buffer[1024];
|
||||
char *clean;
|
||||
out[0] = 0;
|
||||
printf("%s", prompt);
|
||||
printf("[%s] ", the_default);
|
||||
if (!fgets(buffer, sizeof(buffer), stdin))
|
||||
return -1;
|
||||
clean = clean_string(buffer);
|
||||
if (strlen(clean) < 1) {
|
||||
// empty line, use the default
|
||||
strcpy(out, the_default);
|
||||
return 0;
|
||||
}
|
||||
strcpy(out, clean);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* produce the image file */
|
||||
int commit_redolog(const char *flatname, const char *redologname)
|
||||
{
|
||||
int flatfd, redologfd;
|
||||
redolog_header_t header;
|
||||
Bit32u *catalog, catalog_size;
|
||||
Bit8u *bitmap;
|
||||
Bit32u i, bitmap_blocs, extent_blocs;
|
||||
Bit8u buffer[512];
|
||||
|
||||
// check if flat file exists
|
||||
flatfd = open (flatname, O_WRONLY
|
||||
#ifdef O_BINARY
|
||||
| O_BINARY
|
||||
#endif
|
||||
);
|
||||
if (flatfd<0) {
|
||||
fatal("ERROR: flat file not found or not writable");
|
||||
}
|
||||
|
||||
// Check if redolog exists
|
||||
printf("%s\n",redologname);
|
||||
redologfd = open(redologname, O_RDONLY
|
||||
#ifdef O_BINARY
|
||||
| O_BINARY
|
||||
#endif
|
||||
);
|
||||
if (redologfd<0) {
|
||||
fatal("ERROR: redolog file not found");
|
||||
}
|
||||
|
||||
printf ("\nReading redolog header: [");
|
||||
|
||||
if (read(redologfd, &header, STANDARD_HEADER_SIZE) != STANDARD_HEADER_SIZE)
|
||||
fatal("\nERROR: while reading redolog header!");
|
||||
|
||||
// Print infos on redlog
|
||||
printf("Type='%s', Subtype='%s', Version=%d.%d] Done.",
|
||||
header.standard.type, header.standard.subtype,
|
||||
dtoh32(header.standard.version)/0x10000,
|
||||
dtoh32(header.standard.version)%0x10000);
|
||||
|
||||
printf("\nChecking redolog header: [");
|
||||
|
||||
if (strcmp((char *)header.standard.magic, STANDARD_HEADER_MAGIC) != 0)
|
||||
fatal("\nERROR: bad magic in redolog header!");
|
||||
|
||||
if (strcmp((char *)header.standard.type, REDOLOG_TYPE) != 0)
|
||||
fatal("\nERROR: bad type in redolog header!");
|
||||
|
||||
if (strcmp((char *)header.standard.subtype, REDOLOG_SUBTYPE_UNDOABLE) != 0)
|
||||
fatal("\nERROR: bad subtype in redolog header!");
|
||||
|
||||
if (header.standard.version != htod32(STANDARD_HEADER_VERSION))
|
||||
fatal("\nERROR: bad version in redolog header!");
|
||||
|
||||
printf("#entries=%d, bitmap size=%d, exent size = %d] Done.",
|
||||
dtoh32(header.specific.catalog),
|
||||
dtoh32(header.specific.bitmap),
|
||||
dtoh32(header.specific.extent));
|
||||
|
||||
catalog = (Bit32u*)malloc(dtoh32(header.specific.catalog) * sizeof(Bit32u));
|
||||
bitmap = (Bit8u*)malloc(dtoh32(header.specific.bitmap));
|
||||
printf("\nReading Catalog: [");
|
||||
|
||||
lseek(redologfd, dtoh32(header.standard.header), SEEK_SET);
|
||||
|
||||
catalog_size = dtoh32(header.specific.catalog) * sizeof(Bit32u);
|
||||
if ((Bit32u) read(redologfd, catalog, catalog_size) != catalog_size)
|
||||
fatal("\nERROR: while reading redolog catalog!");
|
||||
|
||||
printf("] Done.");
|
||||
|
||||
printf("\nCommitting changes to flat file: [ 0%%]");
|
||||
|
||||
bitmap_blocs = 1 + (dtoh32(header.specific.bitmap) - 1) / 512;
|
||||
extent_blocs = 1 + (dtoh32(header.specific.extent) - 1) / 512;
|
||||
|
||||
for(i=0; i<dtoh32(header.specific.catalog); i++)
|
||||
{
|
||||
printf("\x8\x8\x8\x8\x8%3d%%]", (i+1)*100/dtoh32(header.specific.catalog));
|
||||
fflush(stdout);
|
||||
|
||||
if (dtoh32(catalog[i]) != REDOLOG_PAGE_NOT_ALLOCATED) {
|
||||
Bit64s bitmap_offset;
|
||||
Bit32u bitmap_size, j;
|
||||
|
||||
bitmap_offset = (Bit64s)STANDARD_HEADER_SIZE + (dtoh32(header.specific.catalog) * sizeof(Bit32u));
|
||||
bitmap_offset += (Bit64s)512 * dtoh32(catalog[i]) * (extent_blocs + bitmap_blocs);
|
||||
|
||||
// Read bitmap
|
||||
lseek(redologfd, bitmap_offset, SEEK_SET);
|
||||
|
||||
bitmap_size = dtoh32(header.specific.bitmap);
|
||||
if ((Bit32u) read(redologfd, bitmap, bitmap_size) != bitmap_size)
|
||||
fatal("\nERROR: while reading bitmap from redolog !");
|
||||
|
||||
for(j=0; j<dtoh32(header.specific.bitmap); j++)
|
||||
{
|
||||
Bit32u bit;
|
||||
|
||||
for(bit=0; bit<8; bit++)
|
||||
{
|
||||
if ( (bitmap[j] & (1<<bit)) != 0)
|
||||
{
|
||||
Bit64s flat_offset, bloc_offset;
|
||||
|
||||
bloc_offset = bitmap_offset + ((Bit64s)512 * (bitmap_blocs + ((j*8)+bit)));
|
||||
|
||||
lseek(redologfd, (off_t)bloc_offset, SEEK_SET);
|
||||
|
||||
if (read(redologfd, buffer, 512) != 512)
|
||||
fatal("\nERROR: while reading bloc from redolog !");
|
||||
|
||||
flat_offset = (Bit64s)i * (dtoh32(header.specific.extent));
|
||||
flat_offset += (Bit64s)512 * ((j * 8) + bit);
|
||||
|
||||
lseek(flatfd, (off_t)flat_offset, SEEK_SET);
|
||||
|
||||
if (write(flatfd, buffer, 512) != 512)
|
||||
fatal("\nERROR: while writing bloc in flatfile !");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
printf(" Done.");
|
||||
printf("\n");
|
||||
|
||||
close(flatfd);
|
||||
close(redologfd);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CDECL main()
|
||||
{
|
||||
char filename[256];
|
||||
char tmplogname[256];
|
||||
char redologname[256];
|
||||
int remove;
|
||||
|
||||
print_banner();
|
||||
filename[0] = 0;
|
||||
redologname[0] = 0;
|
||||
|
||||
if (ask_string("\nWhat is the flat image name?\n", "c.img", filename) < 0)
|
||||
fatal(EOF_ERR);
|
||||
|
||||
snprintf(tmplogname,256,"%s%s", filename, UNDOABLE_REDOLOG_EXTENSION);
|
||||
|
||||
if (ask_string("\nWhat is the redolog name?\n", tmplogname, redologname) < 0)
|
||||
fatal(EOF_ERR);
|
||||
|
||||
if (ask_yn("\nShall I remove the redolog afterwards?\n", 1, &remove) < 0)
|
||||
fatal(EOF_ERR);
|
||||
|
||||
commit_redolog(filename, redologname);
|
||||
|
||||
if (remove) {
|
||||
if (unlink(redologname) != 0)
|
||||
fatal("ERROR: while removing the redolog !\n");
|
||||
}
|
||||
|
||||
// make picky compilers (c++, gcc) happy,
|
||||
// even though we leave via 'myexit' just above
|
||||
return 0;
|
||||
}
|
||||
748
simulators/bochs/misc/bximage.c
Normal file
748
simulators/bochs/misc/bximage.c
Normal file
@ -0,0 +1,748 @@
|
||||
/*
|
||||
* misc/bximage.c
|
||||
* $Id$
|
||||
*
|
||||
* Create empty hard disk or floppy disk images for bochs.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifdef WIN32
|
||||
# include <conio.h>
|
||||
# include <windows.h>
|
||||
# include <winioctl.h>
|
||||
#ifdef _MSC_VER
|
||||
# include <io.h>
|
||||
#endif
|
||||
#endif
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
#include <assert.h>
|
||||
#include "config.h"
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#include "../osdep.h"
|
||||
|
||||
#define HDIMAGE_HEADERS_ONLY 1
|
||||
#include "../iodev/hdimage.h"
|
||||
|
||||
int bx_hdimage;
|
||||
int bx_fdsize_idx;
|
||||
int bx_hdsize;
|
||||
int bx_hdimagemode;
|
||||
int bx_interactive;
|
||||
char bx_filename[256];
|
||||
|
||||
typedef int (*WRITE_IMAGE)(FILE*, Bit64u);
|
||||
#ifdef WIN32
|
||||
typedef int (*WRITE_IMAGE_WIN32)(HANDLE, Bit64u);
|
||||
#endif
|
||||
|
||||
char *EOF_ERR = "ERROR: End of input";
|
||||
char *rcsid = "$Id$";
|
||||
char *divider = "========================================================================";
|
||||
|
||||
/* menu data for choosing floppy/hard disk */
|
||||
char *fdhd_menu = "\nDo you want to create a floppy disk image or a hard disk image?\nPlease type hd or fd. ";
|
||||
char *fdhd_choices[] = { "fd", "hd" };
|
||||
int fdhd_n_choices = 2;
|
||||
|
||||
/* menu data for choosing floppy size */
|
||||
char *fdsize_menu = "\nChoose the size of floppy disk image to create, in megabytes.\nPlease type 0.16, 0.18, 0.32, 0.36, 0.72, 1.2, 1.44, 1.68, 1.72, or 2.88.\n ";
|
||||
char *fdsize_choices[] = { "0.16","0.18","0.32","0.36","0.72","1.2","1.44","1.68","1.72","2.88" };
|
||||
int fdsize_n_choices = 10;
|
||||
|
||||
/* menu data for choosing disk mode */
|
||||
char *hdmode_menu = "\nWhat kind of image should I create?\nPlease type flat, sparse or growing. ";
|
||||
char *hdmode_choices[] = {"flat", "sparse", "growing" };
|
||||
int hdmode_n_choices = 3;
|
||||
|
||||
void myexit(int code)
|
||||
{
|
||||
#ifdef WIN32
|
||||
printf("\nPress any key to continue\n");
|
||||
getch();
|
||||
#endif
|
||||
exit(code);
|
||||
}
|
||||
|
||||
/* stolen from main.cc */
|
||||
void bx_center_print(FILE *file, char *line, int maxwidth)
|
||||
{
|
||||
int imax;
|
||||
int i;
|
||||
imax = (maxwidth - strlen(line)) >> 1;
|
||||
for (i=0; i<imax; i++) fputc(' ', file);
|
||||
fputs(line, file);
|
||||
}
|
||||
|
||||
void print_banner()
|
||||
{
|
||||
printf("%s\n", divider);
|
||||
bx_center_print(stdout, "bximage\n", 72);
|
||||
bx_center_print(stdout, "Disk Image Creation Tool for Bochs\n", 72);
|
||||
bx_center_print(stdout, rcsid, 72);
|
||||
printf("\n%s\n", divider);
|
||||
}
|
||||
|
||||
/* this is how we crash */
|
||||
void fatal(const char *c)
|
||||
{
|
||||
printf("%s\n", c);
|
||||
myexit(1);
|
||||
}
|
||||
|
||||
/* check if the argument string is present in the list -
|
||||
returns index on success, -1 on failure. */
|
||||
int get_menu_index(char *arg, int n_choices, char *choice[])
|
||||
{
|
||||
int i;
|
||||
for (i=0; i<n_choices; i++) {
|
||||
if (!strcmp(choice[i], arg)) {
|
||||
// matched, return the choice number
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* remove leading spaces, newline junk at end. returns pointer to
|
||||
cleaned string, which is between s0 and the null */
|
||||
char *clean_string(char *s0)
|
||||
{
|
||||
char *s = s0;
|
||||
char *ptr;
|
||||
/* find first nonblank */
|
||||
while(isspace(*s))
|
||||
s++;
|
||||
/* truncate string at first non-alphanumeric */
|
||||
ptr = s;
|
||||
while(isprint(*ptr))
|
||||
ptr++;
|
||||
*ptr = 0;
|
||||
return s;
|
||||
}
|
||||
|
||||
/* returns 0 on success, -1 on failure. The value goes into out. */
|
||||
int ask_int(const char *prompt, int min, int max, int the_default, int *out)
|
||||
{
|
||||
int n = max + 1;
|
||||
char buffer[1024];
|
||||
char *clean;
|
||||
int illegal;
|
||||
while(1) {
|
||||
printf("%s", prompt);
|
||||
printf("[%d] ", the_default);
|
||||
if (!fgets(buffer, sizeof(buffer), stdin))
|
||||
return -1;
|
||||
clean = clean_string(buffer);
|
||||
if (strlen(clean) < 1) {
|
||||
// empty line, use the default
|
||||
*out = the_default;
|
||||
return 0;
|
||||
}
|
||||
illegal = (1 != sscanf(buffer, "%d", &n));
|
||||
if (illegal || n<min || n>max) {
|
||||
printf("Your choice (%s) was not an integer between %d and %d.\n\n",
|
||||
clean, min, max);
|
||||
} else {
|
||||
// choice is okay
|
||||
*out = n;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int ask_menu(const char *prompt, int n_choices, char *choice[], int the_default, int *out)
|
||||
{
|
||||
char buffer[1024];
|
||||
char *clean;
|
||||
int i;
|
||||
*out = -1;
|
||||
while(1) {
|
||||
printf("%s", prompt);
|
||||
printf("[%s] ", choice[the_default]);
|
||||
if (!fgets(buffer, sizeof(buffer), stdin))
|
||||
return -1;
|
||||
clean = clean_string(buffer);
|
||||
if (strlen(clean) < 1) {
|
||||
// empty line, use the default
|
||||
*out = the_default;
|
||||
return 0;
|
||||
}
|
||||
for (i=0; i<n_choices; i++) {
|
||||
if (!strcmp(choice[i], clean)) {
|
||||
// matched, return the choice number
|
||||
*out = i;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
printf("Your choice (%s) did not match any of the choices:\n", clean);
|
||||
for (i=0; i<n_choices; i++) {
|
||||
if (i>0) printf(", ");
|
||||
printf("%s", choice[i]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
|
||||
int ask_yn(const char *prompt, int the_default, int *out)
|
||||
{
|
||||
char buffer[16];
|
||||
char *clean;
|
||||
*out = -1;
|
||||
while (1) {
|
||||
printf("%s", prompt);
|
||||
printf("[%s] ", the_default?"yes":"no");
|
||||
if (!fgets(buffer, sizeof(buffer), stdin))
|
||||
return -1;
|
||||
clean = clean_string(buffer);
|
||||
if (strlen(clean) < 1) {
|
||||
// empty line, use the default
|
||||
*out = the_default;
|
||||
return 0;
|
||||
}
|
||||
switch(tolower(clean[0])) {
|
||||
case 'y': *out=1; return 0;
|
||||
case 'n': *out=0; return 0;
|
||||
}
|
||||
printf("Please type either yes or no.\n");
|
||||
}
|
||||
}
|
||||
|
||||
int ask_string(const char *prompt, char *the_default, char *out)
|
||||
{
|
||||
char buffer[1024];
|
||||
char *clean;
|
||||
out[0] = 0;
|
||||
printf("%s", prompt);
|
||||
printf("[%s] ", the_default);
|
||||
if (!fgets(buffer, sizeof(buffer), stdin))
|
||||
return -1;
|
||||
clean = clean_string(buffer);
|
||||
if (strlen(clean) < 1) {
|
||||
// empty line, use the default
|
||||
strcpy(out, the_default);
|
||||
return 0;
|
||||
}
|
||||
strcpy(out, clean);
|
||||
return 0;
|
||||
}
|
||||
|
||||
// fileset is like memset but for a file handle
|
||||
void fileset(FILE * fp, int c, size_t n)
|
||||
{
|
||||
#define BLOCK_SIZE (1024)
|
||||
int block[BLOCK_SIZE];
|
||||
size_t left_to_write = n;
|
||||
|
||||
memset(block, c, sizeof(block));
|
||||
|
||||
while(left_to_write > 0)
|
||||
{
|
||||
size_t write = sizeof(block);
|
||||
if (write > left_to_write) write = left_to_write;
|
||||
|
||||
if (1 != fwrite(block, write, 1, fp))
|
||||
{
|
||||
fclose(fp);
|
||||
fatal("ERROR: The disk image is not complete - could not write data block!");
|
||||
}
|
||||
|
||||
left_to_write -= write;
|
||||
}
|
||||
}
|
||||
|
||||
/* Create a suited redolog header */
|
||||
void make_redolog_header(redolog_header_t *header, const char* type, Bit64u size)
|
||||
{
|
||||
Bit32u entries, extent_size, bitmap_size;
|
||||
Bit64u maxsize;
|
||||
|
||||
// Set standard header values
|
||||
strcpy((char*)header->standard.magic, STANDARD_HEADER_MAGIC);
|
||||
strcpy((char*)header->standard.type, REDOLOG_TYPE);
|
||||
strcpy((char*)header->standard.subtype, type);
|
||||
header->standard.version = htod32(STANDARD_HEADER_VERSION);
|
||||
header->standard.header = htod32(STANDARD_HEADER_SIZE);
|
||||
|
||||
entries = 512;
|
||||
bitmap_size = 1;
|
||||
|
||||
// Compute #entries and extent size values
|
||||
do {
|
||||
static Bit32u flip=0;
|
||||
|
||||
extent_size = 8 * bitmap_size * 512;
|
||||
|
||||
header->specific.catalog = htod32(entries);
|
||||
header->specific.bitmap = htod32(bitmap_size);
|
||||
header->specific.extent = htod32(extent_size);
|
||||
|
||||
maxsize = (Bit64u)entries * (Bit64u)extent_size;
|
||||
|
||||
flip++;
|
||||
|
||||
if(flip&0x01) bitmap_size *= 2;
|
||||
else entries *= 2;
|
||||
} while (maxsize < size);
|
||||
|
||||
header->specific.disk = htod64(size);
|
||||
}
|
||||
|
||||
/* produce a flat image file */
|
||||
#ifdef WIN32
|
||||
int make_flat_image_win32(HANDLE hFile, Bit64u sec)
|
||||
{
|
||||
LARGE_INTEGER pos;
|
||||
DWORD dwCount, errCode;
|
||||
USHORT mode;
|
||||
char buffer[1024];
|
||||
|
||||
SetLastError(NO_ERROR);
|
||||
mode = COMPRESSION_FORMAT_DEFAULT;
|
||||
dwCount = 0;
|
||||
memset(buffer, 0, 512);
|
||||
WriteFile(hFile, buffer, 512, &dwCount, NULL); // set the first sector to 0, Win98 doesn't zero out the file
|
||||
// if there is a write at/over the end
|
||||
DeviceIoControl(hFile, FSCTL_SET_COMPRESSION, &mode, sizeof(mode), NULL, 0, &dwCount, NULL);
|
||||
pos.u.LowPart = (unsigned long)((sec - 1) << 9);
|
||||
pos.u.HighPart = (unsigned long)((sec - 1) >> 23);
|
||||
pos.u.LowPart = SetFilePointer(hFile, pos.u.LowPart, &pos.u.HighPart, FILE_BEGIN);
|
||||
memset(buffer, 0, 512);
|
||||
if ((pos.u.LowPart == 0xffffffff && GetLastError() != NO_ERROR) || !WriteFile(hFile, buffer, 512, &dwCount, NULL) || dwCount != 512)
|
||||
{
|
||||
errCode = GetLastError();
|
||||
CloseHandle(hFile);
|
||||
if (errCode == ERROR_DISK_FULL) {
|
||||
fatal("\nERROR: Not enough space on disk for image!");
|
||||
} else {
|
||||
sprintf(buffer, "\nERROR: Disk image creation failed with error code %i!", errCode);
|
||||
fatal(buffer);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
int make_flat_image(FILE *fp, Bit64u sec)
|
||||
{
|
||||
/*
|
||||
* seek to sec*512-1 and write a single character.
|
||||
* can't just do: fseek(fp, 512*sec-1, SEEK_SET)
|
||||
* because 512*sec may be too large for signed int.
|
||||
*/
|
||||
while(sec > 0)
|
||||
{
|
||||
/* temp <-- min(sec, 4194303)
|
||||
* 4194303 is (int)(0x7FFFFFFF/512)
|
||||
*/
|
||||
long temp = (long)((sec < 4194303) ? sec : 4194303);
|
||||
fseek(fp, 512*temp, SEEK_CUR);
|
||||
sec -= temp;
|
||||
}
|
||||
|
||||
fseek(fp, -1, SEEK_CUR);
|
||||
if (fputc('\0', fp) == EOF)
|
||||
{
|
||||
fclose(fp);
|
||||
fatal("\nERROR: The disk image is not complete! (image larger then free space?)");
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* produce a sparse image file */
|
||||
int make_sparse_image(FILE *fp, Bit64u sec)
|
||||
{
|
||||
Bit64u numpages;
|
||||
sparse_header_t header;
|
||||
size_t sizesofar;
|
||||
size_t padtopagesize;
|
||||
|
||||
memset(&header, 0, sizeof(header));
|
||||
header.magic = htod32(SPARSE_HEADER_MAGIC);
|
||||
header.version = htod32(SPARSE_HEADER_VERSION);
|
||||
|
||||
header.pagesize = htod32((1 << 10) * 32); // Use 32 KB Pages - could be configurable
|
||||
numpages = (sec / (dtoh32(header.pagesize) / 512)) + 1;
|
||||
|
||||
header.numpages = htod32((Bit32u)numpages);
|
||||
header.disk = htod64(sec * 512);
|
||||
|
||||
if (numpages != dtoh32(header.numpages))
|
||||
{
|
||||
fclose(fp);
|
||||
fatal("ERROR: The disk image is too large for a sparse image!");
|
||||
// Could increase page size here.
|
||||
// But note this only happens at 128 Terabytes!
|
||||
}
|
||||
|
||||
if (fwrite(&header, sizeof(header), 1, fp) != 1)
|
||||
{
|
||||
fclose(fp);
|
||||
fatal("ERROR: The disk image is not complete - could not write header!");
|
||||
}
|
||||
|
||||
fileset(fp, 0xff, 4 * dtoh32(header.numpages));
|
||||
|
||||
sizesofar = SPARSE_HEADER_SIZE + (4 * dtoh32(header.numpages));
|
||||
padtopagesize = dtoh32(header.pagesize) - (sizesofar & (dtoh32(header.pagesize) - 1));
|
||||
|
||||
fileset(fp, 0, padtopagesize);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* produce a growing image file */
|
||||
int make_growing_image(FILE *fp, Bit64u sec)
|
||||
{
|
||||
redolog_header_t header;
|
||||
Bit32u i, not_allocated = htod32(REDOLOG_PAGE_NOT_ALLOCATED);
|
||||
|
||||
memset(&header, 0, sizeof(header));
|
||||
make_redolog_header(&header, REDOLOG_SUBTYPE_GROWING, sec * 512);
|
||||
|
||||
if (fwrite(&header, sizeof(header), 1, fp) != 1) {
|
||||
fclose(fp);
|
||||
fatal("ERROR: The disk image is not complete - could not write header!");
|
||||
}
|
||||
|
||||
for (i=0; i<dtoh32(header.specific.catalog); i++) {
|
||||
if (fwrite(¬_allocated, sizeof(Bit32u), 1, fp) != 1) {
|
||||
fclose(fp);
|
||||
fatal("ERROR: The disk image is not complete - could not write catalog!");
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* produce the image file */
|
||||
#ifdef WIN32
|
||||
int make_image_win32 (Bit64u sec, char *filename, WRITE_IMAGE_WIN32 write_image)
|
||||
{
|
||||
HANDLE hFile;
|
||||
char buffer[1024];
|
||||
|
||||
// check if it exists before trashing someone's disk image
|
||||
hFile = CreateFile(filename, GENERIC_READ, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL , NULL);
|
||||
if (hFile != INVALID_HANDLE_VALUE) {
|
||||
int confirm;
|
||||
sprintf(buffer, "\nThe disk image '%s' already exists. Are you sure you want to replace it?\nPlease type yes or no. ", filename);
|
||||
if (ask_yn(buffer, 0, &confirm) < 0)
|
||||
fatal(EOF_ERR);
|
||||
if (!confirm)
|
||||
fatal("ERROR: Aborted");
|
||||
CloseHandle(hFile);
|
||||
}
|
||||
|
||||
// okay, now open it for writing
|
||||
hFile = CreateFile(filename, GENERIC_WRITE|GENERIC_READ, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
|
||||
if (hFile == INVALID_HANDLE_VALUE) {
|
||||
// attempt to print an error
|
||||
#ifdef HAVE_PERROR
|
||||
sprintf(buffer, "while opening '%s' for writing", filename);
|
||||
perror(buffer);
|
||||
#endif
|
||||
fatal("ERROR: Could not write disk image");
|
||||
}
|
||||
|
||||
printf("\nWriting: [");
|
||||
|
||||
if((*write_image)(hFile, sec) != 0)
|
||||
fatal("ERROR: while writing disk image!");
|
||||
|
||||
printf("] Done.\n");
|
||||
CloseHandle(hFile);
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
int make_image(Bit64u sec, char *filename, WRITE_IMAGE write_image)
|
||||
{
|
||||
FILE *fp;
|
||||
char buffer[1024];
|
||||
|
||||
// check if it exists before trashing someone's disk image
|
||||
fp = fopen(filename, "r");
|
||||
if (fp) {
|
||||
int confirm;
|
||||
sprintf(buffer, "\nThe disk image '%s' already exists. Are you sure you want to replace it?\nPlease type yes or no. ", filename);
|
||||
if (ask_yn(buffer, 0, &confirm) < 0)
|
||||
fatal(EOF_ERR);
|
||||
if (!confirm)
|
||||
fatal("ERROR: Aborted");
|
||||
fclose(fp);
|
||||
}
|
||||
|
||||
// okay, now open it for writing
|
||||
fp = fopen(filename, "w");
|
||||
if (fp == NULL) {
|
||||
// attempt to print an error
|
||||
#ifdef HAVE_PERROR
|
||||
sprintf(buffer, "while opening '%s' for writing", filename);
|
||||
perror(buffer);
|
||||
#endif
|
||||
fatal("ERROR: Could not write disk image");
|
||||
}
|
||||
|
||||
printf("\nWriting: [");
|
||||
|
||||
if((*write_image)(fp, sec) != 0)
|
||||
fatal("ERROR: while writing disk image!");
|
||||
|
||||
printf("] Done.\n");
|
||||
fclose(fp);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void print_usage()
|
||||
{
|
||||
fprintf(stderr,
|
||||
"Usage: bximage [options] [filename]\n\n"
|
||||
"Supported options:\n"
|
||||
" -fd create floppy image\n"
|
||||
" -hd create hard disk image\n"
|
||||
" -mode=... image mode (hard disks only)\n"
|
||||
" -size=... image size in megabytes\n"
|
||||
" -q quiet mode (don't prompt for user input)\n"
|
||||
" --help display this help and exit\n\n");
|
||||
}
|
||||
|
||||
int parse_cmdline(int argc, char *argv[])
|
||||
{
|
||||
int arg = 1;
|
||||
int ret = 1;
|
||||
|
||||
bx_hdimage = -1;
|
||||
bx_fdsize_idx = -1;
|
||||
bx_hdsize = -1;
|
||||
bx_hdimagemode = -1;
|
||||
bx_interactive = 1;
|
||||
bx_filename[0] = 0;
|
||||
while ((arg < argc) && (ret == 1)) {
|
||||
// parse next arg
|
||||
if (!strcmp("--help", argv[arg]) || !strncmp("/?", argv[arg], 2)) {
|
||||
print_usage();
|
||||
ret = 0;
|
||||
}
|
||||
else if (!strcmp("-fd", argv[arg])) {
|
||||
bx_hdimage = 0;
|
||||
bx_hdimagemode = 0;
|
||||
}
|
||||
else if (!strcmp("-hd", argv[arg])) {
|
||||
bx_hdimage = 1;
|
||||
bx_fdsize_idx = 0;
|
||||
}
|
||||
else if (!strncmp("-mode=", argv[arg], 6)) {
|
||||
if (bx_hdimage == 1) {
|
||||
bx_hdimagemode = get_menu_index(&argv[arg][6], hdmode_n_choices, hdmode_choices);
|
||||
if (bx_hdimagemode < 0) {
|
||||
printf("Unknown image mode: %s\n\n", &argv[arg][6]);
|
||||
ret = 0;
|
||||
}
|
||||
} else {
|
||||
printf("Image mode option only supported for hard disks\n\n");
|
||||
ret = 0;
|
||||
}
|
||||
}
|
||||
else if (!strncmp("-size=", argv[arg], 6)) {
|
||||
if (bx_hdimage == 0) {
|
||||
bx_fdsize_idx = get_menu_index(&argv[arg][6], fdsize_n_choices, fdsize_choices);
|
||||
if (bx_fdsize_idx < 0) {
|
||||
printf("Unknown floppy image size: %s\n\n", &argv[arg][6]);
|
||||
ret = 0;
|
||||
}
|
||||
} else if (bx_hdimage == 1) {
|
||||
if (sscanf(&argv[arg][6], "%d", &bx_hdsize) != 1) {
|
||||
printf("Error in hard disk image size argument: %s\n\n", &argv[arg][6]);
|
||||
ret = 0;
|
||||
} else if ((bx_hdsize < 1) || (bx_hdsize > 32255)) {
|
||||
printf("Hard disk image size out of range\n\n");
|
||||
ret = 0;
|
||||
}
|
||||
} else {
|
||||
printf("Image type (fd/hd) not specified\n\n");
|
||||
}
|
||||
}
|
||||
else if (!strcmp("-q", argv[arg])) {
|
||||
bx_interactive = 0;
|
||||
}
|
||||
else if (argv[arg][0] == '-') {
|
||||
printf("Unknown option: %s\n\n", argv[arg]);
|
||||
ret = 0;
|
||||
} else {
|
||||
strcpy(bx_filename, argv[arg]);
|
||||
}
|
||||
arg++;
|
||||
}
|
||||
if (bx_hdimage == -1) {
|
||||
bx_hdimage = 1;
|
||||
bx_fdsize_idx = 6;
|
||||
bx_interactive = 1;
|
||||
}
|
||||
if (bx_hdimage == 1) {
|
||||
if (bx_hdimagemode == -1) {
|
||||
bx_hdimagemode = 0;
|
||||
bx_interactive = 1;
|
||||
}
|
||||
if (bx_hdsize == -1) {
|
||||
bx_hdsize = 10;
|
||||
bx_interactive = 1;
|
||||
}
|
||||
} else {
|
||||
if (bx_fdsize_idx == -1) {
|
||||
bx_fdsize_idx = 6;
|
||||
bx_interactive = 1;
|
||||
}
|
||||
}
|
||||
if (!strlen(bx_filename)) {
|
||||
bx_interactive = 1;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
int CDECL main(int argc, char *argv[])
|
||||
{
|
||||
Bit64s sectors = 0;
|
||||
char filename[256];
|
||||
char bochsrc_line[256];
|
||||
|
||||
WRITE_IMAGE write_function=NULL;
|
||||
#ifdef WIN32
|
||||
WRITE_IMAGE_WIN32 writefn_win32=NULL;
|
||||
#endif
|
||||
|
||||
if (!parse_cmdline(argc, argv))
|
||||
myexit(1);
|
||||
|
||||
print_banner();
|
||||
if (bx_interactive) {
|
||||
if (ask_menu(fdhd_menu, fdhd_n_choices, fdhd_choices, bx_hdimage, &bx_hdimage) < 0)
|
||||
fatal(EOF_ERR);
|
||||
}
|
||||
if (bx_hdimage) {
|
||||
unsigned int cyl;
|
||||
int hdsize, heads=16, spt=63;
|
||||
int mode;
|
||||
|
||||
if (bx_interactive) {
|
||||
if (ask_menu(hdmode_menu, hdmode_n_choices, hdmode_choices, bx_hdimagemode, &mode) < 0)
|
||||
fatal (EOF_ERR);
|
||||
if (ask_int("\nEnter the hard disk size in megabytes, between 1 and 129023\n", 1, 129023, bx_hdsize, &hdsize) < 0)
|
||||
fatal(EOF_ERR);
|
||||
} else {
|
||||
mode = bx_hdimagemode;
|
||||
hdsize = bx_hdsize;
|
||||
}
|
||||
cyl = (unsigned int) (hdsize*1024.0*1024.0/16.0/63.0/512.0);
|
||||
assert (cyl < 262144);
|
||||
sectors = cyl*heads*spt;
|
||||
printf("\nI will create a '%s' hard disk image with\n", hdmode_choices[mode]);
|
||||
printf(" cyl=%d\n", cyl);
|
||||
printf(" heads=%d\n", heads);
|
||||
printf(" sectors per track=%d\n", spt);
|
||||
printf(" total sectors=" FMT_LL "d\n", sectors);
|
||||
printf(" total size=%.2f megabytes\n", (float)(Bit64s)(sectors/2)/1024.0);
|
||||
if (bx_interactive) {
|
||||
if (!strlen(bx_filename)) strcpy(bx_filename, "c.img");
|
||||
if (ask_string("\nWhat should I name the image?\n", bx_filename, filename) < 0)
|
||||
fatal(EOF_ERR);
|
||||
} else {
|
||||
strcpy(filename, bx_filename);
|
||||
}
|
||||
|
||||
sprintf(bochsrc_line, "ata0-master: type=disk, path=\"%s\", mode=%s, cylinders=%d, heads=%d, spt=%d", filename, hdmode_choices[mode], cyl, heads, spt);
|
||||
|
||||
switch (mode) {
|
||||
case 1:
|
||||
write_function=make_sparse_image;
|
||||
break;
|
||||
case 2:
|
||||
write_function=make_growing_image;
|
||||
break;
|
||||
default:
|
||||
#ifdef WIN32
|
||||
writefn_win32=make_flat_image_win32;
|
||||
#else
|
||||
write_function=make_flat_image;
|
||||
#endif
|
||||
}
|
||||
} else {
|
||||
int fdsize, cyl=0, heads=0, spt=0;
|
||||
if (bx_interactive) {
|
||||
if (ask_menu(fdsize_menu, fdsize_n_choices, fdsize_choices, bx_fdsize_idx, &fdsize) < 0)
|
||||
fatal(EOF_ERR);
|
||||
} else {
|
||||
fdsize = bx_fdsize_idx;
|
||||
}
|
||||
switch (fdsize) {
|
||||
case 0: cyl=40; heads=1; spt=8; break; /* 0.16 meg */
|
||||
case 1: cyl=40; heads=1; spt=9; break; /* 0.18 meg */
|
||||
case 2: cyl=40; heads=2; spt=8; break; /* 0.32 meg */
|
||||
case 3: cyl=40; heads=2; spt=9; break; /* 0.36 meg */
|
||||
case 4: cyl=80; heads=2; spt=9; break; /* 0.72 meg */
|
||||
case 5: cyl=80; heads=2; spt=15; break; /* 1.2 meg */
|
||||
case 6: cyl=80; heads=2; spt=18; break; /* 1.44 meg */
|
||||
case 7: cyl=80; heads=2; spt=21; break; /* 1.68 meg */
|
||||
case 8: cyl=82; heads=2; spt=21; break; /* 1.72 meg */
|
||||
case 9: cyl=80; heads=2; spt=36; break; /* 2.88 meg */
|
||||
default:
|
||||
fatal("ERROR: fdsize out of range");
|
||||
}
|
||||
sectors = cyl*heads*spt;
|
||||
printf("I will create a floppy image with\n");
|
||||
printf(" cyl=%d\n", cyl);
|
||||
printf(" heads=%d\n", heads);
|
||||
printf(" sectors per track=%d\n", spt);
|
||||
printf(" total sectors=" FMT_LL "d\n", sectors);
|
||||
printf(" total bytes=" FMT_LL "d\n", sectors*512);
|
||||
if (bx_interactive) {
|
||||
if (!strlen(bx_filename)) strcpy(bx_filename, "a.img");
|
||||
if (ask_string("\nWhat should I name the image?\n", bx_filename, filename) < 0)
|
||||
fatal(EOF_ERR);
|
||||
} else {
|
||||
strcpy(filename, bx_filename);
|
||||
}
|
||||
sprintf(bochsrc_line, "floppya: image=\"%s\", status=inserted", filename);
|
||||
|
||||
write_function=make_flat_image;
|
||||
}
|
||||
if (sectors < 1)
|
||||
fatal("ERROR: Illegal disk size!");
|
||||
if (strlen (filename) < 1)
|
||||
fatal("ERROR: Illegal filename");
|
||||
#ifdef WIN32
|
||||
if (writefn_win32 != NULL) {
|
||||
make_image_win32(sectors, filename, writefn_win32);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
make_image(sectors, filename, write_function);
|
||||
}
|
||||
printf("\nI wrote " FMT_LL "u bytes to ", sectors*512);
|
||||
printf("%s.\n", filename);
|
||||
printf("\nThe following line should appear in your bochsrc:\n");
|
||||
printf(" %s\n", bochsrc_line);
|
||||
#ifdef WIN32
|
||||
if (OpenClipboard(NULL)) {
|
||||
HGLOBAL hgClip;
|
||||
EmptyClipboard();
|
||||
hgClip = GlobalAlloc(GMEM_DDESHARE, (strlen(bochsrc_line) + 1));
|
||||
strcpy((char *)GlobalLock(hgClip), bochsrc_line);
|
||||
GlobalUnlock(hgClip);
|
||||
SetClipboardData(CF_TEXT, hgClip);
|
||||
CloseClipboard();
|
||||
printf("(The line is stored in your windows clipboard, use CTRL-V to paste)\n");
|
||||
}
|
||||
#endif
|
||||
myexit(0);
|
||||
|
||||
// make picky compilers (c++, gcc) happy,
|
||||
// even though we leave via 'myexit' just above
|
||||
return 0;
|
||||
}
|
||||
103
simulators/bochs/misc/make_cmos_image.cc
Normal file
103
simulators/bochs/misc/make_cmos_image.cc
Normal file
@ -0,0 +1,103 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id$
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
//
|
||||
// MandrakeSoft S.A.
|
||||
// 43, rue d'Aboukir
|
||||
// 75002 Paris - France
|
||||
// http://www.linux-mandrake.com/
|
||||
// http://www.mandrakesoft.com/
|
||||
//
|
||||
// This library is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU Lesser General Public
|
||||
// License as published by the Free Software Foundation; either
|
||||
// version 2 of the License, or (at your option) any later version.
|
||||
//
|
||||
// This library is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
// Lesser General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Lesser General Public
|
||||
// License along with this library; if not, write to the Free Software
|
||||
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
|
||||
// Program which generates sample CMOS image files
|
||||
|
||||
|
||||
|
||||
extern "C" {
|
||||
#include <stdio.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
}
|
||||
|
||||
|
||||
#if 1
|
||||
unsigned char cmos[] = {
|
||||
0x29, 0x2b, 0x30, 0x2b, 0x16, 0x0b, 0x00, 0x01,
|
||||
0x01, 0x96, 0x26, 0x02, 0x50, 0x80, 0x00, 0x00,
|
||||
0x40, 0x8f, 0xf0, 0xc0, 0x3f, 0x80, 0x02, 0x00,
|
||||
0x3c, 0x2f, 0x00, 0x4c, 0x0c, 0x10, 0x00, 0x00,
|
||||
0x3f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x48, 0x2b, 0x03, 0x03, 0x03, 0x04, 0xce,
|
||||
0x00, 0x3c, 0x19, 0xff, 0xff, 0xf0, 0x00, 0xf0,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x7b
|
||||
};
|
||||
|
||||
#else
|
||||
unsigned char cmos[] = {
|
||||
0x29, 0x2b, 0x30, 0x2b, 0x16, 0x0b, 0x00, 0x01,
|
||||
0x01, 0x96, 0x26, 0x02, 0x50, 0x80, 0x00, 0x00,
|
||||
0x40, 0x8f, 0xf0, 0xc0, 0x0f, 0x80, 0x02, 0x00,
|
||||
0x3c, 0x2f, 0x00, 0x1e, 0x00, 0x04, 0xff, 0xff,
|
||||
0x11, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x08, 0x08, 0x03, 0x03, 0x03, 0x05, 0xc5,
|
||||
0x00, 0x3c, 0x00, 0x00, 0x00, 0xf0, 0x00, 0x10,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x21, // 0x21
|
||||
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x10, // 50
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // 60
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // 70
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
|
||||
};
|
||||
#endif
|
||||
|
||||
int
|
||||
main(int argc, char *argv[])
|
||||
{
|
||||
int fd, ret;
|
||||
|
||||
if (argc != 2) {
|
||||
fprintf(stderr, "usage: %s pathname\n", argv[0]);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
fd = open(argv[1], O_WRONLY | O_CREAT
|
||||
#ifdef O_BINARY
|
||||
| O_BINARY
|
||||
#endif
|
||||
, S_IRUSR | S_IWUSR
|
||||
);
|
||||
if (fd < 0) {
|
||||
perror("trying to open cmos image file to write.\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
ret = write(fd, cmos, sizeof(cmos));
|
||||
if (ret != sizeof(cmos)) {
|
||||
perror("write() did not write all CMOS data.\n");
|
||||
exit(1);
|
||||
}
|
||||
printf("CMOS data successfuly written to file '%s'.\n", argv[1]);
|
||||
}
|
||||
187
simulators/bochs/misc/niclist.c
Normal file
187
simulators/bochs/misc/niclist.c
Normal file
@ -0,0 +1,187 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// misc/niclist.c
|
||||
// by Don Becker <x-odus@iname.com>
|
||||
// $Id$
|
||||
//
|
||||
// This program is for win32 only. It lists the network interface cards
|
||||
// that you can use in the "ethdev" field of the ne2k line in your bochsrc.
|
||||
//
|
||||
// For this program and for win32 ethernet, the winpcap library is required.
|
||||
// Download it from http://www.winpcap.org/
|
||||
//
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifndef WIN32
|
||||
#error Niclist will only work on WIN32 platforms.
|
||||
#endif
|
||||
|
||||
#include <windows.h>
|
||||
#include <stdio.h>
|
||||
#include <conio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#define MAX_ADAPTERS 10
|
||||
#define NIC_BUFFER_SIZE 2048
|
||||
|
||||
// declare our NT/9X structures to hold the adapter name and descriptions
|
||||
typedef struct {
|
||||
LPWSTR wstrName;
|
||||
LPSTR strDesc;
|
||||
} NIC_INFO_NT;
|
||||
|
||||
typedef struct {
|
||||
LPSTR strName;
|
||||
LPSTR strDesc;
|
||||
} NIC_INFO_9X;
|
||||
|
||||
// declare an array of structures to hold our adapter information
|
||||
NIC_INFO_NT niNT[MAX_ADAPTERS];
|
||||
NIC_INFO_9X ni9X[MAX_ADAPTERS];
|
||||
|
||||
BOOLEAN (*PacketGetAdapterNames)(PTSTR, PULONG) = NULL;
|
||||
PCHAR (*PacketGetVersion)() = NULL;
|
||||
|
||||
void myexit (int code)
|
||||
{
|
||||
printf ("\nPress any key to continue\n");
|
||||
getch();
|
||||
exit(code);
|
||||
}
|
||||
|
||||
int CDECL main(int argc, char **argv)
|
||||
{
|
||||
int i;
|
||||
HINSTANCE hPacket;
|
||||
DWORD dwVersion, dwMajorVersion;
|
||||
char AdapterInfo[NIC_BUFFER_SIZE] = { '\0','\0' };
|
||||
unsigned long AdapterLength = NIC_BUFFER_SIZE;
|
||||
LPWSTR wstrName;
|
||||
LPSTR strName, strDesc;
|
||||
int nAdapterCount;
|
||||
PCHAR dllVersion;
|
||||
PCHAR testString;
|
||||
int nDLLMajorVersion, nDLLMinorVersion;
|
||||
|
||||
// Attemp to load the WinpCap packet library
|
||||
hPacket = LoadLibrary("PACKET.DLL");
|
||||
if(hPacket)
|
||||
{
|
||||
// Now look up the address
|
||||
PacketGetAdapterNames = (BOOLEAN (*)(PTSTR, PULONG))GetProcAddress(hPacket, "PacketGetAdapterNames");
|
||||
PacketGetVersion = (PCHAR (*)())GetProcAddress(hPacket, "PacketGetVersion");
|
||||
}
|
||||
else {
|
||||
printf("Could not load WinPCap driver!\n");
|
||||
printf ("You can download them for free from\n");
|
||||
printf ("http://www.winpcap.org/\n");
|
||||
myexit(1);
|
||||
}
|
||||
|
||||
dwVersion = GetVersion();
|
||||
dwMajorVersion = (DWORD)(LOBYTE(LOWORD(dwVersion)));
|
||||
|
||||
// Get DLL Version and Tokenize
|
||||
dllVersion = PacketGetVersion();
|
||||
nDLLMajorVersion = -1;
|
||||
nDLLMinorVersion = -1;
|
||||
for (testString = strtok(dllVersion, ",. ");
|
||||
testString != NULL; testString = strtok(NULL, ",. "))
|
||||
{
|
||||
// If Single Character, Convert
|
||||
if (strlen( testString ) == 1)
|
||||
{
|
||||
// Check Major First
|
||||
if (nDLLMajorVersion == -1)
|
||||
{
|
||||
nDLLMajorVersion = atoi(testString);
|
||||
}
|
||||
else if ( nDLLMinorVersion == -1 )
|
||||
{
|
||||
nDLLMinorVersion = atoi(testString);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Get out blob of adapter info
|
||||
PacketGetAdapterNames(AdapterInfo,&AdapterLength);
|
||||
|
||||
// If this is Windows NT ... And DLL Returns UNICODE
|
||||
if(!(dwVersion >= 0x80000000 && dwMajorVersion >= 4) &&
|
||||
(nDLLMajorVersion < 3 || (nDLLMajorVersion == 3 && nDLLMinorVersion < 1)))
|
||||
{
|
||||
wstrName=(LPWSTR)AdapterInfo;
|
||||
|
||||
// Obtain Names
|
||||
nAdapterCount = 0;
|
||||
while ((*wstrName))
|
||||
{
|
||||
// store pointer to name
|
||||
niNT[nAdapterCount].wstrName=wstrName;
|
||||
wstrName += lstrlenW(wstrName) +1;
|
||||
nAdapterCount++;
|
||||
}
|
||||
|
||||
strDesc = (LPSTR)++wstrName;
|
||||
|
||||
// Obtain descriptions ....
|
||||
for(i=0;i<nAdapterCount;i++)
|
||||
{
|
||||
// store pointer to description
|
||||
niNT[i].strDesc=strDesc;
|
||||
strDesc += lstrlen(strDesc) +1;
|
||||
|
||||
// ... and display adapter info
|
||||
printf("\n%d: %s\n",i+1,niNT[i].strDesc);
|
||||
wprintf(L" Device: %s",niNT[i].wstrName);
|
||||
}
|
||||
|
||||
if(i) {
|
||||
printf("\n\nExample config for bochsrc:\n");
|
||||
wprintf(L"ne2k: ioaddr=0x300, irq=3, mac=b0:c4:20:00:00:00, ethmod=win32, ethdev=%s",niNT[0].wstrName);
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
// Windows 9x
|
||||
strName=(LPSTR)AdapterInfo;
|
||||
|
||||
// Obtain Names
|
||||
nAdapterCount = 0;
|
||||
while ((*strName))
|
||||
{
|
||||
// store pointer to name
|
||||
ni9X[nAdapterCount].strName=strName;
|
||||
strName += lstrlen(strName) +1;
|
||||
nAdapterCount++;
|
||||
}
|
||||
|
||||
strDesc = (LPSTR)++strName;
|
||||
|
||||
// Obtain descriptions ....
|
||||
for(i=0;i<nAdapterCount;i++)
|
||||
{
|
||||
// store pointer to description
|
||||
ni9X[i].strDesc=strDesc;
|
||||
strDesc += lstrlen(strDesc) +1;
|
||||
|
||||
// ... and display adapter info
|
||||
printf("\n%d: %s\n",i+1,ni9X[i].strDesc);
|
||||
printf(" Device: %s",ni9X[i].strName);
|
||||
}
|
||||
|
||||
if(i)
|
||||
{
|
||||
printf("\n\nExample config for bochsrc:\n");
|
||||
printf("ne2k: ioaddr=0x300, irq=3, mac=b0:c4:20:00:00:00, ethmod=win32, ethdev=%s",ni9X[0].strName);
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
myexit (0);
|
||||
return 0; /* shut up stupid compilers */
|
||||
}
|
||||
502
simulators/bochs/misc/sb16/sb16ctrl.c
Normal file
502
simulators/bochs/misc/sb16/sb16ctrl.c
Normal file
@ -0,0 +1,502 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id$
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
//
|
||||
// MandrakeSoft S.A.
|
||||
// 43, rue d'Aboukir
|
||||
// 75002 Paris - France
|
||||
// http://www.linux-mandrake.com/
|
||||
// http://www.mandrakesoft.com/
|
||||
//
|
||||
// This library is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU Lesser General Public
|
||||
// License as published by the Free Software Foundation; either
|
||||
// version 2 of the License, or (at your option) any later version.
|
||||
//
|
||||
// This library is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
// Lesser General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Lesser General Public
|
||||
// License along with this library; if not, write to the Free Software
|
||||
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
// This file (SB16CTRL.C) written and donated by Josef Drexler
|
||||
|
||||
|
||||
|
||||
|
||||
// The purpose of this program is to provide runtime configuration
|
||||
// options to the SB16 Emulator until Bochs has a more sophisticated
|
||||
// user interface allowing to do these things better.
|
||||
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
|
||||
#ifdef dos
|
||||
# include <dos.h>
|
||||
#endif
|
||||
|
||||
#if defined(__linux__) || defined(__GNU__) || defined(__GLIBC__)
|
||||
# include <sys/io.h>
|
||||
# include <errno.h>
|
||||
# define inp inb
|
||||
# define outp(a,b) outb(b,a)
|
||||
#endif
|
||||
|
||||
/*
|
||||
#define DEBUG
|
||||
*/
|
||||
|
||||
#define EMULPORT 0x333
|
||||
|
||||
int checked = 0;
|
||||
int filelevel = 0;
|
||||
int verbose = 0;
|
||||
char ofline[256] = " in the command line";
|
||||
|
||||
/******************************
|
||||
* System dependent functions *
|
||||
******************************/
|
||||
|
||||
/* Read a value from the emulator port */
|
||||
int reademul()
|
||||
{
|
||||
return inp(EMULPORT);
|
||||
}
|
||||
|
||||
/* Write a value to the emulator port */
|
||||
void writeemul(int value)
|
||||
{
|
||||
outp(EMULPORT, value);
|
||||
}
|
||||
|
||||
/* Enable access to the emulator port */
|
||||
void enableport()
|
||||
{
|
||||
#if defined(__linux__) || defined(__GNU__) || defined(__GLIBC__)
|
||||
if (ioperm(EMULPORT, 1, 1)) {
|
||||
printf("Could not access emulator port %03x: %s.\n", EMULPORT, strerror(errno));
|
||||
exit(1);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/********************************
|
||||
* System independent functions *
|
||||
********************************/
|
||||
|
||||
/* Forward definitions*/
|
||||
void command(int cmd, char *arg);
|
||||
void checkemulator();
|
||||
|
||||
/* Convert a string into a number */
|
||||
int strtoi(char *nptr, char **endptr, int base)
|
||||
{
|
||||
int value, digit;
|
||||
int sign = 1;
|
||||
|
||||
/* Skip leading white space */
|
||||
while( isspace(*nptr) )
|
||||
nptr++;
|
||||
|
||||
/* Check if there is a sign */
|
||||
if (*nptr == '-')
|
||||
{
|
||||
sign = -1;
|
||||
nptr++;
|
||||
}
|
||||
else if (*nptr == '+')
|
||||
{
|
||||
sign = 1;
|
||||
nptr++;
|
||||
}
|
||||
|
||||
/* Check the base if undefined and determine it */
|
||||
if (base == 0)
|
||||
{
|
||||
if (*nptr == '0')
|
||||
{
|
||||
nptr++;
|
||||
if ( (*nptr == 'x') ||
|
||||
(*nptr == 'X') )
|
||||
{
|
||||
nptr++;
|
||||
base = 16;
|
||||
}
|
||||
else
|
||||
base = 8;
|
||||
}
|
||||
else
|
||||
base = 10;
|
||||
}
|
||||
|
||||
/* Convert the number */
|
||||
value = 0;
|
||||
digit = -1;
|
||||
while ( isalnum(*nptr) )
|
||||
{
|
||||
if ( isdigit(*nptr) )
|
||||
digit = *nptr - '0';
|
||||
else
|
||||
digit = tolower(*nptr) - 'a' + 10;
|
||||
|
||||
if ( (digit >= base) || (digit < 0) )
|
||||
break; /* Isn't a valid char, abort conversion */
|
||||
|
||||
value = value * base + digit;
|
||||
nptr++;
|
||||
}
|
||||
|
||||
if (endptr != NULL)
|
||||
*endptr = nptr;
|
||||
|
||||
return sign * value;
|
||||
}
|
||||
|
||||
/* Print the command line usage */
|
||||
void usage()
|
||||
{
|
||||
printf("SB16 emulator control program for Bochs.\n"
|
||||
"\n"
|
||||
"Usage: sb16ctrl [-i #] [-t #,#,#,#,#,#] [-r] [-m #,..] [-f filename]\n"
|
||||
"\n"
|
||||
"This program is used to control the operation of the SB16 emulator\n"
|
||||
"until it has a more sophisticated interface.\n"
|
||||
"Any number of commands can be given. If none are present \"-f -\"\n"
|
||||
"is assumed.\n"
|
||||
"\n"
|
||||
"-i # show the selected emulator info string\n"
|
||||
"-t #,#,#,#,#,# load the patch translation into the emulator\n"
|
||||
"-r resets the patch translation table\n"
|
||||
"-m #,... sends the given midi message (up to 255 bytes)\n"
|
||||
"-f filename loads commands from the given file, or stdin if \"-\"\n"
|
||||
"-v be verbose\n"
|
||||
"\n"
|
||||
"# can be decimal, octal (first digit 0) or hexadecimal (0x..)\n"
|
||||
"\n"
|
||||
);
|
||||
}
|
||||
|
||||
/* Execute the given command */
|
||||
void emulcommand(int command)
|
||||
{
|
||||
if (checked == 0)
|
||||
checkemulator();
|
||||
|
||||
writeemul(command);
|
||||
}
|
||||
|
||||
/* Check if we got the expected response */
|
||||
int testemul(int value, char *msg)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (checked == 0)
|
||||
checkemulator();
|
||||
|
||||
i = reademul();
|
||||
#ifndef DEBUG
|
||||
if ( (i != value) && (msg) )
|
||||
{
|
||||
printf("Bochs emulator/SB16 error: %s\n", msg);
|
||||
exit(1);
|
||||
}
|
||||
#endif
|
||||
return i;
|
||||
}
|
||||
|
||||
/* Check if we are running inside the emulator */
|
||||
void checkemulator()
|
||||
{
|
||||
int i;
|
||||
|
||||
checked = 1;
|
||||
|
||||
enableport();
|
||||
|
||||
/* Check emulator status */
|
||||
for (i=0; i<9; i++)
|
||||
writeemul(1); /* Clear input queue */
|
||||
writeemul(10); /* Check Emulator present */
|
||||
testemul(254, "no check ACK: Emulator not present");
|
||||
testemul(0x55, "Emulator not present"); /* should return 0x55 */
|
||||
}
|
||||
|
||||
/* Read internal emulator string and print it */
|
||||
void showemul(int i)
|
||||
{
|
||||
int j;
|
||||
|
||||
emulcommand(5); /* 5 means dump info */
|
||||
writeemul(i); /* Argument to command 5; info number */
|
||||
testemul(254, "no info ACK");
|
||||
printf("Emulator info string %d:", i);
|
||||
do {
|
||||
j = reademul();
|
||||
if (j == 255)
|
||||
break;
|
||||
printf("%c", j);
|
||||
} while (j != 10);
|
||||
}
|
||||
|
||||
/* Process a string - change "," and "/" into a space,
|
||||
and ignore everything after comments "#" */
|
||||
void procstr(char *str)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i=0; str[i] != 0; i++)
|
||||
switch(str[i])
|
||||
{
|
||||
case ',':
|
||||
case '/':
|
||||
case 10:
|
||||
case 13:
|
||||
str[i] = ' ';
|
||||
break;
|
||||
case '#':
|
||||
str[i] = 0;
|
||||
str[i+1] = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Upload a mapping to the emulator */
|
||||
void loadmap(char *map)
|
||||
{
|
||||
int i;
|
||||
int trans[6];
|
||||
char *nextnum;
|
||||
|
||||
procstr(map);
|
||||
|
||||
nextnum = map;
|
||||
for (i=0;i<6;i++) {
|
||||
if (nextnum) {
|
||||
trans[i] = strtoi(nextnum, &nextnum, 0);
|
||||
if ( (!nextnum) ||
|
||||
( (trans[i] > 127) && (trans[i] < 255) ) ||
|
||||
(trans[i] > 255) )
|
||||
printf("Parse error in value %d%s. Command ignored.", i, ofline);
|
||||
}
|
||||
if (!nextnum)
|
||||
trans[i] = 255;
|
||||
}
|
||||
|
||||
/* Load the remap into the emulator, command 4 */
|
||||
emulcommand(4); /* 4 load remap */
|
||||
testemul(254, "no load remap ACK");
|
||||
|
||||
for (i=0;i<6;i++)
|
||||
writeemul(trans[i]);
|
||||
|
||||
testemul(6, "insufficient data"); /* test receipt of 6 arguments */
|
||||
}
|
||||
|
||||
/* Reset the translation table */
|
||||
void resettable()
|
||||
{
|
||||
emulcommand(7);
|
||||
testemul(254, "no table reset ACK");
|
||||
}
|
||||
|
||||
/* Send a series of midi bytes to the sound device */
|
||||
void loadmidi(char *msg)
|
||||
{
|
||||
int i;
|
||||
|
||||
procstr(msg);
|
||||
|
||||
while ( (msg) && (*msg) ) {
|
||||
i = strtoi(msg, &msg, 0);
|
||||
|
||||
emulcommand(11); /* 11: Send midi data byte */
|
||||
writeemul(i);
|
||||
testemul(254, "no midi data ACK");
|
||||
}
|
||||
}
|
||||
|
||||
/* read a file of commands */
|
||||
void loadfile(char *filename)
|
||||
{
|
||||
FILE *file;
|
||||
char cmd;
|
||||
char *pos;
|
||||
char msg[256];
|
||||
int lineno = 0;
|
||||
|
||||
filelevel++;
|
||||
if (filelevel > 10)
|
||||
{
|
||||
printf("Error - Too many nested \"f\" commands.\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if (strcmp(filename, "-") == 0)
|
||||
file = stdin;
|
||||
else
|
||||
file = fopen(filename, "r");
|
||||
|
||||
if (!file) {
|
||||
printf("File %s not found.\n", filename);
|
||||
return;
|
||||
}
|
||||
|
||||
while (!feof(file)) {
|
||||
fgets(msg, sizeof msg, file);
|
||||
lineno++;
|
||||
|
||||
pos = msg;
|
||||
|
||||
procstr(msg);
|
||||
|
||||
while ( (*pos == ' ') || (*pos == 9) )
|
||||
pos++;
|
||||
|
||||
if (*pos)
|
||||
cmd = *pos++;
|
||||
else
|
||||
continue;
|
||||
|
||||
if (cmd == '#') /* it's a comment */
|
||||
continue;
|
||||
while ( (*pos == ' ') || (*pos == 9) )
|
||||
pos++;
|
||||
|
||||
sprintf(ofline, " in line %d of file %s", lineno, filename);
|
||||
|
||||
command(cmd, pos);
|
||||
}
|
||||
if (strcmp(filename, "-") != 0)
|
||||
fclose(file);
|
||||
|
||||
filelevel--;
|
||||
}
|
||||
|
||||
void command(int cmd, char *arg)
|
||||
{
|
||||
if (verbose)
|
||||
{
|
||||
if (arg)
|
||||
printf("Executing command %c %s%s\n", cmd, arg, ofline);
|
||||
else
|
||||
printf("Executing command %c %s\n", cmd, ofline);
|
||||
}
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
case 't':
|
||||
loadmap(arg);
|
||||
break;
|
||||
|
||||
case 'i':
|
||||
showemul(strtoi(arg, NULL, 0));
|
||||
break;
|
||||
|
||||
case 'm':
|
||||
loadmidi(arg);
|
||||
break;
|
||||
|
||||
case 'f':
|
||||
loadfile(arg);
|
||||
break;
|
||||
|
||||
case 'h':
|
||||
usage();
|
||||
break;
|
||||
|
||||
case 'r':
|
||||
resettable();
|
||||
break;
|
||||
|
||||
default:
|
||||
printf("Command %c %s not recognized.\n", cmd, ofline);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int i, opt, optargnum;
|
||||
char *optarg;
|
||||
|
||||
/* No args given, read from stdin */
|
||||
if (argc < 2)
|
||||
{
|
||||
loadfile("-");
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Check command line*/
|
||||
i = 1;
|
||||
while (i < argc)
|
||||
{
|
||||
if ( (argv[i][0] != '/') &&
|
||||
(argv[i][0] != '-') )
|
||||
{
|
||||
printf("Unknown command '%s'.\n"
|
||||
"sb16ctrl -h gives a list of command line options.\n",
|
||||
argv[i]);
|
||||
return 1;
|
||||
}
|
||||
|
||||
optargnum = -1;
|
||||
|
||||
opt = argv[i++][1];
|
||||
|
||||
switch (opt) {
|
||||
case 'h':
|
||||
usage();
|
||||
return 0;
|
||||
|
||||
case 'v':
|
||||
verbose++;
|
||||
break;
|
||||
|
||||
case 'r':
|
||||
optargnum = 0;
|
||||
|
||||
case 't':
|
||||
case 'i':
|
||||
case 'm':
|
||||
case 'f':
|
||||
if (optargnum == -1)
|
||||
optargnum = 1;
|
||||
|
||||
/* Fallthrough for all commands to here */
|
||||
if (optargnum > 0)
|
||||
{
|
||||
if ( (i >= argc) ||
|
||||
(argv[i][0] == '-') ||
|
||||
(argv[i][0] == '/') )
|
||||
{
|
||||
printf("Option '%c' needs an argument.\n"
|
||||
"sb16ctrl -h gives a list of command line options.\n",
|
||||
opt);
|
||||
return 1;
|
||||
}
|
||||
optarg = argv[i++];
|
||||
}
|
||||
else
|
||||
optarg = NULL;
|
||||
|
||||
command(opt, optarg);
|
||||
break;
|
||||
|
||||
default:
|
||||
printf("Unknown option '%c'.\n"
|
||||
"sb16ctrl -h gives a list of command line options.\n",
|
||||
opt);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
36
simulators/bochs/misc/sb16/sb16ctrl.example
Normal file
36
simulators/bochs/misc/sb16/sb16ctrl.example
Normal file
@ -0,0 +1,36 @@
|
||||
#
|
||||
# example for an sb16ctrl file
|
||||
#
|
||||
# comments start with hash character '#' (obviously...)
|
||||
# Numbers can be octal (0...) or hex (0x...) or decimal.
|
||||
#
|
||||
#
|
||||
# first, reset the translation table with command 'r'
|
||||
r
|
||||
|
||||
# then load a few translations.
|
||||
# The format is:
|
||||
# t OldBankMSB OldBankLSB OldProgram NewBankMSB NewBankLSB NewProgram
|
||||
#
|
||||
# All values are in the range of 0-127 or 255.
|
||||
# For old values, 255 means "match any".
|
||||
# For new values, 255 means "don't change".
|
||||
#
|
||||
# When deciding whether a program change is to be remapped, these
|
||||
# remappings are checked first to last, and the first applicable remap
|
||||
# is used.
|
||||
|
||||
# This would map all bank changes to bank 0/0
|
||||
# t 255 255 255 0 0 255
|
||||
# it's commented out, otherwise none of the below changes would
|
||||
# be checked, as this one matches anything.
|
||||
|
||||
t 255 255 0 0 0 19 # remap piano to church organ
|
||||
t 255 255 255 0 0 0 # everything remaining -> piano
|
||||
|
||||
# now show the number of translations that have been loaded
|
||||
i 3
|
||||
|
||||
# and enable GS/GM mode
|
||||
m 0xF0,0x41,0x10,0x42,0x12,0x40,0x00,0x7F,0x00,0x41,0xF7
|
||||
|
||||
BIN
simulators/bochs/misc/sb16/sb16ctrl.exe
Executable file
BIN
simulators/bochs/misc/sb16/sb16ctrl.exe
Executable file
Binary file not shown.
181
simulators/bochs/misc/spoolpipe.c
Normal file
181
simulators/bochs/misc/spoolpipe.c
Normal file
@ -0,0 +1,181 @@
|
||||
/* $Id$
|
||||
*
|
||||
* spoolpipe.c
|
||||
* by Carl Sopchak
|
||||
*
|
||||
* Read a pipe that stays open, send the data to a temp file. Print
|
||||
* the temp file if no new input data is seen within a period of time. This
|
||||
* is useful, e.g., to create separate spool files without exiting a program
|
||||
* that doesn't close it's printer output file.
|
||||
*
|
||||
* ---------------------------------------------------------------------------
|
||||
*
|
||||
* Copyright (c) 2002 Cegis Enterprises, Inc. Syracuse, NY 13215
|
||||
*
|
||||
* ---------------------------------------------------------------------------
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
* as published by the Free Software Foundation; either version 2
|
||||
* of the License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* --------------------------------------------------------------------------
|
||||
* Modification log:
|
||||
*
|
||||
* 2002/05/20 - Initial programming
|
||||
*
|
||||
* --------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#define BUF_SIZE 4*1024
|
||||
#define DEBUG 0
|
||||
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/wait.h>
|
||||
#include <unistd.h>
|
||||
|
||||
int infd, outfd;
|
||||
|
||||
unsigned int delay = 60; // default delay, in seconds
|
||||
unsigned int count_down = 0;
|
||||
|
||||
char buffer[BUF_SIZE];
|
||||
ssize_t readcnt, writecnt;
|
||||
|
||||
int didwait = 0; // have we already waited?
|
||||
int havedata = 0; // have we read anything in?
|
||||
|
||||
int q;
|
||||
|
||||
pid_t pid, wait_pid;
|
||||
int wait_status;
|
||||
|
||||
int main (int argc, char *argv[]) {
|
||||
|
||||
#if DEBUG
|
||||
printf("Command line arguments (%d):\n", argc);
|
||||
for (q = 0; q < argc ; q++) {
|
||||
printf(" %d = %s\n", q, argv[q]);
|
||||
}
|
||||
#endif
|
||||
|
||||
if ((argc < 3) || (argc > 4)) {
|
||||
printf("usage: %s <inpipe> <tempfilename> [<maxdelay>]\n", argv[0]);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if (argc == 4) { // get delay
|
||||
delay = strtol(argv[3], (char **) NULL, 10);
|
||||
if (delay < 0) {
|
||||
printf("Unable to convert maximum delay value: %s\n", argv[3]);
|
||||
exit(2);
|
||||
}
|
||||
} // get delay
|
||||
|
||||
#if DEBUG
|
||||
printf("Delay is set to %d seconds.\n", delay);
|
||||
#endif
|
||||
|
||||
infd = open(argv[1], O_RDONLY | O_NONBLOCK);
|
||||
if (infd == -1) {
|
||||
printf("Error opening input pipe %s: %d - %s\n", argv[1], errno, strerror(errno));
|
||||
exit(3);
|
||||
}
|
||||
|
||||
outfd = open(argv[2], O_RDWR | O_CREAT | O_TRUNC, S_IRWXU);
|
||||
if (outfd == -1) {
|
||||
printf("Error opening output file %s: %d - %s\n", argv[2], errno, strerror(errno));
|
||||
exit(4);
|
||||
}
|
||||
|
||||
count_down = delay;
|
||||
while (1) { // must kill with a signal....
|
||||
readcnt = read(infd, buffer, (size_t) BUF_SIZE);
|
||||
#if DEBUG
|
||||
printf("read() returned with readcnt = %d, errno = %d\n", readcnt, errno);
|
||||
#endif
|
||||
if ((readcnt == -1) && (errno != EAGAIN)) { // EAGAIN - no data waiting, can ignore
|
||||
printf("Error reading input pipe: %d - %s\n", errno, strerror(errno));
|
||||
exit(5);
|
||||
} else { // no errors reading input pipe
|
||||
if (readcnt > 0) {
|
||||
writecnt = write(outfd, buffer, readcnt);
|
||||
if (writecnt == -1) {
|
||||
printf("Error writing output file: %d - %s\n", errno, strerror(errno));
|
||||
exit(6);
|
||||
}
|
||||
didwait = 0; // reset wait flag (wait again)
|
||||
count_down = delay;
|
||||
havedata = 1; // set flag that we got some data
|
||||
} else { //readcnt must = 0
|
||||
if (!didwait) { //have not waited yet...
|
||||
if (count_down > 0) { // sleep a bit
|
||||
sleep(1);
|
||||
count_down -= 1;
|
||||
} else {
|
||||
didwait = 1; // set wait flag (don't wait again)
|
||||
}
|
||||
} else { // already waited
|
||||
if (havedata) { // have data to print, close & reopen output file
|
||||
if (close(outfd) != 0) {
|
||||
printf("Error closing output file: %d - %s\n", errno, strerror(errno));
|
||||
exit(7);
|
||||
}
|
||||
|
||||
#if DEBUG
|
||||
printf("Spooling temp file...\n");
|
||||
#endif
|
||||
|
||||
pid = fork();
|
||||
if (pid == -1) {
|
||||
printf("Error forking new process: %d - %s\n", errno, strerror(errno));
|
||||
exit(9);
|
||||
}
|
||||
if (pid == 0) { // we're now running in the child process...
|
||||
execlp("lpr", "lpr", argv[2], NULL);
|
||||
exit(99); // should never get here...
|
||||
} // we're now running in the child process...
|
||||
if (pid > 0) { // we're running in the parent process...
|
||||
wait_pid = waitpid(pid, (int *)&wait_status, 0);
|
||||
if (wait_pid != pid) { // some sort of error
|
||||
printf("Wait for 'lpr' command returned abnormally!\n");
|
||||
if (WIFEXITED(wait_status)) {
|
||||
printf(" 'lpr' exited normally.\n");
|
||||
} else {
|
||||
printf(" 'lpr' exited abnormally, return code = %d.\n", WEXITSTATUS(wait_status));
|
||||
}
|
||||
if (WIFSIGNALED(wait_status)) {
|
||||
printf(" 'lpr' received uncaught signal %d\n", WTERMSIG(wait_status));
|
||||
}
|
||||
} // some sort of error
|
||||
} // we're running in the parent process...
|
||||
outfd = open(argv[2], O_RDWR | O_TRUNC);
|
||||
if (outfd == -1) {
|
||||
printf("Error re-opening output file: %d - %s\n", errno, strerror(errno));
|
||||
exit(8);
|
||||
}
|
||||
} // have data to print, close & repoen output file.
|
||||
havedata = 0; // no more data waiting
|
||||
count_down = delay;
|
||||
didwait = 0; // reset wait flag (wait again)
|
||||
} // already waited
|
||||
} // readcnt must = 0
|
||||
} // no errors reading input pipe
|
||||
} // must kill with a signal...
|
||||
|
||||
exit(0);
|
||||
} // eof(spoolpipe.c)
|
||||
378
simulators/bochs/misc/test-access-check.cc
Normal file
378
simulators/bochs/misc/test-access-check.cc
Normal file
@ -0,0 +1,378 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// test-access-check.cc
|
||||
// $Id$
|
||||
// by Bryce Denney
|
||||
//
|
||||
// This whole program is intended to test just a few lines in
|
||||
// cpu/access.cc, where it checks if a memory access goes over the
|
||||
// segment limits.
|
||||
//
|
||||
// NOTE: The variable called limit is actually "limit_scaled" in the
|
||||
// bochs code. Limit_scaled is equal to the limit when granularity is 0,
|
||||
// and equal to (limit << 12) | 0xfff when granularity is 1.
|
||||
//
|
||||
// Compile with:
|
||||
// cc -I. -Iinstrument/stubs -o test-access-check misc/test-access-check.cc
|
||||
// Then run "test-access-check" and see how it goes. If mismatches=0,
|
||||
// the rule is good.
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include <bochs.h>
|
||||
|
||||
// rule1 is the original rule used in Bochs from 2000-03-25. It has bad
|
||||
// overflow problems.
|
||||
int rule1 (Bit32u limit, Bit32u length, Bit32u offset);
|
||||
|
||||
// rule2 is Bryce's first try, which turned out to have bad underflow problems
|
||||
// instead.
|
||||
int rule2 (Bit32u limit, Bit32u length, Bit32u offset);
|
||||
|
||||
// rule3 is Bryce's second try, which as far as he knows works for all
|
||||
// cases.
|
||||
int rule3 (Bit32u limit, Bit32u length, Bit32u offset);
|
||||
|
||||
// edit this to test other rules.
|
||||
#define TEST_RULE rule3
|
||||
|
||||
typedef struct {
|
||||
Bit32u limit, length, offset, the_answer;
|
||||
} TestStruct;
|
||||
|
||||
TestStruct tests[] = {
|
||||
// limit length offset exception
|
||||
{0x0a, 4, 0, 0},
|
||||
{0x0a, 4, 1, 0},
|
||||
{0x0a, 4, 2, 0},
|
||||
{0x0a, 4, 3, 0},
|
||||
{0x0a, 4, 4, 0},
|
||||
{0x0a, 4, 5, 0},
|
||||
{0x0a, 4, 6, 0},
|
||||
{0x0a, 4, 7, 0},
|
||||
{0x0a, 4, 8, 1},
|
||||
{0x0a, 4, 9, 1},
|
||||
{0x0a, 4, 0x0a, 1},
|
||||
{0x0a, 4, 0x0b, 1},
|
||||
{0x0a, 4, 0x0c, 1},
|
||||
{0x0a, 4, 0xfffffffd, 1},
|
||||
{0x0a, 4, 0xfffffffe, 1},
|
||||
{0x0a, 4, 0xffffffff, 1},
|
||||
{0x0a, 2, 0, 0},
|
||||
{0x0a, 2, 1, 0},
|
||||
{0x0a, 2, 2, 0},
|
||||
{0x0a, 2, 3, 0},
|
||||
{0x0a, 2, 4, 0},
|
||||
{0x0a, 2, 5, 0},
|
||||
{0x0a, 2, 6, 0},
|
||||
{0x0a, 2, 7, 0},
|
||||
{0x0a, 2, 8, 0},
|
||||
{0x0a, 2, 9, 0},
|
||||
{0x0a, 2, 0x0a, 1},
|
||||
{0x0a, 2, 0x0b, 1},
|
||||
{0x0a, 2, 0x0c, 1},
|
||||
{0x0a, 2, 0xfffffffd, 1},
|
||||
{0x0a, 2, 0xfffffffe, 1},
|
||||
{0x0a, 2, 0xffffffff, 1},
|
||||
{0x0a, 1, 0, 0},
|
||||
{0x0a, 1, 1, 0},
|
||||
{0x0a, 1, 2, 0},
|
||||
{0x0a, 1, 3, 0},
|
||||
{0x0a, 1, 4, 0},
|
||||
{0x0a, 1, 5, 0},
|
||||
{0x0a, 1, 6, 0},
|
||||
{0x0a, 1, 7, 0},
|
||||
{0x0a, 1, 8, 0},
|
||||
{0x0a, 1, 9, 0},
|
||||
{0x0a, 1, 0x0a, 0},
|
||||
{0x0a, 1, 0x0b, 1},
|
||||
{0x0a, 1, 0x0c, 1},
|
||||
//
|
||||
// try a few near the common 0xffff boundary
|
||||
//
|
||||
{0xffff, 1, 0, 0},
|
||||
{0xffff, 1, 0x100, 0},
|
||||
{0xffff, 1, 0x1000, 0},
|
||||
{0xffff, 1, 0x8000, 0},
|
||||
{0xffff, 1, 0xf000, 0},
|
||||
{0xffff, 1, 0xfff0, 0},
|
||||
{0xffff, 1, 0xfff1, 0},
|
||||
{0xffff, 1, 0xfff2, 0},
|
||||
{0xffff, 1, 0xfff3, 0},
|
||||
{0xffff, 1, 0xfff4, 0},
|
||||
{0xffff, 1, 0xfff5, 0},
|
||||
{0xffff, 1, 0xfff6, 0},
|
||||
{0xffff, 1, 0xfff7, 0},
|
||||
{0xffff, 1, 0xfff8, 0},
|
||||
{0xffff, 1, 0xfff9, 0},
|
||||
{0xffff, 1, 0xfffa, 0},
|
||||
{0xffff, 1, 0xfffb, 0},
|
||||
{0xffff, 1, 0xfffc, 0},
|
||||
{0xffff, 1, 0xfffd, 0},
|
||||
{0xffff, 1, 0xfffe, 0},
|
||||
{0xffff, 1, 0xffff, 0},
|
||||
{0xffff, 1, 0x10000, 1},
|
||||
{0xffff, 1, 0x10001, 1},
|
||||
{0xffff, 1, 0x10002, 1},
|
||||
{0xffff, 1, 0x10021, 1},
|
||||
{0xffff, 1, 0x40001, 1},
|
||||
{0xffff, 1, 0xffffffff, 1},
|
||||
//
|
||||
// near 0xffff, length 2
|
||||
//
|
||||
{0xffff, 2, 0, 0},
|
||||
{0xffff, 2, 0x100, 0},
|
||||
{0xffff, 2, 0x1000, 0},
|
||||
{0xffff, 2, 0x8000, 0},
|
||||
{0xffff, 2, 0xf000, 0},
|
||||
{0xffff, 2, 0xfff0, 0},
|
||||
{0xffff, 2, 0xfff1, 0},
|
||||
{0xffff, 2, 0xfff2, 0},
|
||||
{0xffff, 2, 0xfff3, 0},
|
||||
{0xffff, 2, 0xfff4, 0},
|
||||
{0xffff, 2, 0xfff5, 0},
|
||||
{0xffff, 2, 0xfff6, 0},
|
||||
{0xffff, 2, 0xfff7, 0},
|
||||
{0xffff, 2, 0xfff8, 0},
|
||||
{0xffff, 2, 0xfff9, 0},
|
||||
{0xffff, 2, 0xfffa, 0},
|
||||
{0xffff, 2, 0xfffb, 0},
|
||||
{0xffff, 2, 0xfffc, 0},
|
||||
{0xffff, 2, 0xfffd, 0},
|
||||
{0xffff, 2, 0xfffe, 0},
|
||||
{0xffff, 2, 0xffff, 1},
|
||||
{0xffff, 2, 0x10000, 1},
|
||||
{0xffff, 2, 0x10001, 1},
|
||||
{0xffff, 2, 0x10002, 1},
|
||||
{0xffff, 2, 0x10021, 1},
|
||||
{0xffff, 2, 0x40001, 1},
|
||||
{0xffff, 2, 0xffffffff, 1},
|
||||
//
|
||||
// near 0xffff, length 4
|
||||
//
|
||||
{0xffff, 4, 0, 0},
|
||||
{0xffff, 4, 0x100, 0},
|
||||
{0xffff, 4, 0x1000, 0},
|
||||
{0xffff, 4, 0x8000, 0},
|
||||
{0xffff, 4, 0xf000, 0},
|
||||
{0xffff, 4, 0xfff0, 0},
|
||||
{0xffff, 4, 0xfff1, 0},
|
||||
{0xffff, 4, 0xfff2, 0},
|
||||
{0xffff, 4, 0xfff3, 0},
|
||||
{0xffff, 4, 0xfff4, 0},
|
||||
{0xffff, 4, 0xfff5, 0},
|
||||
{0xffff, 4, 0xfff6, 0},
|
||||
{0xffff, 4, 0xfff7, 0},
|
||||
{0xffff, 4, 0xfff8, 0},
|
||||
{0xffff, 4, 0xfff9, 0},
|
||||
{0xffff, 4, 0xfffa, 0},
|
||||
{0xffff, 4, 0xfffb, 0},
|
||||
{0xffff, 4, 0xfffc, 0},
|
||||
{0xffff, 4, 0xfffd, 1},
|
||||
{0xffff, 4, 0xfffe, 1},
|
||||
{0xffff, 4, 0xffff, 1},
|
||||
{0xffff, 4, 0x10000, 1},
|
||||
{0xffff, 4, 0x10001, 1},
|
||||
{0xffff, 4, 0x10002, 1},
|
||||
{0xffff, 4, 0x10021, 1},
|
||||
{0xffff, 4, 0x40001, 1},
|
||||
{0xffff, 4, 0xffffffff, 1},
|
||||
//
|
||||
// now a few near the max limit 0xffffffff
|
||||
//
|
||||
{0xffffffff, 1, 0, 0},
|
||||
{0xffffffff, 1, 0x100, 0},
|
||||
{0xffffffff, 1, 0x1000, 0},
|
||||
{0xffffffff, 1, 0x8000, 0},
|
||||
{0xffffffff, 1, 0xf000, 0},
|
||||
{0xffffffff, 1, 0xfff0, 0},
|
||||
{0xffffffff, 1, 0xfff1, 0},
|
||||
{0xffffffff, 1, 0xfff2, 0},
|
||||
{0xffffffff, 1, 0xfff3, 0},
|
||||
{0xffffffff, 1, 0xfff4, 0},
|
||||
{0xffffffff, 1, 0xfff5, 0},
|
||||
{0xffffffff, 1, 0xfff6, 0},
|
||||
{0xffffffff, 1, 0xfff7, 0},
|
||||
{0xffffffff, 1, 0xfff8, 0},
|
||||
{0xffffffff, 1, 0xfff9, 0},
|
||||
{0xffffffff, 1, 0xfffa, 0},
|
||||
{0xffffffff, 1, 0xfffb, 0},
|
||||
{0xffffffff, 1, 0xfffc, 0},
|
||||
{0xffffffff, 1, 0xfffd, 0},
|
||||
{0xffffffff, 1, 0xfffe, 0},
|
||||
{0xffffffff, 1, 0xffff, 0},
|
||||
{0xffffffff, 1, 0x10000, 0},
|
||||
{0xffffffff, 1, 0x10001, 0},
|
||||
{0xffffffff, 1, 0x10002, 0},
|
||||
{0xffffffff, 1, 0x10021, 0},
|
||||
{0xffffffff, 1, 0x40001, 0},
|
||||
{0xffffffff, 1, 0xfffffff0, 0},
|
||||
{0xffffffff, 1, 0xfffffff9, 0},
|
||||
{0xffffffff, 1, 0xfffffffa, 0},
|
||||
{0xffffffff, 1, 0xfffffffb, 0},
|
||||
{0xffffffff, 1, 0xfffffffc, 0},
|
||||
{0xffffffff, 1, 0xfffffffd, 0},
|
||||
{0xffffffff, 1, 0xfffffffe, 0},
|
||||
{0xffffffff, 1, 0xffffffff, 0},
|
||||
{0xffffffff, 1, 0x00000000, 0},
|
||||
{0xffffffff, 1, 0x00000001, 0},
|
||||
{0xffffffff, 1, 0x00000002, 0},
|
||||
{0xffffffff, 1, 0x00000003, 0},
|
||||
{0xffffffff, 1, 0x00000004, 0},
|
||||
{0xffffffff, 1, 0x00000005, 0},
|
||||
//
|
||||
// repeat with length 2
|
||||
//
|
||||
{0xffffffff, 2, 0, 0},
|
||||
{0xffffffff, 2, 0x100, 0},
|
||||
{0xffffffff, 2, 0x1000, 0},
|
||||
{0xffffffff, 2, 0x8000, 0},
|
||||
{0xffffffff, 2, 0xf000, 0},
|
||||
{0xffffffff, 2, 0xfff0, 0},
|
||||
{0xffffffff, 2, 0xfff1, 0},
|
||||
{0xffffffff, 2, 0xfff2, 0},
|
||||
{0xffffffff, 2, 0xfff3, 0},
|
||||
{0xffffffff, 2, 0xfff4, 0},
|
||||
{0xffffffff, 2, 0xfff5, 0},
|
||||
{0xffffffff, 2, 0xfff6, 0},
|
||||
{0xffffffff, 2, 0xfff7, 0},
|
||||
{0xffffffff, 2, 0xfff8, 0},
|
||||
{0xffffffff, 2, 0xfff9, 0},
|
||||
{0xffffffff, 2, 0xfffa, 0},
|
||||
{0xffffffff, 2, 0xfffb, 0},
|
||||
{0xffffffff, 2, 0xfffc, 0},
|
||||
{0xffffffff, 2, 0xfffd, 0},
|
||||
{0xffffffff, 2, 0xfffe, 0},
|
||||
{0xffffffff, 2, 0xffff, 0},
|
||||
{0xffffffff, 2, 0x10000, 0},
|
||||
{0xffffffff, 2, 0x10001, 0},
|
||||
{0xffffffff, 2, 0x10002, 0},
|
||||
{0xffffffff, 2, 0x10021, 0},
|
||||
{0xffffffff, 2, 0x40001, 0},
|
||||
{0xffffffff, 2, 0xfffffff0, 0},
|
||||
{0xffffffff, 2, 0xfffffff9, 0},
|
||||
{0xffffffff, 2, 0xfffffffa, 0},
|
||||
{0xffffffff, 2, 0xfffffffb, 0},
|
||||
{0xffffffff, 2, 0xfffffffc, 0},
|
||||
{0xffffffff, 2, 0xfffffffd, 0},
|
||||
{0xffffffff, 2, 0xfffffffe, 0},
|
||||
{0xffffffff, 2, 0xffffffff, 1},
|
||||
{0xffffffff, 2, 0x00000000, 0},
|
||||
{0xffffffff, 2, 0x00000001, 0},
|
||||
{0xffffffff, 2, 0x00000002, 0},
|
||||
{0xffffffff, 2, 0x00000003, 0},
|
||||
{0xffffffff, 2, 0x00000004, 0},
|
||||
{0xffffffff, 2, 0x00000005, 0},
|
||||
//
|
||||
// repeat with length 4
|
||||
//
|
||||
{0xffffffff, 4, 0, 0},
|
||||
{0xffffffff, 4, 0x100, 0},
|
||||
{0xffffffff, 4, 0x1000, 0},
|
||||
{0xffffffff, 4, 0x8000, 0},
|
||||
{0xffffffff, 4, 0xf000, 0},
|
||||
{0xffffffff, 4, 0xfff0, 0},
|
||||
{0xffffffff, 4, 0xfff1, 0},
|
||||
{0xffffffff, 4, 0xfff2, 0},
|
||||
{0xffffffff, 4, 0xfff3, 0},
|
||||
{0xffffffff, 4, 0xfff4, 0},
|
||||
{0xffffffff, 4, 0xfff5, 0},
|
||||
{0xffffffff, 4, 0xfff6, 0},
|
||||
{0xffffffff, 4, 0xfff7, 0},
|
||||
{0xffffffff, 4, 0xfff8, 0},
|
||||
{0xffffffff, 4, 0xfff9, 0},
|
||||
{0xffffffff, 4, 0xfffa, 0},
|
||||
{0xffffffff, 4, 0xfffb, 0},
|
||||
{0xffffffff, 4, 0xfffc, 0},
|
||||
{0xffffffff, 4, 0xfffd, 0},
|
||||
{0xffffffff, 4, 0xfffe, 0},
|
||||
{0xffffffff, 4, 0xffff, 0},
|
||||
{0xffffffff, 4, 0x10000, 0},
|
||||
{0xffffffff, 4, 0x10001, 0},
|
||||
{0xffffffff, 4, 0x10002, 0},
|
||||
{0xffffffff, 4, 0x10021, 0},
|
||||
{0xffffffff, 4, 0x40001, 0},
|
||||
{0xffffffff, 4, 0xfffffff0, 0},
|
||||
{0xffffffff, 4, 0xfffffff9, 0},
|
||||
{0xffffffff, 4, 0xfffffffa, 0},
|
||||
{0xffffffff, 4, 0xfffffffb, 0},
|
||||
{0xffffffff, 4, 0xfffffffc, 0},
|
||||
{0xffffffff, 4, 0xfffffffd, 1},
|
||||
{0xffffffff, 4, 0xfffffffe, 1},
|
||||
{0xffffffff, 4, 0xffffffff, 1},
|
||||
{0xffffffff, 4, 0x00000000, 0},
|
||||
{0xffffffff, 4, 0x00000001, 0},
|
||||
{0xffffffff, 4, 0x00000002, 0},
|
||||
{0xffffffff, 4, 0x00000003, 0},
|
||||
{0xffffffff, 4, 0x00000004, 0},
|
||||
{0xffffffff, 4, 0x00000005, 0},
|
||||
//
|
||||
// now make some underflow cases to disprove my new rule
|
||||
//
|
||||
{1, 1, 0, 0},
|
||||
{1, 1, 1, 0},
|
||||
{1, 1, 2, 1},
|
||||
{1, 1, 3, 1},
|
||||
{1, 1, 4, 1},
|
||||
{1, 1, 0xfffffffc, 1},
|
||||
{1, 1, 0xfffffffd, 1},
|
||||
{1, 1, 0xfffffffe, 1},
|
||||
{1, 1, 0xffffffff, 1},
|
||||
{1, 2, 0, 0},
|
||||
{1, 2, 1, 1},
|
||||
{1, 2, 2, 1},
|
||||
{1, 2, 3, 1},
|
||||
{1, 2, 4, 1},
|
||||
{1, 2, 0xfffffffc, 1},
|
||||
{1, 2, 0xfffffffd, 1},
|
||||
{1, 2, 0xfffffffe, 1},
|
||||
{1, 2, 0xffffffff, 1},
|
||||
{1, 4, 0, 1},
|
||||
{1, 4, 1, 1},
|
||||
{1, 4, 2, 1},
|
||||
{1, 4, 3, 1},
|
||||
{1, 4, 4, 1},
|
||||
{1, 4, 0xfffffffc, 1},
|
||||
{1, 4, 0xfffffffd, 1},
|
||||
{1, 4, 0xfffffffe, 1},
|
||||
{1, 4, 0xffffffff, 1}
|
||||
};
|
||||
|
||||
int main () {
|
||||
int total=0, mismatches=0;
|
||||
int t;
|
||||
for (t=0; t<sizeof(tests)/sizeof(tests[0]); t++) {
|
||||
TestStruct *ts = &tests[t];
|
||||
int my_answer = TEST_RULE (ts->limit, ts->length, ts->offset);
|
||||
printf ("limit=%x len=%x offset=%x exception=%x %s\n",
|
||||
ts->limit,
|
||||
ts->length,
|
||||
ts->offset,
|
||||
my_answer,
|
||||
(ts->the_answer==my_answer) ? "" : "MISMATCH");
|
||||
if (ts->the_answer!=my_answer) mismatches++;
|
||||
total++;
|
||||
}
|
||||
printf ("mismatches=%d\n", mismatches);
|
||||
printf ("total=%d\n", total);
|
||||
}
|
||||
|
||||
int rule1 (Bit32u limit, Bit32u length, Bit32u offset)
|
||||
{
|
||||
if ((offset + length - 1) > limit) return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int rule2 (Bit32u limit, Bit32u length, Bit32u offset)
|
||||
{
|
||||
if (offset > (limit - length + 1)) return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int rule3 (Bit32u limit, Bit32u length, Bit32u offset)
|
||||
{
|
||||
if (offset > (limit - length + 1) || (length-1 > limit)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
Reference in New Issue
Block a user