- commit patch.wxwindows.gz in the main branch. Now you can try out
the wxwindows interface by just "configure --with-wx; make" Modified Files: Makefile.in bochs.h config.h.in configure configure.in load32bitOShack.cc logio.cc main.cc cpu/cpu.cc cpu/cpu.h debug/dbg_main.cc gui/Makefile.in gui/control.cc gui/gui.cc gui/siminterface.cc gui/siminterface.h gui/x.cc iodev/cdrom.cc iodev/keyboard.cc memory/misc_mem.cc Added Files: README-wxWindows wxbochs.rc gui/wx.cc gui/wxmain.cc gui/wxmain.h gui/bitmaps/cdromd.xpm gui/bitmaps/configbutton.xpm gui/bitmaps/copy.xpm gui/bitmaps/floppya.xpm gui/bitmaps/floppyb.xpm gui/bitmaps/mouse.xpm gui/bitmaps/paste.xpm gui/bitmaps/power.xpm gui/bitmaps/reset.xpm gui/bitmaps/snapshot.xpm Removed Files: patches/patch.wxwindows.gz
This commit is contained in:
parent
13bb61838e
commit
30aaf4088e
@ -96,6 +96,7 @@ GUI_LINK_OPTS_MACOS =
|
||||
GUI_LINK_OPTS_CARBON = -framework Carbon
|
||||
GUI_LINK_OPTS_NOGUI =
|
||||
GUI_LINK_OPTS_TERM = @GUI_LINK_OPTS_TERM@
|
||||
GUI_LINK_OPTS_WX = `wx-config --libs`
|
||||
GUI_LINK_OPTS = @GUI_LINK_OPTS@
|
||||
RANLIB = @RANLIB@
|
||||
|
||||
@ -187,7 +188,7 @@ $(BX_OBJS): $(BX_INCLUDES)
|
||||
bxversion.h:
|
||||
$(RM) -f bxversion.h
|
||||
echo '/////////////////////////////////////////////////////////////////////////' > bxversion.h
|
||||
echo '// $$Id: Makefile.in,v 1.67 2002-03-28 00:28:41 bdenney Exp $$' >> bxversion.h
|
||||
echo '// $$Id: Makefile.in,v 1.68 2002-04-18 00:22:18 bdenney Exp $$' >> bxversion.h
|
||||
echo '/////////////////////////////////////////////////////////////////////////' >> bxversion.h
|
||||
echo '// This file is generated by "make bxversion.h"' >> bxversion.h
|
||||
echo "#define VER_STRING \"$(VER_STRING)\"" >> bxversion.h
|
||||
|
442
bochs/README-wxWindows
Normal file
442
bochs/README-wxWindows
Normal file
@ -0,0 +1,442 @@
|
||||
Readme for wxWindows Interface
|
||||
updated Wed Apr 17 19:59:17 EDT 2002
|
||||
Bryce Denney
|
||||
|
||||
-------------
|
||||
April 17, 2002: The wxwindows interface is now checked into the main
|
||||
branch. Known problems
|
||||
|
||||
TO DO:
|
||||
- disk change dialogs for floppy and cdrom need work.
|
||||
http://sourceforge.net/tracker/index.php?func=detail&aid=545414&group_id=12580&atid=112580
|
||||
- with --with-wx and debugger, control-C in the terminal window kills the
|
||||
process instead of just interrupting the simulation.
|
||||
- tons of dialogs need to be written
|
||||
- debugger interface
|
||||
-------------
|
||||
|
||||
wxWindows Configuration Interface
|
||||
|
||||
The wxWindows port began in June 2001 around the time of Bochs 1.2.1. Dave
|
||||
Poirier and Bryce Denney started adding a wxWindows configuration interface.
|
||||
We made some progress, but stopped after a while. Then in March/April 2002
|
||||
Bryce and Psyon revived the wxWindows branch and turned it into a (mostly)
|
||||
usable interface. Psyon did most of the work to get text and graphics
|
||||
working, and Bryce worked on event passing between threads, and keyboard
|
||||
mapping.
|
||||
|
||||
The wxWindows window appears first. This WILL BE where you can choose a preset
|
||||
configuration or create one from scratch, then edit the bochsrc options using
|
||||
the GUI. Then, by clicking on Simulate:Start, you can start up the Bochs
|
||||
simulation. The VGA display is implemented in wxWindows.
|
||||
|
||||
WARNING: Don't expect perfect code yet!
|
||||
|
||||
Bryce has tested in linux, where a "configure --with-wx;make" should work fine.
|
||||
To build in VC++:
|
||||
|
||||
- in cygwin, do "sh .conf.win32-vcpp". If you want different configure
|
||||
options from the default, edit .conf.win32-vcpp first.
|
||||
- in cygwin, do "unzip build/win32/workspace.zip", or use winzip. Now
|
||||
you should have bochs.dsw and bochs.dsp in the main directory.
|
||||
- open up bochs.dsw, the workspace file.
|
||||
- edit project settings so that VC++ can find the wxWindows include
|
||||
files and libraries on your system. I installed them in
|
||||
d:/wx/wx232/include and d:/wx/wx232/lib. Specifically, edit
|
||||
- Project>Settings>C/C++>Preprocessor: include directories.
|
||||
- Project>Settings>Link>Input: additional library path.
|
||||
- build
|
||||
|
||||
Note that the project is set up for wxWindows 2.3.2, and the only
|
||||
configuration that I've used is called Win32 Debug. To use on
|
||||
other wxwindows versions, you will have to change some of the names
|
||||
of the libraries to include. Use the samples that came with that
|
||||
version of wxwindows for reference.
|
||||
|
||||
What works right now:
|
||||
- cd to a directory with a bochsrc and disk images in it (I use dlxlinux)
|
||||
- start up bochs. You get a small wxwindows window with a File menu.
|
||||
- choose "Start" on the Simulate menu.
|
||||
- a new window pops up with is the normal bochs window. Bochs starts running.
|
||||
You can pause it, resume it, or kill it on the Simulate menu.
|
||||
- the only visible change is that I've made several of the toolbar
|
||||
icons bring up wxwindows dialog boxes. There is a lot going on behind
|
||||
the scenes to make this possible--trust me! The 2 floppy icons, CDROM
|
||||
icon, and snapshot icon all bring up appropriate dialog boxes to let
|
||||
you choose a file.
|
||||
- That's all. The other menu options are not implemented except for quit.
|
||||
|
||||
To do:
|
||||
- sketch the GUI pieces that need to be made, with text description of
|
||||
basically what they should do. See README.gui-sketch for latest ideas.
|
||||
- have a few people look over the sketches so that we don't waste lots of
|
||||
time building dialogs that people will hate.
|
||||
- code some dialog boxes in wxwindows. Just get it looking right at first, and
|
||||
Bryce can help you to get it connected to the simulator using the event
|
||||
infrastructure that he has made. Again, after one or two is done there will
|
||||
be some good examples to look at.
|
||||
- implement ASK_PARAM gui event for all types of parameters. Currently only
|
||||
string params are supported, meaning that when you call ask_param() on
|
||||
a string parameter, the GUI gives the user a chance to edit that parameter's
|
||||
value. We will need to implement boolean, enum, numerical parameters, and
|
||||
lists. Lists should probably be displayed as a table or a dialog box
|
||||
with several things to select.
|
||||
- debugger interface. There's lots of demand for a debugger interface
|
||||
to Bochs: possibly more demand than for a configuration interface. We
|
||||
should talk about what this will look like, and when we have a plan we
|
||||
can start sketching and coding dialogs for the debugger interface too.
|
||||
- clean up the biggest memory leaks and init/cleanup code. The gui allows you
|
||||
to kill the simulator and restart, but it doesn't do well after the first
|
||||
time. Valgrind should help with memory leak debugging, though it doesn't run
|
||||
multithreaded programes.
|
||||
------------------------------------------------------
|
||||
|
||||
Random notes follow
|
||||
|
||||
Added some sketches in README.gui-sketch. I'm thinking that the control
|
||||
panel will be able to basically show one of these screens at a time. When
|
||||
you first start you would see ChooseConfigScreen which chooses between the
|
||||
configurations that you have loaded recently (which it would remember
|
||||
by the pathname of their bochsrc). Whether you choose an existing
|
||||
configuration to be loaded or a new one, when you click Ok you go to
|
||||
the first configuration screen, ConfigDiskScreen.
|
||||
|
||||
Each of the configuration screens takes up the whole control panel window.
|
||||
We could use tabs on the top and/or "<-Prev" and "Next->" buttons to make
|
||||
it quick to navigate the configuration screens. Each screen should
|
||||
probably have a Prev, Next, Revert to Saved, and Accept button.
|
||||
The menu choices like Disk..., VGA..., etc. just switch directly to
|
||||
that tab.
|
||||
|
||||
|
||||
------------------------------------------------------
|
||||
Notes:
|
||||
|
||||
events from gui to sim:
|
||||
- [async] key pressed or released
|
||||
- [async] mouse motion with button state
|
||||
- [sync] query parameter
|
||||
- [sync] change parameter
|
||||
- [async] start, pause, stop, reset simulation. Can be implemented
|
||||
as changing a parameter.
|
||||
- [async] request notification when some param changes
|
||||
|
||||
events from sim to gui:
|
||||
- [async] log message to be displayed (or not)
|
||||
- [async] ask user how to proceed (like panic: action=ask)
|
||||
- [async] param value changed
|
||||
- make my thread sleep for X microseconds (call wxThread::sleep then return)
|
||||
|
||||
In a synchronous event, the event object will contain space for the entire
|
||||
response. The sender allocates memory for the event and builds it. The
|
||||
receiver fills in blanks in the event structure (or could overwrite parts)
|
||||
and returns the same event pointer as a response. For async events, probably
|
||||
the sender will allocate and the receiver will have to delete it.
|
||||
|
||||
implement the floppyA and floppyB change buttons using new event
|
||||
structure. How should it work?
|
||||
|
||||
vga gui detects a click on floppyA bitmap
|
||||
construct a BxEvent type BX_EVT_ASK_PARAM
|
||||
post the event to the wxwindows gui thread (somehow) and block for response
|
||||
when it arrives in the gui thread, show a modal dialog box
|
||||
get the answer back to the simulator thread
|
||||
|
||||
|
||||
right now, this is working ok within the simulator thread using
|
||||
wxMutexGuiEnter/Leave. Still I'm going to change it so that the
|
||||
siminterface.cc code builds an event structure and the gui code
|
||||
fills in the blank in the structure, instead of the stupid
|
||||
notify_get_int_arg stuff.
|
||||
|
||||
|
||||
Starting and Killing Threads
|
||||
|
||||
When a detachable (default) thread finishes (returns from its Entry()
|
||||
function), wxwindows frees the memory associated with that thread.
|
||||
Unless the thread is never going to end, it is potentially dangerous to have a
|
||||
pointer to it at all. Even if you try to "check if it's alive" first, you may
|
||||
be dereferencing the pointer after it has already been deleted, leading to it
|
||||
claiming to be alive when it's not, or a segfault. To solve this, the approach
|
||||
used in the wxwindows threads example is to have code in the thread's OnExit()
|
||||
method remove the thread's pointer from the list of usable threads. In
|
||||
addition, any references or changes to the list of threads is controlled by a
|
||||
critical section to ensure that it stays correct. This post finally
|
||||
explained what I was seeing.
|
||||
|
||||
+-----------------------
|
||||
| From: Pieter van der Meulen (pgmvdm@yahoo.com)
|
||||
| Subject: Re: Thread Sample program - bug
|
||||
| Newsgroups: comp.soft-sys.wxwindows
|
||||
| Date: 2001-06-28 17:51:35 PST
|
||||
|
|
||||
|
|
||||
| At 06:24 PM 6/28/2001, you wrote:
|
||||
| >Hi,
|
||||
| >I have wxWindows 2.2.7 (wxMSW) installed.
|
||||
| >
|
||||
| >I just found in the thread.cpp sample code this section:
|
||||
| >
|
||||
| ><code>
|
||||
| >void MyFrame::OnQuit(wxCommandEvent& WXUNUSED(event) )
|
||||
| >{
|
||||
| > size_t count = wxGetApp().m_threads.Count();
|
||||
| > for ( size_t i = 0; i < count; i++ )
|
||||
| > {
|
||||
| >===> wxGetApp().m_threads[0]->Delete(); <=====
|
||||
| > }
|
||||
| >
|
||||
| > Close(TRUE);
|
||||
| >}
|
||||
| ></code>
|
||||
| >The indecated line should probably rather have a
|
||||
| >m_threads[i] rather than m_threads[0] .
|
||||
|
|
||||
| No, it should not, although it is not immediately obvious. When Delete() is
|
||||
| called, the thread will eventually delete itself, but not before it calls
|
||||
| MyThread::Exit(), which will remove itself from m_threads[] using
|
||||
| wxArray::Remove(this). wxArray::Remove (RemoveAt) will compact the array to
|
||||
| remove the element, it is now size-1. After this wxThread::Delete() returns.
|
||||
|
|
||||
|
|
||||
| >I have have a further question to this:
|
||||
| >Does this mean that a detached thread created with new
|
||||
| >HAS to be deleted manually ? Or is this only in case it might still
|
||||
| >be running?
|
||||
|
|
||||
| Firstly, you must create every detached thread using new since it will
|
||||
| delete itself, literally calling delete this.
|
||||
| Calling wxThread::Delete() is a correct way to terminate a thread, but
|
||||
| manually deleting (using delete) a detached wxThread object is not.
|
||||
| wxThread::Delete() will ask the thread to exit, the thread should check for
|
||||
| this in wxThread::Entry() regularly using wxThread::TestDestroy() and exit
|
||||
| when asked to do so.
|
||||
|
|
||||
| >(In general I have a unsatisfied felling about when delete is
|
||||
| >neccessary and when not -- "I only know, it's not , if the class is
|
||||
| >derived from wxWindows")
|
||||
|
|
||||
| For wxThreads: joinable threads must be deleted (when allocated on the
|
||||
| heap), detached threads may never be deleted. For other classes, consult
|
||||
| the documentation ;)
|
||||
|
|
||||
|
|
||||
| >Thanks for some feedback,
|
||||
| >Sebastian
|
||||
|
|
||||
| Regards,
|
||||
|
|
||||
| Pieter.
|
||||
+-----------------------
|
||||
|
||||
tracking some kind of deadlock bug in Linux.
|
||||
|
||||
seems to be in ReadMailcap, src/unix/mimetypes.cpp in wxwindows sources
|
||||
src/unix/mimetype.cpp:2312
|
||||
|
||||
SOLUTION: compile with -pthread on every compile and link line.
|
||||
|
||||
|
||||
---------------------------------------------------------------------------
|
||||
Here are some quick ASCII sketches of what different parts of the interface
|
||||
look like. Nothing is implemented yet, and everything is open for debate.
|
||||
Whoever writes the wxwindows code for any of these screens gets several
|
||||
thousand votes.
|
||||
|
||||
|
||||
Menus:
|
||||
- Configuration
|
||||
+----------------------+
|
||||
| New Configuration |
|
||||
| Read Configuration |
|
||||
| Save Configuration |
|
||||
+----------------------+
|
||||
| Quit |
|
||||
+----------------------+
|
||||
- Edit
|
||||
+----------------------+
|
||||
| Disks... |
|
||||
| Boot -----------> Floppy, Hard disk, or Cdrom
|
||||
| VGA... |
|
||||
| Memory... |
|
||||
| Sound... |
|
||||
| Networking... |
|
||||
| Keyboard... |
|
||||
| Other... |
|
||||
+----------------------+
|
||||
- Simulate
|
||||
+----------------------+
|
||||
| Start |
|
||||
| Pause/Resume |
|
||||
| Stop |
|
||||
+----------------------+
|
||||
| Speed... |
|
||||
+----------------------|
|
||||
- Debug
|
||||
+----------------------|
|
||||
| Show CPU |
|
||||
| Show Memory |
|
||||
| ? what else ? |
|
||||
+----------------------|
|
||||
- Event Log
|
||||
+----------------------+
|
||||
| View |
|
||||
| Preferences... |
|
||||
| By Device... |
|
||||
+----------------------+
|
||||
- Help
|
||||
+----------------------+
|
||||
| About Bochs... |
|
||||
+----------------------+
|
||||
|
||||
What should show up on the control panel when it first comes up?
|
||||
I think the standard thing should be to choose a configuration and
|
||||
start simulating.
|
||||
|
||||
|
||||
ChooseConfigScreen:
|
||||
+--------------------------------------------------------+
|
||||
| |
|
||||
| Choose a configuration for the Bochs simulator: |
|
||||
| |
|
||||
| +---+ |
|
||||
| | O | DLX Linux Demo |
|
||||
| | | | Boot 10MB Hard Disk |
|
||||
| +---+ |
|
||||
| |
|
||||
| +---+ |
|
||||
| | O | Redhat Linux Image |
|
||||
| | | | Boot 10MB Hard Disk |
|
||||
| +---+ |
|
||||
| |
|
||||
| +---+ |
|
||||
| | O | FreeDOS |
|
||||
| | | | Boot 40MB Hard Disk |
|
||||
| +---+ |
|
||||
| |
|
||||
| |
|
||||
| ?? Create new configuration |
|
||||
| |
|
||||
| |
|
||||
| [ |
|
||||
+--------------------------------------------------------+
|
||||
|
||||
ConfigDisksScreen:
|
||||
+---------------------------------------------------------------+
|
||||
| |
|
||||
| /----+ |
|
||||
| |= =| A Drive +----+ |
|
||||
| [ ] | __ | Raw Floppy Drive |Edit| |
|
||||
| || || A: +----+ |
|
||||
| ++--++ |
|
||||
| |
|
||||
| /----+ |
|
||||
| |= =| B Drive +----+ |
|
||||
| [ ] | __ | Floppy Disk Image |Edit| |
|
||||
| || || C:\Bochs\Images\A.img +----+ |
|
||||
| ++--++ |
|
||||
| |
|
||||
| +-----+ C Drive |
|
||||
| |=====| Hard Disk Image +----+ |
|
||||
| [BOOT] | o| C:\Bochs\Images\HD30meg.img |Edit| |
|
||||
| +-----+ +----+ |
|
||||
| |
|
||||
| ___ |
|
||||
| / \ D Drive +----+ |
|
||||
| [ ] | O | ISO CD Image |Edit| |
|
||||
| \___/ C:\Bochs\Images\BootCD.img +----+ |
|
||||
| |
|
||||
| |
|
||||
+---------------------------------------------------------------+
|
||||
|
||||
EditFloppyScreen:
|
||||
+---------------------------------------------------------------+
|
||||
| |
|
||||
| Bochs can use a real floppy drive as Disk A, or use an |
|
||||
| image file. |
|
||||
| |
|
||||
| [X] Physical A: drive |
|
||||
| [ ] Physical B: drive |
|
||||
| [ ] Disk image: [_____________________________] [Browse] |
|
||||
| Capacity: [1.44 MB] |
|
||||
| |
|
||||
| Hint: To create a disk image, choose the name and capacity |
|
||||
| above, then click Ok. |
|
||||
| |
|
||||
| [ Cancel ] [ Ok ] |
|
||||
+---------------------------------------------------------------+
|
||||
|
||||
|
||||
ConfigVgaScreen:
|
||||
FIXME
|
||||
|
||||
ConfigMemoryScreen:
|
||||
romimage: file=bios/BIOS-bochs-latest, address=0xf0000
|
||||
megs: 32
|
||||
vgaromimage: bios/VGABIOS-elpin-2.40
|
||||
FIXME
|
||||
|
||||
ConfigSoundScreen:
|
||||
sb16: midimode=1, midi=/dev/midi00, wavemode=1, wave=/dev/dsp, loglevel=2, log=sb16.log, dmatimer=600000
|
||||
FIXME
|
||||
|
||||
ConfigNetworkingScreen:
|
||||
+---------------------------------------------------------------+
|
||||
| |
|
||||
| Bochs can emulate an NE2000-compatible network card. Would |
|
||||
| you like to enable it? |
|
||||
| |
|
||||
| Enable networking? [X] |
|
||||
| |
|
||||
| NE2000 I/O address: [ 0x280 ] |
|
||||
| IRQ: [ 9 ] |
|
||||
| MAC address: [ b0:c4:00:00:00:00 ] |
|
||||
| Connection to the OS: [ Linux Packet Filter ] |
|
||||
| Physical NIC to use: [ eth0 ] |
|
||||
| NE2000 Debug messages: [ ] |
|
||||
| |
|
||||
+---------------------------------------------------------------+
|
||||
|
||||
ConfigKeyboardScreen:
|
||||
keyboard_mapping: enabled=1, map=US,France,Germany,Spain
|
||||
keyboard_type: xt,at,mf
|
||||
keyboard_serial_delay: 250
|
||||
|
||||
FIXME
|
||||
|
||||
ConfigOtherScreen:
|
||||
FIXME
|
||||
|
||||
ConfigSpeedScreen:
|
||||
explain what the heck ips is
|
||||
adjust ips with a slider?
|
||||
FIXME
|
||||
|
||||
EventLogPreferences:
|
||||
FIXME
|
||||
panic: action=ignore,report,fatal,ask
|
||||
error: action=ignore,report,fatal,ask
|
||||
info: action=ignore,report,fatal,ask
|
||||
debug: action=ignore,report,fatal,ask
|
||||
|
||||
EventLogPrefByDevice:
|
||||
FIXME
|
||||
keyboard panic=ask error=report info=report debug=ignore
|
||||
vga panic=ask error=report info=report debug=ignore
|
||||
network panic=ask error=report info=report debug=ignore
|
||||
cpu panic=ask error=report info=report debug=ignore
|
||||
sound panic=ask error=report info=report debug=ignore
|
||||
etc. for about 20 devices.
|
||||
|
||||
DebugShowCpuRegisters:
|
||||
show standard cpu registers and state
|
||||
values will update in real time
|
||||
this is sort of the start of the debugger interface
|
||||
when debugging, maybe highlight values that change between sim steps
|
||||
|
||||
DebugShowMemory:
|
||||
let use choose memory ranges to display
|
||||
when debugging, maybe highlight values that change between sim steps
|
||||
|
||||
|
||||
--------------------------------------------------------------------
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: bochs.h,v 1.61 2002-03-26 13:59:35 bdenney Exp $
|
||||
// $Id: bochs.h,v 1.62 2002-04-18 00:22:18 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
@ -222,13 +222,6 @@ extern Bit8u DTPageDirty[];
|
||||
|
||||
#define MAGIC_LOGNUM 0x12345678
|
||||
|
||||
// Log Level defines
|
||||
#define LOGLEV_DEBUG 0
|
||||
#define LOGLEV_INFO 1
|
||||
#define LOGLEV_ERROR 2
|
||||
#define LOGLEV_PANIC 3
|
||||
#define N_LOGLEV 4
|
||||
|
||||
typedef class logfunctions {
|
||||
char *prefix;
|
||||
int type;
|
||||
@ -463,7 +456,7 @@ typedef struct {
|
||||
|
||||
#define BX_ASSERT(x) do {if (!(x)) BX_PANIC(("failed assertion \"%s\" at %s:%d\n", #x, __FILE__, __LINE__));} while (0)
|
||||
void bx_signal_handler (int signum);
|
||||
void bx_atexit(void);
|
||||
int bx_atexit(void);
|
||||
extern bx_debug_t bx_dbg;
|
||||
|
||||
|
||||
@ -516,6 +509,8 @@ extern bx_devices_c bx_devices;
|
||||
#define BX_RESET_SOFTWARE 10
|
||||
#define BX_RESET_HARDWARE 11
|
||||
|
||||
void bx_init_before_control_panel ();
|
||||
|
||||
// This value controls how often each I/O device's periodic() method
|
||||
// gets called. The timer is set up in iodev/devices.cc.
|
||||
#define BX_IODEV_HANDLER_PERIOD 100 // microseconds
|
||||
|
@ -40,6 +40,15 @@
|
||||
// USER CONFIGURABLE OPTIONS : EDIT ONLY OPTIONS IN THIS SECTION //
|
||||
///////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
#if 1
|
||||
// quit_sim is defined in gui/siminterface.h
|
||||
#define BX_EXIT(x) SIM->quit_sim (x)
|
||||
#else
|
||||
// provide the real main and the usual exit.
|
||||
#define BX_EXIT(x) ::exit(x)
|
||||
#endif
|
||||
|
||||
#define BX_USE_CONTROL_PANEL 1
|
||||
|
||||
// I have tested the following combinations:
|
||||
@ -340,6 +349,7 @@
|
||||
#define BX_WITH_RFB 0
|
||||
#define BX_WITH_AMIGAOS 0
|
||||
#define BX_WITH_SDL 0
|
||||
#define BX_WITH_WX 0
|
||||
|
||||
|
||||
// Roland Mainz's idle hack is presently specific to X11. If people try to
|
||||
|
6152
bochs/configure
vendored
6152
bochs/configure
vendored
File diff suppressed because it is too large
Load Diff
@ -69,6 +69,7 @@ if (test "$with_sdl" != yes) && \
|
||||
(test "$with_rfb" != yes) && \
|
||||
(test "$with_amigaos" != yes) && \
|
||||
(test "$with_carbon" != yes) && \
|
||||
(test "$with_wx" != yes) && \
|
||||
(test "$with_macos" != yes); then
|
||||
# use DEFAULT_GUI. Set the appropriate variable.
|
||||
# DEFAULT_GUI must be set to one of the names above. Otherwise, no
|
||||
@ -1029,6 +1030,10 @@ AC_ARG_WITH(sdl,
|
||||
[ --with-sdl use SDL libraries],
|
||||
)
|
||||
|
||||
AC_ARG_WITH(wx,
|
||||
[ --with-wx use wxWindows libraries],
|
||||
)
|
||||
|
||||
dnl // DASH is option prefix for your platform
|
||||
dnl // SLASH is directory for your platform
|
||||
dnl // CXXFP is C++ File Prefix; the flag that tells the compiler
|
||||
@ -1068,34 +1073,34 @@ if test "$with_x11" = yes; then
|
||||
exit 1
|
||||
fi
|
||||
AC_DEFINE(BX_WITH_X11, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_X11)'
|
||||
GUI_OBJS='$(GUI_OBJS_X11) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_X)'
|
||||
INSTALL_LIST_FOR_PLATFORM='$(INSTALL_LIST_X11)'
|
||||
elif test "$with_beos" = yes; then
|
||||
AC_MSG_RESULT(beos)
|
||||
AC_DEFINE(BX_WITH_BEOS, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_BEOS)'
|
||||
GUI_OBJS='$(GUI_OBJS_BEOS) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_BEOS)'
|
||||
elif test "$with_sdl" = yes; then
|
||||
AC_MSG_RESULT(sdl)
|
||||
CFLAGS="$CFLAGS \`sdl-config --cflags\`"
|
||||
AC_DEFINE(BX_WITH_SDL, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_SDL)'
|
||||
GUI_OBJS='$(GUI_OBJS_SDL) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_SDL)'
|
||||
elif test "$with_rfb" = yes; then
|
||||
AC_MSG_RESULT(rfb)
|
||||
AC_DEFINE(BX_WITH_RFB, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_RFB)'
|
||||
GUI_OBJS='$(GUI_OBJS_RFB) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_RFB)'
|
||||
elif test "$with_amigaos" = yes; then
|
||||
AC_MSG_RESULT(amigaos)
|
||||
AC_DEFINE(BX_WITH_AMIGAOS, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_AMIGAOS)'
|
||||
GUI_OBJS='$(GUI_OBJS_AMIGAOS) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_AMIGAOS)'
|
||||
elif test "$with_win32" = yes; then
|
||||
AC_MSG_RESULT(win32)
|
||||
AC_DEFINE(BX_WITH_WIN32, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_WIN32)'
|
||||
GUI_OBJS='$(GUI_OBJS_WIN32) control.o'
|
||||
case $target in
|
||||
*-pc-windows*)
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_WIN32_VCPP)' # native libs for win gui
|
||||
@ -1109,24 +1114,39 @@ elif test "$with_win32" = yes; then
|
||||
elif test "$with_macos" = yes; then
|
||||
AC_MSG_RESULT(macos)
|
||||
AC_DEFINE(BX_WITH_MACOS, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_MACOS)'
|
||||
GUI_OBJS='$(GUI_OBJS_MACOS) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_MACOS)'
|
||||
elif test "$with_carbon" = yes; then
|
||||
AC_MSG_RESULT(carbon)
|
||||
AC_DEFINE(BX_WITH_CARBON, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_CARBON)'
|
||||
GUI_OBJS='$(GUI_OBJS_CARBON) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_CARBON)'
|
||||
PRIMARY_TARGET=bochs.app/.build # only for carbon application
|
||||
elif test "$with_term" = yes; then
|
||||
AC_MSG_RESULT(term)
|
||||
AC_DEFINE(BX_WITH_TERM, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_TERM)'
|
||||
GUI_OBJS='$(GUI_OBJS_TERM) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_TERM)'
|
||||
use_curses=yes
|
||||
elif test "$with_wx" = yes; then
|
||||
AC_MSG_RESULT(wxWindows)
|
||||
AC_DEFINE(BX_WITH_WX, 1)
|
||||
CFLAGS="$CFLAGS `wx-config --cflags`"
|
||||
CXXFLAGS="$CFLAGS `wx-config --cxxflags`"
|
||||
# if gtk-config exists, then add it to the cflags.
|
||||
gtkconf=`gtk-config --cflags`
|
||||
if test $? = 0; then
|
||||
# gtk-config was found and returned 0, so it must return valid output
|
||||
CFLAGS="$CFLAGS `gtk-config --cflags`"
|
||||
CXXFLAGS="$CXXFLAGS `gtk-config --cflags`"
|
||||
fi
|
||||
# wxwindows is the only one without control.o in GUI_OBJS
|
||||
GUI_OBJS='$(GUI_OBJS_WX)'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_WX)'
|
||||
else
|
||||
AC_MSG_RESULT(none)
|
||||
AC_DEFINE(BX_WITH_NOGUI, 1)
|
||||
GUI_OBJS='$(GUI_OBJS_NOGUI)'
|
||||
GUI_OBJS='$(GUI_OBJS_NOGUI) control.o'
|
||||
GUI_LINK_OPTS='$(GUI_LINK_OPTS_NOGUI)'
|
||||
fi
|
||||
|
||||
@ -1184,32 +1204,232 @@ if test "$use_curses" = yes; then
|
||||
fi
|
||||
fi
|
||||
|
||||
|
||||
# The ACX_PTHREAD function was written by
|
||||
# Steven G. Johnson <stevenj@alum.mit.edu> and
|
||||
# Alejandro Forero Cuervo <bachue@bachue.com>
|
||||
# I found it in the ac-archive project on Source Forge.
|
||||
|
||||
AC_DEFUN([ACX_PTHREAD], [
|
||||
AC_REQUIRE([AC_CANONICAL_HOST])
|
||||
acx_pthread_ok=no
|
||||
|
||||
# First, check if the POSIX threads header, pthread.h, is available.
|
||||
# If it isn't, don't bother looking for the threads libraries.
|
||||
AC_CHECK_HEADER(pthread.h, , acx_pthread_ok=noheader)
|
||||
|
||||
# We must check for the threads library under a number of different
|
||||
# names; the ordering is very important because some systems
|
||||
# (e.g. DEC) have both -lpthread and -lpthreads, where one of the
|
||||
# libraries is broken (non-POSIX).
|
||||
|
||||
# First of all, check if the user has set any of the PTHREAD_LIBS,
|
||||
# etcetera environment variables, and if threads linking works using
|
||||
# them:
|
||||
if test x"$PTHREAD_LIBS$PTHREAD_CFLAGS" != x; then
|
||||
save_CFLAGS="$CFLAGS"
|
||||
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
save_LIBS="$LIBS"
|
||||
LIBS="$PTHREAD_LIBS $LIBS"
|
||||
AC_MSG_CHECKING([for pthread_join in LIBS=$PTHREAD_LIBS with CFLAGS=$PTHREAD_CFLAGS])
|
||||
AC_TRY_LINK_FUNC(pthread_join, acx_pthread_ok=yes)
|
||||
AC_MSG_RESULT($acx_pthread_ok)
|
||||
if test x"$acx_pthread_ok" = xno; then
|
||||
PTHREAD_LIBS=""
|
||||
PTHREAD_CFLAGS=""
|
||||
fi
|
||||
LIBS="$save_LIBS"
|
||||
CFLAGS="$save_CFLAGS"
|
||||
fi
|
||||
|
||||
# Create a list of thread flags to try. Items starting with a "-" are
|
||||
# C compiler flags, and other items are library names, except for "none"
|
||||
# which indicates that we try without any flags at all.
|
||||
|
||||
acx_pthread_flags="pthreads none -Kthread -kthread lthread -pthread -pthreads -mthreads pthread --thread-safe -mt"
|
||||
|
||||
# The ordering *is* (sometimes) important. Some notes on the
|
||||
# individual items follow:
|
||||
|
||||
# pthreads: AIX (must check this before -lpthread)
|
||||
# none: in case threads are in libc; should be tried before -Kthread and
|
||||
# other compiler flags to prevent continual compiler warnings
|
||||
# -Kthread: Sequent (threads in libc, but -Kthread needed for pthread.h)
|
||||
# -kthread: FreeBSD kernel threads (preferred to -pthread since SMP-able)
|
||||
# lthread: LinuxThreads port on FreeBSD (also preferred to -pthread)
|
||||
# -pthread: Linux/gcc (kernel threads), BSD/gcc (userland threads)
|
||||
# -pthreads: Solaris/gcc
|
||||
# -mthreads: Mingw32/gcc, Lynx/gcc
|
||||
# -mt: Sun Workshop C (may only link SunOS threads [-lthread], but it
|
||||
# doesn't hurt to check since this sometimes defines pthreads too;
|
||||
# also defines -D_REENTRANT)
|
||||
# pthread: Linux, etcetera
|
||||
# --thread-safe: KAI C++
|
||||
|
||||
case "${host_cpu}-${host_os}" in
|
||||
*solaris*)
|
||||
|
||||
# On Solaris (at least, for some versions), libc contains stubbed
|
||||
# (non-functional) versions of the pthreads routines, so link-based
|
||||
# tests will erroneously succeed. (We need to link with -pthread or
|
||||
# -lpthread.) (The stubs are missing pthread_cleanup_push, or rather
|
||||
# a function called by this macro, so we could check for that, but
|
||||
# who knows whether they'll stub that too in a future libc.) So,
|
||||
# we'll just look for -pthreads and -lpthread first:
|
||||
|
||||
acx_pthread_flags="-pthread -pthreads pthread -mt $acx_pthread_flags"
|
||||
;;
|
||||
esac
|
||||
|
||||
if test x"$acx_pthread_ok" = xno; then
|
||||
for flag in $acx_pthread_flags; do
|
||||
|
||||
case $flag in
|
||||
none)
|
||||
AC_MSG_CHECKING([whether pthreads work without any flags])
|
||||
;;
|
||||
|
||||
-*)
|
||||
AC_MSG_CHECKING([whether pthreads work with $flag])
|
||||
PTHREAD_CFLAGS="$flag"
|
||||
;;
|
||||
|
||||
*)
|
||||
AC_MSG_CHECKING([for the pthreads library -l$flag])
|
||||
PTHREAD_LIBS="-l$flag"
|
||||
;;
|
||||
esac
|
||||
|
||||
save_LIBS="$LIBS"
|
||||
save_CFLAGS="$CFLAGS"
|
||||
LIBS="$PTHREAD_LIBS $LIBS"
|
||||
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
|
||||
# Check for various functions. We must include pthread.h,
|
||||
# since some functions may be macros. (On the Sequent, we
|
||||
# need a special flag -Kthread to make this header compile.)
|
||||
# We check for pthread_join because it is in -lpthread on IRIX
|
||||
# while pthread_create is in libc. We check for pthread_attr_init
|
||||
# due to DEC craziness with -lpthreads. We check for
|
||||
# pthread_cleanup_push because it is one of the few pthread
|
||||
# functions on Solaris that doesn't have a non-functional libc stub.
|
||||
# We try pthread_create on general principles.
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[pthread_t th; pthread_join(th, 0);
|
||||
pthread_attr_init(0); pthread_cleanup_push(0, 0);
|
||||
pthread_create(0,0,0,0); pthread_cleanup_pop(0); ],
|
||||
[acx_pthread_ok=yes])
|
||||
|
||||
LIBS="$save_LIBS"
|
||||
CFLAGS="$save_CFLAGS"
|
||||
|
||||
AC_MSG_RESULT($acx_pthread_ok)
|
||||
if test "x$acx_pthread_ok" = xyes; then
|
||||
break;
|
||||
fi
|
||||
|
||||
PTHREAD_LIBS=""
|
||||
PTHREAD_CFLAGS=""
|
||||
done
|
||||
fi
|
||||
|
||||
# Various other checks:
|
||||
if test "x$acx_pthread_ok" = xyes; then
|
||||
save_LIBS="$LIBS"
|
||||
LIBS="$PTHREAD_LIBS $LIBS"
|
||||
save_CFLAGS="$CFLAGS"
|
||||
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
|
||||
# Detect AIX lossage: threads are created detached by default
|
||||
# and the JOINABLE attribute has a nonstandard name (UNDETACHED).
|
||||
AC_MSG_CHECKING([for joinable pthread attribute])
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[int attr=PTHREAD_CREATE_JOINABLE;],
|
||||
ok=PTHREAD_CREATE_JOINABLE, ok=unknown)
|
||||
if test x"$ok" = xunknown; then
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[int attr=PTHREAD_CREATE_UNDETACHED;],
|
||||
ok=PTHREAD_CREATE_UNDETACHED, ok=unknown)
|
||||
fi
|
||||
if test x"$ok" != xPTHREAD_CREATE_JOINABLE; then
|
||||
AC_DEFINE(PTHREAD_CREATE_JOINABLE, $ok,
|
||||
[Define to the necessary symbol if this constant
|
||||
uses a non-standard name on your system.])
|
||||
fi
|
||||
AC_MSG_RESULT(${ok})
|
||||
if test x"$ok" = xunknown; then
|
||||
AC_MSG_WARN([we do not know how to create joinable pthreads])
|
||||
fi
|
||||
|
||||
AC_MSG_CHECKING([if more special flags are required for pthreads])
|
||||
flag=no
|
||||
case "${host_cpu}-${host_os}" in
|
||||
*-aix* | *-freebsd*) flag="-D_THREAD_SAFE";;
|
||||
*solaris* | alpha*-osf*) flag="-D_REENTRANT";;
|
||||
esac
|
||||
AC_MSG_RESULT(${flag})
|
||||
if test "x$flag" != xno; then
|
||||
PTHREAD_CFLAGS="$flag $PTHREAD_CFLAGS"
|
||||
fi
|
||||
|
||||
LIBS="$save_LIBS"
|
||||
CFLAGS="$save_CFLAGS"
|
||||
|
||||
# More AIX lossage: must compile with cc_r
|
||||
AC_CHECK_PROG(PTHREAD_CC, cc_r, cc_r, ${CC})
|
||||
else
|
||||
PTHREAD_CC="$CC"
|
||||
fi
|
||||
|
||||
AC_SUBST(PTHREAD_LIBS)
|
||||
AC_SUBST(PTHREAD_CFLAGS)
|
||||
AC_SUBST(PTHREAD_CC)
|
||||
|
||||
# Finally, execute ACTION-IF-FOUND/ACTION-IF-NOT-FOUND:
|
||||
if test x"$acx_pthread_ok" = xyes; then
|
||||
ifelse([$1],,AC_DEFINE(HAVE_PTHREAD,1,[Define if you have POSIX threads libraries and header files.]),[$1])
|
||||
:
|
||||
else
|
||||
acx_pthread_ok=no
|
||||
$2
|
||||
fi
|
||||
|
||||
])dnl ACX_PTHREAD
|
||||
|
||||
pthread_ok=no
|
||||
ACX_PTHREAD([
|
||||
pthread_ok=yes
|
||||
#echo Using PTHREAD_LIBS=$PTHREAD_LIBS
|
||||
#echo Using PTHREAD_CFLAGS=$PTHREAD_CFLAGS
|
||||
#echo Using PTHREAD_CC=$PTHREAD_CC
|
||||
])
|
||||
|
||||
|
||||
if test "$with_rfb" = yes; then
|
||||
# first see if compiler takes "-pthread" argument
|
||||
AC_MSG_CHECKING(for -pthread arg to compiler)
|
||||
CFLAGS_SAVE="$CFLAGS"
|
||||
CFLAGS="$CFLAGS -pthread"
|
||||
AC_TRY_LINK([ #include <pthread.h> ],
|
||||
[ pthread_create(0,0,0,0); ],
|
||||
[
|
||||
# it compiles with -pthread
|
||||
AC_MSG_RESULT(yes)
|
||||
CXXFLAGS="$CXXFLAGS -pthread"
|
||||
],
|
||||
[
|
||||
AC_MSG_RESULT(no)
|
||||
# now try with -lpthread
|
||||
CFLAGS="$CFLAGS_SAVE"
|
||||
AC_CHECK_LIB(pthread,
|
||||
pthread_create,
|
||||
[
|
||||
# it compiles with -lpthread
|
||||
RFB_LIBS='-lpthread'
|
||||
],
|
||||
[
|
||||
echo ERROR: --with-rfb requires the pthread library, which could not be found.; exit 1
|
||||
])
|
||||
])
|
||||
if test "$pthread_ok" = yes; then
|
||||
RFB_LIBS="$PTHREAD_LIBS"
|
||||
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
CC="$PTHREAD_CC"
|
||||
else
|
||||
echo ERROR: --with-rfb requires the pthread library, which could not be found.; exit 1
|
||||
fi
|
||||
fi
|
||||
|
||||
if test "$with_wx" = yes; then
|
||||
if test "$pthread_ok" = yes; then
|
||||
GUI_LINK_OPTS="$PTHREAD_LIBS $GUI_LINK_OPTS"
|
||||
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
CXXFLAGS="$CXXFLAGS $PTHREAD_CFLAGS"
|
||||
CC="$PTHREAD_CC"
|
||||
else
|
||||
case "$target" in
|
||||
*-pc-windows* | *-pc-winnt*)
|
||||
# pthread not needed for win32
|
||||
;;
|
||||
*)
|
||||
echo ERROR: --with-wx requires the pthread library, which could not be found.; exit 1
|
||||
esac
|
||||
fi
|
||||
fi
|
||||
|
||||
# Create some subdirectories for when you run configure from some other
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: cpu.cc,v 1.27 2002-04-01 13:14:37 instinc Exp $
|
||||
// $Id: cpu.cc,v 1.28 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
@ -469,6 +469,9 @@ handle_async_event:
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
} else if (BX_CPU_THIS_PTR kill_bochs_request) {
|
||||
// setting kill_bochs_request causes the cpu loop to return ASAP.
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: cpu.h,v 1.18 2002-04-01 04:42:43 instinc Exp $
|
||||
// $Id: cpu.h,v 1.19 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
@ -819,6 +819,7 @@ public: // for now...
|
||||
Bit32u debug_trap; // holds DR6 value to be set as well
|
||||
volatile Boolean async_event;
|
||||
volatile Boolean INTR;
|
||||
volatile Boolean kill_bochs_request;
|
||||
|
||||
/* wether this CPU is the BSP always set for UP */
|
||||
Boolean bsp;
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: dbg_main.cc,v 1.42 2002-04-01 04:44:15 instinc Exp $
|
||||
// $Id: dbg_main.cc,v 1.43 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
@ -285,7 +285,7 @@ bx_dbg_main(int argc, char *argv[])
|
||||
BX_ERROR(( "%s: -rc option used, but no path specified.",
|
||||
argv[0] ));
|
||||
bx_dbg_usage();
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
strncpy(bx_debug_rc_fname, argv[2], BX_MAX_PATH-1);
|
||||
i += 2; // skip past "-rc" and filename
|
||||
|
@ -33,7 +33,7 @@ SHELL = /bin/sh
|
||||
@SET_MAKE@
|
||||
|
||||
CXX = @CXX@
|
||||
CXXFLAGS = @CXXFLAGS@
|
||||
CXXFLAGS = @CXXFLAGS@ `wx-config --cxxflags`
|
||||
|
||||
LDFLAGS = @LDFLAGS@
|
||||
LIBS = @LIBS@
|
||||
@ -53,7 +53,9 @@ GUI_OBJS_NOGUI = nogui.o
|
||||
GUI_OBJS_TERM = term.o
|
||||
GUI_OBJS_RFB = rfb.o
|
||||
GUI_OBJS_AMIGAOS = amigaos.o
|
||||
GUI_OBJS = keymap.o gui.o control.o siminterface.o @GUI_OBJS@
|
||||
GUI_OBJS_WX = wx.o wxmain.o
|
||||
GUI_OBJS = keymap.o gui.o siminterface.o @GUI_OBJS@
|
||||
|
||||
|
||||
BX_INCDIRS = -I.. -I$(srcdir)/.. -I../iodev -I$(srcdir)/../iodev -I../@INSTRUMENT_DIR@ -I$(srcdir)/../@INSTRUMENT_DIR@
|
||||
LOCAL_CXXFLAGS =
|
||||
@ -224,3 +226,5 @@ x.o: x.@CPP_SUFFIX@ ../bochs.h ../config.h ../osdep.h ../debug/debug.h \
|
||||
../iodev/unmapped.h ../iodev/eth.h ../iodev/ne2k.h \
|
||||
../iodev/guest2host.h ../iodev/slowdown_timer.h \
|
||||
../instrument/stubs/instrument.h icon_bochs.h
|
||||
wx.o: wxmain.h
|
||||
wxmain.o: wxmain.h
|
||||
|
41
bochs/gui/bitmaps/cdromd.xpm
Normal file
41
bochs/gui/bitmaps/cdromd.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *cdromd_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
"................................",
|
||||
".............##..###............",
|
||||
"............#....#..#...........",
|
||||
"............#....#..#...........",
|
||||
"............#....#..#...........",
|
||||
".............##..###............",
|
||||
"................................",
|
||||
"............########............",
|
||||
"..........##........##..........",
|
||||
".........#...######...#.........",
|
||||
"........#..##......##..#........",
|
||||
".......#.##..######..##.#.......",
|
||||
"......#.#..##......##..#.#......",
|
||||
".....#..#.#..######..#.#..#.....",
|
||||
".....#.#.#..#......#..#.#.#.....",
|
||||
"....#..#.#.#..####..#.#.#..#....",
|
||||
"....#.#.#.#..#....#..#.#.#.#....",
|
||||
"....#.#.#.#.#......#.#.#.#.#....",
|
||||
"....#.#.#.#.#......#.#.#.#.#....",
|
||||
"....#.#.#.#.#......#.#.#.#.#....",
|
||||
"....#.#.#.#.#......#.#.#.#.#....",
|
||||
"....#.#.#.#..#....#..#.#.#.#....",
|
||||
"....#..#.#.#..####..#.#.#..#....",
|
||||
".....#.#.#..#......#..#.#.#.....",
|
||||
".....#..#.#..######..#.#..#.....",
|
||||
"......#.#..##......##..#.#......",
|
||||
".......#.##..######..##.#.......",
|
||||
"........#..##......##..#........",
|
||||
".........#...######...#.........",
|
||||
"..........##........##..........",
|
||||
"............########............",
|
||||
"................................"
|
||||
};
|
41
bochs/gui/bitmaps/configbutton.xpm
Normal file
41
bochs/gui/bitmaps/configbutton.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *configbutton_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
"................................",
|
||||
"..#....................##.......",
|
||||
"..#############.......####......",
|
||||
"..###############.....####......",
|
||||
"..###############.....####......",
|
||||
"..#############.......####......",
|
||||
"..#....####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####...........####......",
|
||||
".......####..........######.....",
|
||||
".......####.........########....",
|
||||
".......####.........###..###....",
|
||||
".......####.........##....##....",
|
||||
".......####.........##....##....",
|
||||
".......####..........#....#.....",
|
||||
"................................",
|
||||
"...###..###..#...#.###.#..###...",
|
||||
"..#....#...#.##..#.#...#.#......",
|
||||
"..#....#...#.#.#.#.###.#.#..##..",
|
||||
"..#....#...#.#..##.#...#.#...#..",
|
||||
"...###..###..#...#.#...#..###...",
|
||||
"................................"
|
||||
};
|
41
bochs/gui/bitmaps/copy.xpm
Normal file
41
bochs/gui/bitmaps/copy.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *copy_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
"................................",
|
||||
"........####....................",
|
||||
".......#........................",
|
||||
".......#.....##..###..#..#......",
|
||||
".......#....#..#.#..#.#..#......",
|
||||
".......#....#..#.#..#.#..#......",
|
||||
"........####.##..###...###......",
|
||||
".................#.......#......",
|
||||
"...###########...#.......#......",
|
||||
"...#.........#........###.......",
|
||||
"...#.#####.#.#..................",
|
||||
"...#.........#..................",
|
||||
"...#.###.###.#..................",
|
||||
"...#.........#..................",
|
||||
"...#.####..###..................",
|
||||
"...#......#..#..................",
|
||||
"...#...#.....#..................",
|
||||
"...#.#######.#.###########......",
|
||||
"...#.........#.#.........#......",
|
||||
"...###########.#.#####.#.#......",
|
||||
"...............#.........#......",
|
||||
".......#...#...#.###.###.#......",
|
||||
".......#....#..#.........#......",
|
||||
"........######.#.####..###......",
|
||||
"............#..#......#..#......",
|
||||
"...........#...#...#.....#......",
|
||||
"...............#.#######.#......",
|
||||
"...............#.........#......",
|
||||
"...............###########......",
|
||||
"................................",
|
||||
"................................",
|
||||
"................................"
|
||||
};
|
41
bochs/gui/bitmaps/floppya.xpm
Normal file
41
bochs/gui/bitmaps/floppya.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *floppya_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
"...............#................",
|
||||
"..............#.#...............",
|
||||
"..............#.#...#...........",
|
||||
"..............###...............",
|
||||
".............##.##..#...........",
|
||||
".............##.##..............",
|
||||
"................................",
|
||||
".....######################.....",
|
||||
".....####..............####.....",
|
||||
".....#..#.############.#..#.....",
|
||||
".....#..#..............#..#.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....######################.....",
|
||||
".....######################.....",
|
||||
".....######################.....",
|
||||
".....######################.....",
|
||||
".....#######.#.#.#.#.######.....",
|
||||
".....######.#####.#.#.#####.....",
|
||||
".....#######.###.#.#.######.....",
|
||||
".....######.#####.#.#.#####.....",
|
||||
"......######.###.#.#.######.....",
|
||||
".......####.#.#.#.#.#.#####.....",
|
||||
"........####.#.#.#.#.######....."
|
||||
};
|
41
bochs/gui/bitmaps/floppyb.xpm
Normal file
41
bochs/gui/bitmaps/floppyb.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *floppyb_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
".............###................",
|
||||
".............#..#...............",
|
||||
".............###...#............",
|
||||
".............#..#...............",
|
||||
".............#..#..#............",
|
||||
".............###................",
|
||||
"................................",
|
||||
".....######################.....",
|
||||
".....####..............####.....",
|
||||
".....#..#.############.#..#.....",
|
||||
".....#..#..............#..#.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....####.############.####.....",
|
||||
".....####..............####.....",
|
||||
".....######################.....",
|
||||
".....######################.....",
|
||||
".....######################.....",
|
||||
".....######################.....",
|
||||
".....#######.#.#.#.#.######.....",
|
||||
".....######.#####.#.#.#####.....",
|
||||
".....#######.###.#.#.######.....",
|
||||
".....######.#####.#.#.#####.....",
|
||||
"......######.###.#.#.######.....",
|
||||
".......####.#.#.#.#.#.#####.....",
|
||||
"........####.#.#.#.#.######....."
|
||||
};
|
41
bochs/gui/bitmaps/mouse.xpm
Normal file
41
bochs/gui/bitmaps/mouse.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *mouse_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
"................................",
|
||||
".............######.............",
|
||||
"...........##########...........",
|
||||
"..........##........##..........",
|
||||
".........##..........##.........",
|
||||
".........##...........#.........",
|
||||
"...#############......##........",
|
||||
"..##...........##.....##........",
|
||||
"..#..#...#...#..#.....##........",
|
||||
"..#.###.###.###.#......#........",
|
||||
"..#.###.###.###.#......##.......",
|
||||
"..#.###.###.###.#......##.......",
|
||||
"..#.###.###.###.#.......#.......",
|
||||
"..#.###.###.###.#.......##......",
|
||||
"..#.###.###.###.#........##.....",
|
||||
"..#..#...#...#..#.........##....",
|
||||
"..##...........##..........###..",
|
||||
"..#.............#...............",
|
||||
"..##...........##...............",
|
||||
"..#.............#...............",
|
||||
"..##...........##...............",
|
||||
"..#.............#...............",
|
||||
"..##...........##...............",
|
||||
"..#.............#...............",
|
||||
"..##...........##...............",
|
||||
"..#.#.........#.#...............",
|
||||
"..##.#.......#.##...............",
|
||||
"..#.#.#.#.#.#.#.#...............",
|
||||
"..##.#.#.#.#.#.##...............",
|
||||
"...#############................",
|
||||
"................................",
|
||||
"................................"
|
||||
};
|
41
bochs/gui/bitmaps/paste.xpm
Normal file
41
bochs/gui/bitmaps/paste.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *paste_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
"................................",
|
||||
".....####...........#...........",
|
||||
".....#...#.##..###..#..###......",
|
||||
".....#...##..##....####...#.....",
|
||||
".....####.#..#.###..#.#####.....",
|
||||
".....#....#..#....#.#.#.........",
|
||||
".....#.....##.####..#..###......",
|
||||
"...............##...............",
|
||||
"..............##.#..............",
|
||||
"..........#####.######..........",
|
||||
"......####.....##.....####......",
|
||||
".....#...#............#...#.....",
|
||||
".....#..#..............#..#.....",
|
||||
".....#..#..............#..#.....",
|
||||
".....#.##################.#.....",
|
||||
".....#....................#.....",
|
||||
".....#....................#.....",
|
||||
".....#.....###########....#.....",
|
||||
".....#.....#.........#....#.....",
|
||||
".....#.....#.#####.#.#....#.....",
|
||||
".....#.....#.........#....#.....",
|
||||
".....#.....#.###.###.#....#.....",
|
||||
".....#.....#.........#....#.....",
|
||||
".....#.....#.####..###....#.....",
|
||||
".....#.....#......#..#....#.....",
|
||||
".....#.....#...#.....#....#.....",
|
||||
".....#.....#.#######.#....#.....",
|
||||
".....#.....#.........#....#.....",
|
||||
".....#.....###########....#.....",
|
||||
".....#....................#.....",
|
||||
"......####################......",
|
||||
"................................"
|
||||
};
|
41
bochs/gui/bitmaps/power.xpm
Normal file
41
bochs/gui/bitmaps/power.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *power_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
"................................",
|
||||
"................................",
|
||||
".####...........................",
|
||||
"..#..#..###..##..##..##...#.##..",
|
||||
"..#..#.#...#.#...#..#..#...#..#.",
|
||||
".#.##..#...#.#.#.#.#####..#.....",
|
||||
".#.....#..#..##.#..#......#.....",
|
||||
"###.....##...#.#....###..###....",
|
||||
"................................",
|
||||
"...........#######..............",
|
||||
".........###########............",
|
||||
"........####.....####...........",
|
||||
".......###.........###..........",
|
||||
"......##.............##.........",
|
||||
".....###.....###.....###........",
|
||||
".....##......###......##........",
|
||||
"....###......###......###.......",
|
||||
"....##.......###.......##.......",
|
||||
"....##.......###.......##.......",
|
||||
"....##.......###.......##.......",
|
||||
"....##.......###.......##.......",
|
||||
"....##.......###.......##.......",
|
||||
"....###......###......###.......",
|
||||
".....##......###......##........",
|
||||
".....###.....###.....###........",
|
||||
"......##.............##.........",
|
||||
".......###.........###..........",
|
||||
"........####.....####...........",
|
||||
".........###########............",
|
||||
"...........#######..............",
|
||||
"................................",
|
||||
"................................"
|
||||
};
|
41
bochs/gui/bitmaps/reset.xpm
Normal file
41
bochs/gui/bitmaps/reset.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *reset_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
"................................",
|
||||
".............................#..",
|
||||
"..####......................#...",
|
||||
"...#..#...##....###...##..#####.",
|
||||
"...#..#..#..#..#.....#..#...#...",
|
||||
"..#.##..#####...##..#####..#....",
|
||||
"..#..#..#.....#..#..#......#..#.",
|
||||
".###.##..###..###....###....##..",
|
||||
"................................",
|
||||
"................................",
|
||||
"................................",
|
||||
"................................",
|
||||
"................................",
|
||||
"...............#................",
|
||||
"..............##................",
|
||||
".............#######............",
|
||||
"............#########...........",
|
||||
".............#########..........",
|
||||
"........###...##...###..........",
|
||||
"........###....#...###..........",
|
||||
"........###........###..........",
|
||||
"........###........###..........",
|
||||
"........###........###..........",
|
||||
"........###........###..........",
|
||||
"........###........###..........",
|
||||
"........##############..........",
|
||||
".........############...........",
|
||||
"..........##########............",
|
||||
"................................",
|
||||
"................................",
|
||||
"................................",
|
||||
"................................"
|
||||
};
|
41
bochs/gui/bitmaps/snapshot.xpm
Normal file
41
bochs/gui/bitmaps/snapshot.xpm
Normal file
@ -0,0 +1,41 @@
|
||||
/* XPM */
|
||||
static char *snapshot_xpm[] = {
|
||||
/* width height num_colors chars_per_pixel */
|
||||
" 32 32 2 1",
|
||||
/* colors */
|
||||
". c #ffffff",
|
||||
"# c #000000",
|
||||
/* pixels */
|
||||
".....................#........#.",
|
||||
"###.###..##..###.###.###..##.###",
|
||||
"#...#..#...#.#.#.#...#.#.#..#.#.",
|
||||
".##.#..#..##.#.#..##.#.#.#..#.#.",
|
||||
"..#.#..#.#.#.#.#...#.#.#.#..#.#.",
|
||||
"###.##.#.###.###.###.#.#..##..##",
|
||||
".............#..................",
|
||||
"............########............",
|
||||
"...........#........#...........",
|
||||
"..#####.####........#...#####...",
|
||||
".#.########..........#.#.###.#..",
|
||||
".#....#.###..........#.#....#.#.",
|
||||
"##...#.###............##.....###",
|
||||
"########.###.######.###.######.#",
|
||||
"#.......#..##########..#......#.",
|
||||
"#.......#.###......###.#.....#.#",
|
||||
"#########.#..######..#.#########",
|
||||
"########.#.###.#.#.##.#.########",
|
||||
"#########.#.#.#.#.#.##.#########",
|
||||
"#########.##...#.#.#.#.#########",
|
||||
"########.##.#...#.#.#.#.########",
|
||||
"########.#...#.#.#.#.##.########",
|
||||
"########.##...#.#.#.#.#.########",
|
||||
"########.#.#.#.#.#.#.##.########",
|
||||
"########.##.#.#.#.#.#.#.########",
|
||||
".#######.###.#.#.#.#.##.#######.",
|
||||
"........#.#.#.#.#.#.##.#........",
|
||||
"........#.####.#.#.###.#........",
|
||||
".........#.##########.#.........",
|
||||
"..........#..######..#..........",
|
||||
"...........##......##...........",
|
||||
".............######............."
|
||||
};
|
@ -1,10 +1,10 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: control.cc,v 1.46 2002-04-08 00:11:52 bdenney Exp $
|
||||
// $Id: control.cc,v 1.47 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
/*
|
||||
* gui/control.cc
|
||||
* $Id: control.cc,v 1.46 2002-04-08 00:11:52 bdenney Exp $
|
||||
* $Id: control.cc,v 1.47 2002-04-18 00:22:19 bdenney Exp $
|
||||
*
|
||||
* This is code for a text-mode control panel. Note that this file
|
||||
* does NOT include bochs.h. Instead, it does all of its contact with
|
||||
@ -614,24 +614,32 @@ int bx_write_rc (char *rc)
|
||||
char *log_action_ask_choices[] = { "cont", "alwayscont", "die", "abort", "debug" };
|
||||
int log_action_n_choices = 4 + (BX_DEBUGGER?1:0);
|
||||
|
||||
int control_panel_notify_callback (int code)
|
||||
BxEvent *
|
||||
control_panel_notify_callback (void *unused, BxEvent *event)
|
||||
{
|
||||
switch (code)
|
||||
event->retcode = -1;
|
||||
switch (event->type)
|
||||
{
|
||||
case NOTIFY_CODE_LOGMSG:
|
||||
case BX_SYNC_EVT_TICK:
|
||||
event->retcode = 0;
|
||||
return event;
|
||||
case BX_SYNC_EVT_ASK_PARAM:
|
||||
fprintf (stderr, "BX_SYNC_EVT_ASK_PARAM\n");
|
||||
return event;
|
||||
case BX_ASYNC_EVT_SHUTDOWN_GUI:
|
||||
fprintf (stderr, "BX_ASYNC_EVT_SHUTDOWN_GUI\n");
|
||||
return event;
|
||||
case BX_ASYNC_EVT_LOG_MSG:
|
||||
{
|
||||
int level;
|
||||
char prefix[512], msg[512];
|
||||
int retval = SIM->log_msg_2 (prefix, &level, msg, sizeof(msg)) >= 0;
|
||||
assert (retval);
|
||||
int level = event->u.logmsg.level;
|
||||
fprintf (stderr, "========================================================================\n");
|
||||
fprintf (stderr, "Event type: %s\n", SIM->get_log_level_name (level));
|
||||
fprintf (stderr, "Device: %s\n", prefix);
|
||||
fprintf (stderr, "Message: %s\n\n", msg);
|
||||
fprintf (stderr, "Device: %s\n", event->u.logmsg.prefix);
|
||||
fprintf (stderr, "Message: %s\n\n", event->u.logmsg.msg);
|
||||
fprintf (stderr, "A %s has occurred. Do you want to:\n", SIM->get_log_level_name (level));
|
||||
fprintf (stderr, " cont - continue execution\n");
|
||||
fprintf (stderr, " alwayscont - continue execution, and don't ask again.\n");
|
||||
fprintf (stderr, " This affects only %s events from device %s\n", SIM->get_log_level_name (level), prefix);
|
||||
fprintf (stderr, " This affects only %s events from device %s\n", SIM->get_log_level_name (level), event->u.logmsg.prefix);
|
||||
fprintf (stderr, " die - stop execution now\n");
|
||||
fprintf (stderr, " abort - dump core %s\n",
|
||||
BX_HAVE_ABORT ? "" : "(Disabled)");
|
||||
@ -642,24 +650,24 @@ int control_panel_notify_callback (int code)
|
||||
ask:
|
||||
if (ask_menu ("Choose one of the actions above: [%s] ",
|
||||
log_action_n_choices, log_action_ask_choices, 2, &choice) < 0)
|
||||
return SIM->notify_return(-1);
|
||||
event->retcode = -1;
|
||||
// return 0 for continue, 1 for alwayscontinue, 2 for die, 3 for debug.
|
||||
if (!BX_HAVE_ABORT && choice==3) goto ask;
|
||||
fflush(stdout);
|
||||
fflush(stderr);
|
||||
SIM->notify_return(choice);
|
||||
event->retcode = choice;
|
||||
}
|
||||
break;
|
||||
return event;
|
||||
default:
|
||||
fprintf (stderr, "Control panel: notify callback called with unknown code %04x\n", code);
|
||||
fprintf (stderr, "Control panel: notify callback called with event type %04x\n", event->type);
|
||||
return event;
|
||||
}
|
||||
// error if we fall through the case
|
||||
return -1;
|
||||
assert (0); // switch statement should return
|
||||
}
|
||||
|
||||
void bx_control_panel_init () {
|
||||
//fprintf (stderr, "bx_control_panel_init()\n");
|
||||
SIM->set_notify_callback (control_panel_notify_callback);
|
||||
SIM->set_notify_callback (control_panel_notify_callback, NULL);
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: gui.cc,v 1.40 2002-03-30 06:45:30 vruppert Exp $
|
||||
// $Id: gui.cc,v 1.41 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2002 MandrakeSoft S.A.
|
||||
@ -192,24 +192,66 @@ bx_gui_c::update_drive_status_buttons (void) {
|
||||
void
|
||||
bx_gui_c::floppyA_handler(void)
|
||||
{
|
||||
#if BX_WITH_WX
|
||||
// instead of just toggling the status, call wxWindows to bring up
|
||||
// a dialog asking what disk image you want to switch to.
|
||||
int ret = SIM->ask_param (BXP_FLOPPYA_PATH);
|
||||
// eject and then insert the disk. If the new path is invalid,
|
||||
// the status will return 0.
|
||||
unsigned new_status = bx_devices.floppy->set_media_status(0, 0);
|
||||
printf ("eject disk, new_status is %d\n", new_status);
|
||||
new_status = bx_devices.floppy->set_media_status(0, 1);
|
||||
printf ("insert disk, new_status is %d\n", new_status);
|
||||
fflush (stdout);
|
||||
BX_GUI_THIS floppyA_status = new_status;
|
||||
#else
|
||||
BX_GUI_THIS floppyA_status = !BX_GUI_THIS floppyA_status;
|
||||
bx_devices.floppy->set_media_status(0, BX_GUI_THIS floppyA_status);
|
||||
#endif
|
||||
BX_GUI_THIS update_drive_status_buttons ();
|
||||
}
|
||||
|
||||
void
|
||||
bx_gui_c::floppyB_handler(void)
|
||||
{
|
||||
#if BX_WITH_WX
|
||||
// instead of just toggling the status, call wxWindows to bring up
|
||||
// a dialog asking what disk image you want to switch to.
|
||||
int ret = SIM->ask_param (BXP_FLOPPYB_PATH);
|
||||
// eject and then insert the disk. If the new path is invalid,
|
||||
// the status will return 0.
|
||||
unsigned new_status = bx_devices.floppy->set_media_status(1, 0);
|
||||
printf ("eject disk, new_status is %d\n", new_status);
|
||||
new_status = bx_devices.floppy->set_media_status(1, 1);
|
||||
printf ("insert disk, new_status is %d\n", new_status);
|
||||
fflush (stdout);
|
||||
BX_GUI_THIS floppyB_status = new_status;
|
||||
#else
|
||||
BX_GUI_THIS floppyB_status = !BX_GUI_THIS floppyB_status;
|
||||
bx_devices.floppy->set_media_status(1, BX_GUI_THIS floppyB_status);
|
||||
#endif
|
||||
BX_GUI_THIS update_drive_status_buttons ();
|
||||
}
|
||||
|
||||
void
|
||||
bx_gui_c::cdromD_handler(void)
|
||||
{
|
||||
#if BX_WITH_WX
|
||||
// instead of just toggling the status, call wxWindows to bring up
|
||||
// a dialog asking what disk image you want to switch to.
|
||||
int ret = SIM->ask_param (BXP_CDROM_PATH);
|
||||
// eject and then insert the disk. If the new path is invalid,
|
||||
// the status will return 0.
|
||||
unsigned status = bx_devices.hard_drive->set_cd_media_status(0);
|
||||
printf ("eject disk, new_status is %d\n", status);
|
||||
status = bx_devices.hard_drive->set_cd_media_status(1);
|
||||
printf ("insert disk, new_status is %d\n", status);
|
||||
fflush (stdout);
|
||||
BX_GUI_THIS cdromD_status = status;
|
||||
#else
|
||||
BX_GUI_THIS cdromD_status =
|
||||
bx_devices.hard_drive->set_cd_media_status(!BX_GUI_THIS cdromD_status);
|
||||
#endif
|
||||
BX_GUI_THIS update_drive_status_buttons ();
|
||||
}
|
||||
|
||||
@ -231,7 +273,7 @@ bx_gui_c::power_handler(void)
|
||||
BX_PANIC (("POWER button turned off."));
|
||||
// shouldn't reach this point, but if you do, QUIT!!!
|
||||
fprintf (stderr, "Bochs is exiting because you pressed the power button.\n");
|
||||
::exit (1);
|
||||
BX_EXIT (1);
|
||||
}
|
||||
|
||||
Bit32s
|
||||
@ -290,24 +332,24 @@ bx_gui_c::snapshot_handler(void)
|
||||
{
|
||||
char *text_snapshot;
|
||||
Bit32u len;
|
||||
char filename[BX_PATHNAME_LEN];
|
||||
int flag;
|
||||
if (make_text_snapshot (&text_snapshot, &len) < 0) {
|
||||
BX_ERROR(( "snapshot button failed, mode not implemented"));
|
||||
return;
|
||||
}
|
||||
// I wish I had a dialog box!!!
|
||||
flag = 0; // 0 = no dialog present / 1 = OK / -1 = Cancel
|
||||
if (!flag) { // use standard filename if dialog is not present
|
||||
strcpy(filename, "snapshot.txt");
|
||||
flag = 1;
|
||||
}
|
||||
if (flag == 1) {
|
||||
FILE *fp = fopen(filename, "wb");
|
||||
fwrite(text_snapshot, 1, strlen(text_snapshot), fp);
|
||||
fclose(fp);
|
||||
BX_INFO (("copied text snapshot to %s", filename));
|
||||
}
|
||||
//FIXME
|
||||
char filename[BX_PATHNAME_LEN];
|
||||
#if BX_WITH_WX
|
||||
int ret = SIM->ask_filename (filename, sizeof(filename),
|
||||
"Save snapshot as...", "snapshot.txt",
|
||||
bx_param_string_c::BX_SAVE_FILE_DIALOG);
|
||||
if (ret < 0) return; // cancelled
|
||||
#else
|
||||
strcpy (filename, "snapshot.txt");
|
||||
#endif
|
||||
FILE *fp = fopen(filename, "w");
|
||||
fwrite(text_snapshot, 1, strlen(text_snapshot), fp);
|
||||
fclose(fp);
|
||||
free(text_snapshot);
|
||||
}
|
||||
|
||||
@ -334,7 +376,7 @@ bx_gui_c::paste_handler(void)
|
||||
void
|
||||
bx_gui_c::config_handler(void)
|
||||
{
|
||||
#if BX_USE_CONTROL_PANEL
|
||||
#if BX_USE_CONTROL_PANEL && !BX_WITH_WX
|
||||
bx_control_panel (BX_CPANEL_RUNTIME);
|
||||
#else
|
||||
BX_ERROR(( "# CONFIG callback (unimplemented)." ));
|
||||
|
@ -1,14 +1,14 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: siminterface.cc,v 1.39 2002-01-30 10:30:52 cbothamy Exp $
|
||||
// $Id: siminterface.cc,v 1.40 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
/*
|
||||
* gui/siminterface.cc
|
||||
* $Id: siminterface.cc,v 1.39 2002-01-30 10:30:52 cbothamy Exp $
|
||||
* $Id: siminterface.cc,v 1.40 2002-04-18 00:22:19 bdenney Exp $
|
||||
*
|
||||
* Defines the actual link between bx_simulator_interface_c methods
|
||||
* and the simulator. This file includes bochs.h because it needs
|
||||
* access to bx_options and other simulator objecst and methods.
|
||||
* access to bx_options and other simulator objects and methods.
|
||||
*
|
||||
*/
|
||||
|
||||
@ -18,10 +18,23 @@ bx_simulator_interface_c *SIM = NULL;
|
||||
logfunctions *siminterface_log = NULL;
|
||||
#define LOG_THIS siminterface_log->
|
||||
|
||||
// bx_simulator_interface just defines the interface that the Bochs simulator
|
||||
// and the gui will use to talk to each other. None of the methods of
|
||||
// bx_simulator_interface are implemented; they are all virtual. The
|
||||
// bx_real_sim_c class is a child of bx_simulator_interface_c, and it
|
||||
// implements all the methods. The idea is that a gui needs to know only
|
||||
// definition of bx_simulator_interface to talk to Bochs. The gui should
|
||||
// not need to include bochs.h.
|
||||
//
|
||||
// I made this separation to ensure that all guis use the siminterface to do
|
||||
// access bochs internals, instead of accessing things like
|
||||
// bx_keyboard.s.internal_buffer[4] (or whatever) directly. -Bryce
|
||||
//
|
||||
|
||||
class bx_real_sim_c : public bx_simulator_interface_c {
|
||||
sim_interface_callback_t callback;
|
||||
void *callback_ptr;
|
||||
#define BX_NOTIFY_MAX_ARGS 10
|
||||
int notify_return_val;
|
||||
int notify_int_args[BX_NOTIFY_MAX_ARGS];
|
||||
char *notify_string_args[BX_NOTIFY_MAX_ARGS];
|
||||
#define NOTIFY_TYPE_INT
|
||||
@ -35,6 +48,10 @@ public:
|
||||
virtual ~bx_real_sim_c ();
|
||||
virtual int get_init_done () { return init_done; }
|
||||
virtual int set_init_done (int n) { init_done = n; return 0;}
|
||||
virtual void get_param_id_range (int *min, int *max) {
|
||||
*min = BXP_NULL;
|
||||
*max = BXP_THIS_IS_THE_LAST-1;
|
||||
}
|
||||
virtual int register_param (bx_id id, bx_param_c *it);
|
||||
virtual bx_param_c *get_param (bx_id id);
|
||||
virtual bx_param_num_c *get_param_num (bx_id id);
|
||||
@ -46,7 +63,7 @@ public:
|
||||
virtual char *get_action_name (int action);
|
||||
virtual const char *get_log_level_name (int level);
|
||||
virtual int get_max_log_level ();
|
||||
virtual void quit_sim (int clean);
|
||||
virtual void quit_sim (int code);
|
||||
virtual int get_default_rc (char *path, int len);
|
||||
virtual int read_rc (char *path);
|
||||
virtual int write_rc (char *path, int overwrite);
|
||||
@ -55,13 +72,16 @@ public:
|
||||
virtual int get_floppy_options (int drive, bx_floppy_options *out);
|
||||
virtual int get_cdrom_options (int drive, bx_cdrom_options *out);
|
||||
virtual char *get_floppy_type_name (int type);
|
||||
virtual void set_notify_callback (sim_interface_callback_t func);
|
||||
virtual int notify_return (int retcode);
|
||||
virtual int LOCAL_notify (int code);
|
||||
virtual int LOCAL_log_msg (const char *prefix, int level, char *msg);
|
||||
virtual int log_msg_2 (char *prefix, int *level, char *msg, int len);
|
||||
virtual void set_notify_callback (sim_interface_callback_t func, void *arg);
|
||||
virtual BxEvent* sim_to_gui_event (BxEvent *event);
|
||||
virtual int log_msg (const char *prefix, int level, char *msg);
|
||||
virtual int ask_param (bx_id which);
|
||||
virtual int get_enabled () { return enabled; }
|
||||
virtual void set_enabled (int enabled) { this->enabled = enabled; }
|
||||
// ask the user for a pathname
|
||||
virtual int ask_filename (char *filename, int maxlen, char *prompt, char *the_default, int flags);
|
||||
// called at a regular interval, currently by the keyboard handler.
|
||||
virtual void periodic ();
|
||||
};
|
||||
|
||||
bx_param_c *
|
||||
@ -70,8 +90,8 @@ bx_real_sim_c::get_param (bx_id id)
|
||||
BX_ASSERT (id >= BXP_NULL && id < BXP_THIS_IS_THE_LAST);
|
||||
int index = (int)id - BXP_NULL;
|
||||
bx_param_c *retval = param_registry[index];
|
||||
if (!retval)
|
||||
BX_PANIC (("get_param can't find id %u", id));
|
||||
if (!retval)
|
||||
BX_INFO (("get_param can't find id %u", id));
|
||||
return retval;
|
||||
}
|
||||
|
||||
@ -102,7 +122,7 @@ bx_real_sim_c::get_param_string (bx_id id) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void init_siminterface ()
|
||||
void bx_init_siminterface ()
|
||||
{
|
||||
siminterface_log = new logfunctions ();
|
||||
siminterface_log->put ("CTRL");
|
||||
@ -118,16 +138,24 @@ bx_simulator_interface_c::bx_simulator_interface_c ()
|
||||
bx_real_sim_c::bx_real_sim_c ()
|
||||
{
|
||||
callback = NULL;
|
||||
notify_return_val = -1;
|
||||
for (int i=0; i<BX_NOTIFY_MAX_ARGS; i++) {
|
||||
callback_ptr = NULL;
|
||||
|
||||
enabled = 1;
|
||||
int i;
|
||||
for (i=0; i<BX_NOTIFY_MAX_ARGS; i++) {
|
||||
notify_int_args[i] = -1;
|
||||
notify_string_args[i] = NULL;
|
||||
}
|
||||
init_done = 0;
|
||||
registry_alloc_size = BXP_THIS_IS_THE_LAST - BXP_NULL;
|
||||
param_registry = new bx_param_c* [registry_alloc_size];
|
||||
for (i=0; i<registry_alloc_size; i++)
|
||||
param_registry[i] = NULL;
|
||||
}
|
||||
|
||||
// called by constructor of bx_param_c, so that every parameter that is
|
||||
// initialized gets registered. This builds a list of all parameters
|
||||
// which can be used to look them up by number (get_param).
|
||||
bx_real_sim_c::~bx_real_sim_c ()
|
||||
{
|
||||
if ( param_registry != NULL )
|
||||
@ -140,8 +168,12 @@ bx_real_sim_c::~bx_real_sim_c ()
|
||||
int
|
||||
bx_real_sim_c::register_param (bx_id id, bx_param_c *it)
|
||||
{
|
||||
if (id == BXP_NULL) return 0;
|
||||
BX_ASSERT (id >= BXP_NULL && id < BXP_THIS_IS_THE_LAST);
|
||||
int index = (int)id - BXP_NULL;
|
||||
if (this->param_registry[index] != NULL) {
|
||||
BX_INFO (("register_param is overwriting parameter id %d", id));
|
||||
}
|
||||
this->param_registry[index] = it;
|
||||
return 0;
|
||||
}
|
||||
@ -192,10 +224,34 @@ bx_real_sim_c::get_max_log_level ()
|
||||
}
|
||||
|
||||
void
|
||||
bx_real_sim_c::quit_sim (int clean) {
|
||||
if (!clean)
|
||||
bx_real_sim_c::quit_sim (int code) {
|
||||
#if 0
|
||||
if (!code)
|
||||
BX_PANIC (("Quit simulation command"));
|
||||
// tell bochs to shut down (includes vga screen)
|
||||
bx_atexit ();
|
||||
// tell the control panel to shut down
|
||||
BxEvent *event = new BxEvent ();
|
||||
event->type = BX_ASYNC_EVT_SHUTDOWN_GUI;
|
||||
sim_to_gui_event (event);
|
||||
// set something that will cause the cpu loop to exit.
|
||||
// or use setjmp/longjmp, or something.
|
||||
//FIXME!
|
||||
#endif
|
||||
BX_INFO (("quit_sim called"));
|
||||
#if BX_WITH_WX
|
||||
// in wxWindows, the whole simulator is running in a separate thread.
|
||||
// our only job is to end the thread as soon as possible, NOT to shut
|
||||
// down the whole application with an exit.
|
||||
BX_CPU_THIS_PTR async_event = 1;
|
||||
BX_CPU_THIS_PTR kill_bochs_request = 1;
|
||||
// the cpu loop will exit very soon after this condition is set.
|
||||
#else
|
||||
// just a single thread. Use exit() to stop the application.
|
||||
if (!code)
|
||||
BX_PANIC (("Quit simulation command"));
|
||||
::exit (0);
|
||||
#endif
|
||||
}
|
||||
|
||||
int
|
||||
@ -272,54 +328,35 @@ bx_real_sim_c::get_floppy_type_name (int type)
|
||||
}
|
||||
|
||||
void
|
||||
bx_real_sim_c::set_notify_callback (sim_interface_callback_t func)
|
||||
bx_real_sim_c::set_notify_callback (sim_interface_callback_t func, void *arg)
|
||||
{
|
||||
callback = func;
|
||||
callback_ptr = arg;
|
||||
}
|
||||
|
||||
int
|
||||
bx_real_sim_c::notify_return (int retcode)
|
||||
{
|
||||
notify_return_val = retcode;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
bx_real_sim_c::LOCAL_notify (int code)
|
||||
BxEvent *
|
||||
bx_real_sim_c::sim_to_gui_event (BxEvent *event)
|
||||
{
|
||||
if (callback == NULL) {
|
||||
BX_ERROR (("notify called, but no callback function is registered"));
|
||||
return -1;
|
||||
return NULL;
|
||||
} else {
|
||||
notify_return_val = -999;
|
||||
(*callback)(code);
|
||||
if (notify_return_val == -999)
|
||||
BX_ERROR (("notify callback returned without setting the return value"));
|
||||
return notify_return_val;
|
||||
return (*callback)(callback_ptr, event);
|
||||
}
|
||||
}
|
||||
|
||||
// returns 0 for continue, 1 for alwayscontinue, 2 for die.
|
||||
int
|
||||
bx_real_sim_c::LOCAL_log_msg (const char *prefix, int level, char *msg)
|
||||
bx_real_sim_c::log_msg (const char *prefix, int level, char *msg)
|
||||
{
|
||||
BxEvent *be = new BxEvent ();
|
||||
be->type = BX_ASYNC_EVT_LOG_MSG;
|
||||
be->u.logmsg.prefix = (char *)prefix;
|
||||
be->u.logmsg.level = level;
|
||||
be->u.logmsg.msg = msg;
|
||||
//fprintf (stderr, "calling notify.\n");
|
||||
notify_string_args[0] = strdup(prefix);
|
||||
notify_int_args[1] = level;
|
||||
notify_string_args[2] = msg;
|
||||
int val = LOCAL_notify (NOTIFY_CODE_LOGMSG);
|
||||
//fprintf (stderr, "notify returned %d\n", val);
|
||||
return val;
|
||||
}
|
||||
|
||||
// called by control.cc
|
||||
int
|
||||
bx_real_sim_c::log_msg_2 (char *prefix, int *level, char *msg, int len)
|
||||
{
|
||||
strncpy (prefix, notify_string_args[0], len);
|
||||
*level= notify_int_args[1];
|
||||
strncpy (msg, notify_string_args[2], len);
|
||||
return 0;
|
||||
BxEvent *response = sim_to_gui_event (be);
|
||||
return response? response->retcode : -1;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
@ -332,8 +369,8 @@ bx_object_c::bx_object_c (bx_id id)
|
||||
this->type = BXT_OBJECT;
|
||||
}
|
||||
|
||||
void
|
||||
bx_object_c::set_type (Bit8u type)
|
||||
void
|
||||
bx_object_c::set_type (bx_objtype type)
|
||||
{
|
||||
this->type = type;
|
||||
}
|
||||
@ -459,6 +496,16 @@ bx_param_string_c::bx_param_string_c (bx_id id,
|
||||
set (initial_val);
|
||||
}
|
||||
|
||||
bx_param_filename_c::bx_param_filename_c (bx_id id,
|
||||
char *name,
|
||||
char *description,
|
||||
char *initial_val,
|
||||
int maxsize)
|
||||
: bx_param_string_c (id, name, description, initial_val, maxsize)
|
||||
{
|
||||
get_options()->set (BX_IS_FILENAME);
|
||||
}
|
||||
|
||||
bx_param_string_c::~bx_param_string_c ()
|
||||
{
|
||||
if ( this->val != NULL )
|
||||
@ -608,3 +655,62 @@ bx_list_c::set_parent (bx_param_c *parent)
|
||||
{
|
||||
this->parent = parent;
|
||||
}
|
||||
|
||||
// Called by simulator whenever it needs the user to choose a new value
|
||||
// for a registered parameter. Create a synchronous ASK_PARAM event,
|
||||
// send it to the GUI, and wait for the response. The GUI will call the
|
||||
// set() method on the parameter if the user changes the value.
|
||||
int
|
||||
bx_real_sim_c::ask_param (bx_id param)
|
||||
{
|
||||
bx_param_c *paramptr = SIM->get_param(param);
|
||||
BX_ASSERT (paramptr != NULL);
|
||||
// create appropriate event
|
||||
BxEvent *event = new BxEvent ();
|
||||
event->type = BX_SYNC_EVT_ASK_PARAM;
|
||||
event->u.param.param = paramptr;
|
||||
BxEvent *response = sim_to_gui_event (event);
|
||||
return response->retcode;
|
||||
}
|
||||
|
||||
int
|
||||
bx_real_sim_c::ask_filename (char *filename, int maxlen, char *prompt, char *the_default, int flags)
|
||||
{
|
||||
// implement using ASK_PARAM on a newly created param. I can't use
|
||||
// ask_param because I don't intend to register this param.
|
||||
BxEvent event;
|
||||
bx_param_string_c param (BXP_NULL, "filename", prompt, the_default, maxlen);
|
||||
flags |= param.BX_IS_FILENAME;
|
||||
param.get_options()->set (flags);
|
||||
event.type = BX_SYNC_EVT_ASK_PARAM;
|
||||
event.u.param.param = ¶m;
|
||||
BxEvent *response = sim_to_gui_event (&event);
|
||||
BX_ASSERT ((response == &event));
|
||||
if (event.retcode >= 0)
|
||||
memcpy (filename, param.getptr(), maxlen);
|
||||
return event.retcode;
|
||||
}
|
||||
|
||||
void
|
||||
bx_real_sim_c::periodic ()
|
||||
{
|
||||
// give the GUI a chance to do periodic things on the bochs thread. in
|
||||
// particular, notice if the thread has been asked to die.
|
||||
BxEvent *tick = new BxEvent ();
|
||||
tick->type = BX_SYNC_EVT_TICK;
|
||||
BxEvent *response = sim_to_gui_event (tick);
|
||||
int retcode = response->retcode;
|
||||
BX_ASSERT (response == tick);
|
||||
delete tick;
|
||||
if (retcode < 0) {
|
||||
BX_INFO (("Bochs thread has been asked to quit."));
|
||||
quit_sim (0);
|
||||
}
|
||||
#if 0
|
||||
// watch for memory leaks. Allocate a small block of memory, print the
|
||||
// pointer that is returned, then free.
|
||||
BxEvent *memcheck = new BxEvent ();
|
||||
BX_INFO(("memory allocation at %p", memcheck));
|
||||
delete memcheck;
|
||||
#endif
|
||||
}
|
||||
|
@ -1,10 +1,10 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: siminterface.h,v 1.34 2002-03-26 13:51:48 bdenney Exp $
|
||||
// $Id: siminterface.h,v 1.35 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
/*
|
||||
* gui/siminterface.h
|
||||
* $Id: siminterface.h,v 1.34 2002-03-26 13:51:48 bdenney Exp $
|
||||
* $Id: siminterface.h,v 1.35 2002-04-18 00:22:19 bdenney Exp $
|
||||
*
|
||||
* Interface to the simulator, currently only used by control.cc.
|
||||
* The base class bx_simulator_interface_c, contains only virtual functions
|
||||
@ -18,10 +18,40 @@
|
||||
*
|
||||
*/
|
||||
|
||||
#define BX_UI_TEXT 1
|
||||
// BX_UI_TEXT should be set to 1 when the text mode configuration interface
|
||||
// is compiled in. This gives each type of parameter a text_print and text_ask
|
||||
// method (defined in gui/control.cc) so that you can call text_ask() on any
|
||||
// kind of parameter to ask the user to edit the value.
|
||||
//
|
||||
// I have been considering whether to use the same strategy for the wxWindows
|
||||
// interface, but I'm not sure if I like it. One problem is that in order to
|
||||
// declare member functions that are useful for wxWindows, the wxWindows header
|
||||
// files would have to be included before the param object definitions. That
|
||||
// means that all the wxwindows headers would have be included when compiling
|
||||
// every single bochs file. One of the things I like about the separation
|
||||
// between the simulator and GUI is that the two halves can be compiled without
|
||||
// any knowledge of the other. Bochs doesn't include <wx.h>, and the wxwindows
|
||||
// code doesn't include <bochs.h>. Aside from making compiles faster, this
|
||||
// enforces the use of the interface so it keeps the interface clean (important
|
||||
// when we may have multiple GUI implementations for example). This argues
|
||||
// for keeping GUI-specific structures out of the simulator interface. It
|
||||
// certainly works well for the text interface, but that's because FILE* is
|
||||
// standard and portable.
|
||||
#define BX_UI_TEXT (!BX_WITH_WX)
|
||||
|
||||
//////////////////////////////////////////////////////
|
||||
|
||||
// list of possible types for bx_param_c and descendant objects
|
||||
typedef enum {
|
||||
BXT_OBJECT = 201,
|
||||
BXT_PARAM,
|
||||
BXT_PARAM_NUM,
|
||||
BXT_PARAM_BOOL,
|
||||
BXT_PARAM_ENUM,
|
||||
BXT_PARAM_STRING,
|
||||
BXT_LIST
|
||||
} bx_objtype;
|
||||
|
||||
typedef enum {
|
||||
BXP_NULL = 101,
|
||||
BXP_IPS,
|
||||
@ -115,27 +145,194 @@ typedef enum {
|
||||
BXP_KEYBOARD_USEMAPPING,
|
||||
BXP_KEYBOARD_MAP,
|
||||
BXP_KEYBOARD,
|
||||
BXP_ASK_FOR_PATHNAME, // for general file selection dialog
|
||||
BXP_THIS_IS_THE_LAST // used to determine length of list
|
||||
} bx_id;
|
||||
|
||||
typedef enum {
|
||||
BXT_OBJECT = 201,
|
||||
BXT_NODE,
|
||||
BXT_PARAM,
|
||||
BXT_PARAM_NUM,
|
||||
BXT_PARAM_BOOL,
|
||||
BXT_PARAM_ENUM,
|
||||
BXT_PARAM_STRING,
|
||||
BXT_LIST
|
||||
} bx_objtype;
|
||||
BX_TOOLBAR_UNDEFINED,
|
||||
BX_TOOLBAR_FLOPPYA,
|
||||
BX_TOOLBAR_FLOPPYB,
|
||||
BX_TOOLBAR_CDROMD,
|
||||
BX_TOOLBAR_RESET,
|
||||
BX_TOOLBAR_POWER,
|
||||
BX_TOOLBAR_COPY,
|
||||
BX_TOOLBAR_PASTE,
|
||||
BX_TOOLBAR_SNAPSHOT,
|
||||
BX_TOOLBAR_CONFIG,
|
||||
BX_TOOLBAR_MOUSE_EN
|
||||
} bx_toolbar_buttons;
|
||||
|
||||
// Log level defines
|
||||
typedef enum {
|
||||
LOGLEV_DEBUG = 0,
|
||||
LOGLEV_INFO,
|
||||
LOGLEV_ERROR,
|
||||
LOGLEV_PANIC,
|
||||
N_LOGLEV
|
||||
} bx_log_levels;
|
||||
|
||||
///////////////////////////////////////////////////////////////////
|
||||
// event structure for communication between simulator and gui
|
||||
///////////////////////////////////////////////////////////////////
|
||||
|
||||
///// types and definitions used in event structures
|
||||
|
||||
#define BX_EVT_IS_ASYNC(type) ((type) > __ALL_EVENTS_BELOW_ARE_ASYNC__)
|
||||
|
||||
typedef enum {
|
||||
__ALL_EVENTS_BELOW_ARE_SYNCHRONOUS__ = 2000,
|
||||
BX_SYNC_EVT_GET_PARAM, // cpanel -> simulator -> cpanel
|
||||
BX_SYNC_EVT_ASK_PARAM, // simulator -> cpanel -> simulator
|
||||
BX_SYNC_EVT_TICK, // simulator -> cpanel, wait for response.
|
||||
__ALL_EVENTS_BELOW_ARE_ASYNC__,
|
||||
BX_ASYNC_EVT_KEY, // vga gui -> simulator
|
||||
BX_ASYNC_EVT_MOUSE, // vga gui -> simulator
|
||||
BX_ASYNC_EVT_SET_PARAM, // cpanel -> simulator
|
||||
BX_ASYNC_EVT_LOG_MSG, // simulator -> cpanel
|
||||
BX_ASYNC_EVT_VALUE_CHANGED, // simulator -> cpanel
|
||||
BX_ASYNC_EVT_SHUTDOWN_GUI, // simulator -> cpanel
|
||||
BX_ASYNC_EVT_TOOLBAR // cpanel -> simulator
|
||||
} BxEventType;
|
||||
|
||||
typedef union {
|
||||
Bit32s s32;
|
||||
char *charptr;
|
||||
} AnyParamVal;
|
||||
|
||||
// Define substructures which make up the interior of BxEvent. The
|
||||
// substructures, such as BxKeyEvent or BxMouseEvent, should never be allocated
|
||||
// on their own. They are only intended to be used within the union in the
|
||||
// BxEvent structure.
|
||||
|
||||
// Event type: BX_SYNC_EVT_TICK
|
||||
// A tick event is synchronous, sent from the simulator to the GUI. The
|
||||
// event doesn't do anything visible. Primarily it gives the GUI a chance
|
||||
// to tell the simulator to quit, if necessary. There may be other uses
|
||||
// for the tick, such as giving some kind of regular status report or
|
||||
// mentioning watched values that changed, but so far it's just for
|
||||
// that one thing. There is no data associated with a tick event.
|
||||
|
||||
// Event type: BX_ASYNC_EVT_KEY
|
||||
// (unused)
|
||||
// A key event can be sent from the GUI to the Bochs simulator. It is
|
||||
// asynchronous.
|
||||
typedef struct {
|
||||
// what was pressed? This is a BX_KEY_* value. For key releases,
|
||||
// BX_KEY_RELEASED is ORed with the base BX_KEY_*.
|
||||
Bit32u bx_key;
|
||||
Boolean raw_scancode;
|
||||
} BxKeyEvent;
|
||||
|
||||
// Event type: BX_ASYNC_EVT_MOUSE
|
||||
// (unused)
|
||||
// A mouse event can be sent from the GUI to the Bochs simulator. It is
|
||||
// asynchronous. Currently not used, but when Psyon's wxwindows gui is
|
||||
// integrated, we will need mouse events.
|
||||
typedef struct {
|
||||
// type is BX_EVT_MOUSE
|
||||
Bit16u x, y; // coordinate (vga screen?)
|
||||
Bit8u buttons; // which buttons are pressed.
|
||||
// bit 0: 1=left button down, 0=up
|
||||
// bit 1: 1=right button down, 0=up
|
||||
} BxMouseEvent;
|
||||
|
||||
// Event type: BX_SYNC_EVT_GET_PARAM, BX_ASYNC_EVT_SET_PARAM
|
||||
// (unused)
|
||||
// Parameter set/get events are initiated by the GUI, since Bochs can always
|
||||
// access the parameters directly. So far, I haven't used this type. In
|
||||
// the GUI I just call SIM->get_param(parameter_id) to get a pointer to the
|
||||
// bx_param_c object and then call the get/set methods. This is okay for
|
||||
// configuration since bochs is not running. However it could be dangerous
|
||||
// for the GUI thread to poke around in Bochs structures while the thread is
|
||||
// running. For these cases, I may have to be more careful: build parameter
|
||||
// change events in the GUI and place them on Bochs's event queue to be
|
||||
// processed during SIM->periodic() or something.
|
||||
typedef struct {
|
||||
// type is BX_EVT_GET_PARAM, BX_EVT_SET_PARAM
|
||||
class bx_param_c *param; // pointer to param structure
|
||||
AnyParamVal val;
|
||||
} BxParamEvent;
|
||||
|
||||
// Event type: BX_SYNC_EVT_ASK_PARAM
|
||||
// Syncronous event sent from the simulator to the GUI. This tells the
|
||||
// GUI to ask the user to choose the value of a parameter. The GUI may
|
||||
// need to discover the type of parameter so that it can use the right
|
||||
// kind of graphical display. The BxParamEvent is used for these events
|
||||
// too.
|
||||
// FIXME: at the moment the GUI implements the ASK_PARAM event for just
|
||||
// a few parameter types. I need to implement the event for all parameter
|
||||
// types.
|
||||
|
||||
// Event type: BX_ASYNC_EVT_VALUE_CHANGED
|
||||
// (unused)
|
||||
// Asynchronous event sent from the simulator to the GUI, telling it that
|
||||
// some value that it (hopefully) cares about has changed. This isn't
|
||||
// being used yet, but a good example is in a debugger interface, you might
|
||||
// want to maintain a reasonably current display of the PC or some other
|
||||
// simulation state. The GUI would set some kind of event mask (which
|
||||
// doesn't exist now of course) and then when certain values change, the
|
||||
// simulator would send this event so that the GUI can update. We may need
|
||||
// some kind of "flow control" since the simulator will be able to produce
|
||||
// new events much faster than the gui can handle them.
|
||||
|
||||
// Event type: BX_ASYNC_EVT_LOG_MSG
|
||||
// Asynchronous event from the simulator to the GUI. When a BX_PANIC,
|
||||
// BX_ERROR, BX_INFO, or BX_DEBUG is found in the simulator code, this
|
||||
// event type can be used to inform the GUI of the condition. There is
|
||||
// no point in sending messages to the GUI that will not be displayed; these
|
||||
// would only slow the simulation. So we will need some mechanism for
|
||||
// choosing what kinds of events will be delivered to the GUI. Normally,
|
||||
// you wouldn't want to look at the log unless something is going wrong.
|
||||
// At that point, you might want to open up a window to watch the debug
|
||||
// messages from one device only.
|
||||
//
|
||||
// Idea: Except for panics that require user attention to continue, it might be
|
||||
// most efficient to just append log messages to a file. When the user wants
|
||||
// to look at the log messages, the gui can reopen the file (read only), skip
|
||||
// to the end, and look backward for a reasonable number of lines to display
|
||||
// (200?). This allows it to skip over huge bursts of log entries without
|
||||
// allocating memory, synchronizing threads, etc. for each.
|
||||
typedef struct {
|
||||
// type is BX_EVT_LOG_MSG
|
||||
Bit8u level;
|
||||
char *prefix;
|
||||
char *msg;
|
||||
} BxLogMsgEvent;
|
||||
|
||||
// Event type: BX_EVT_TOOLBAR
|
||||
// Asynchronous event from the GUI to the simulator, sent when the user
|
||||
// clicks on a toolbar button. This may one day become something more
|
||||
// general, like a command event, but at the moment it's only needed for
|
||||
// the toolbar events.
|
||||
typedef struct {
|
||||
bx_toolbar_buttons button;
|
||||
bool on; // for toggling buttons, on=true means the toolbar button is
|
||||
// pressed. on=false means it is not pressed.
|
||||
} BxToolbarEvent;
|
||||
|
||||
// The BxEvent structure should be used for all events. Every event has
|
||||
// a type and a spot for a return code (only used for synchronous events).
|
||||
typedef struct {
|
||||
BxEventType type; // what kind is this?
|
||||
Bit32s retcode; // sucess or failure. only used for synchronous events.
|
||||
union {
|
||||
BxKeyEvent key;
|
||||
BxMouseEvent mouse;
|
||||
BxParamEvent param;
|
||||
BxLogMsgEvent logmsg;
|
||||
BxToolbarEvent toolbar;
|
||||
} u;
|
||||
} BxEvent;
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
class bx_object_c {
|
||||
private:
|
||||
bx_id id;
|
||||
Bit8u type;
|
||||
bx_objtype type;
|
||||
protected:
|
||||
void set_type (Bit8u type);
|
||||
void set_type (bx_objtype type);
|
||||
public:
|
||||
bx_object_c (bx_id id);
|
||||
bx_id get_id () { return id; }
|
||||
@ -151,9 +348,7 @@ protected:
|
||||
int runtime_param;
|
||||
int enabled;
|
||||
public:
|
||||
bx_param_c (bx_id id,
|
||||
char *name,
|
||||
char *description);
|
||||
bx_param_c (bx_id id, char *name, char *description);
|
||||
void set_format (char *format) {text_format = format;}
|
||||
char *get_format () {return text_format;}
|
||||
void set_ask_format (char *format) {ask_format = format; }
|
||||
@ -188,6 +383,9 @@ public:
|
||||
Bit32s get ();
|
||||
void set (Bit32s val);
|
||||
void set_base (int base) { this->base = base; }
|
||||
int get_base () { return base; }
|
||||
Bit32s get_min () { return min; }
|
||||
Bit32s get_max () { return max; }
|
||||
#if BX_UI_TEXT
|
||||
virtual void text_print (FILE *fp);
|
||||
virtual int text_ask (FILE *fpin, FILE *fpout);
|
||||
@ -215,6 +413,7 @@ public:
|
||||
char **choices,
|
||||
Bit32s initial_val,
|
||||
Bit32s value_base = 0);
|
||||
char *get_choice (int n) { return choices[n]; }
|
||||
#if BX_UI_TEXT
|
||||
virtual void text_print (FILE *fp);
|
||||
virtual int text_ask (FILE *fpin, FILE *fpout);
|
||||
@ -231,7 +430,10 @@ class bx_param_string_c : public bx_param_c {
|
||||
char separator;
|
||||
public:
|
||||
enum {
|
||||
BX_RAW_BYTES = 1,
|
||||
BX_RAW_BYTES = 1, // need binary text editor, like MAC addr
|
||||
BX_IS_FILENAME = 2, // 1=yes it's a filename, 0=not a filename.
|
||||
// Some guis have a file browser.
|
||||
BX_SAVE_FILE_DIALOG = 4, // Use save dialog opposed to open file dialog
|
||||
} bx_string_opt_bits;
|
||||
bx_param_string_c (bx_id id,
|
||||
char *name,
|
||||
@ -252,6 +454,18 @@ public:
|
||||
#endif
|
||||
};
|
||||
|
||||
// declare a filename class. It is identical to a string, except that
|
||||
// it initializes the options differently. This is just a shortcut
|
||||
// for declaring a string param and setting the options with BX_IS_FILENAME.
|
||||
class bx_param_filename_c : public bx_param_string_c {
|
||||
public:
|
||||
bx_param_filename_c (bx_id id,
|
||||
char *name,
|
||||
char *description,
|
||||
char *initial_val,
|
||||
int maxsize=-1);
|
||||
};
|
||||
|
||||
class bx_list_c : public bx_param_c {
|
||||
private:
|
||||
// just a list of bx_param_c objects. size tells current number of
|
||||
@ -347,12 +561,14 @@ struct bx_cdrom_options
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
extern int bx_main (int argc, char *argv[]);
|
||||
|
||||
class bx_simulator_interface_c {
|
||||
public:
|
||||
bx_simulator_interface_c ();
|
||||
virtual int get_init_done () { return -1; }
|
||||
virtual int set_init_done (int n) {return -1;}
|
||||
virtual void get_param_id_range (int *min, int *max) {}
|
||||
virtual int register_param (bx_id id, bx_param_c *it) {return -1;}
|
||||
virtual bx_param_c *get_param (bx_id id) {return NULL;}
|
||||
virtual bx_param_num_c *get_param_num (bx_id id) {return NULL;}
|
||||
@ -364,7 +580,15 @@ public:
|
||||
virtual char *get_action_name (int action) {return 0;}
|
||||
virtual const char *get_log_level_name (int level) {return 0;}
|
||||
virtual int get_max_log_level () {return -1;}
|
||||
virtual void quit_sim (int clean) {}
|
||||
|
||||
// exiting is somewhat complicated! The preferred way to exit bochs is
|
||||
// to call BX_EXIT(exitcode). That is defined to call
|
||||
// SIM->quit_sim(exitcode). The quit_sim function first calls
|
||||
// the cleanup functions in bochs so that it can destroy windows
|
||||
// and free up memory, then sends a notify message to the control
|
||||
// panel telling it that bochs has stopped.
|
||||
virtual void quit_sim (int code) {}
|
||||
|
||||
virtual int get_default_rc (char *path, int len) {return -1;}
|
||||
virtual int read_rc (char *path) {return -1;}
|
||||
virtual int write_rc (char *rc, int overwrite) {return -1;}
|
||||
@ -373,19 +597,36 @@ public:
|
||||
virtual int get_floppy_options (int drive, bx_floppy_options *out) {return -1;}
|
||||
virtual int get_cdrom_options (int drive, bx_cdrom_options *out) {return -1;}
|
||||
virtual char *get_floppy_type_name (int type) {return NULL;}
|
||||
typedef int (*sim_interface_callback_t)(int code);
|
||||
virtual void set_notify_callback (sim_interface_callback_t func) {}
|
||||
virtual int notify_return (int retcode) {return -1;}
|
||||
// methods marked LOCAL should only be called by the simulator, not
|
||||
// from the control panel.
|
||||
#define NOTIFY_CODE_LOGMSG 0x101
|
||||
virtual int LOCAL_notify (int code) {return -1;}
|
||||
virtual int LOCAL_log_msg (const char *prefix, int level, char *msg) {return -1;}
|
||||
virtual int log_msg_2 (char *prefix, int *level, char *msg, int len) {return -1;}
|
||||
|
||||
// The control panel calls set_notify_callback to register an event
|
||||
// handler. This handler is for events which are generated by Bochs
|
||||
// or the Bochs controller vga screen. For example, if the simulator
|
||||
// hits a panic and wants a dialog box to appear, it would use the
|
||||
// sim_interface_callback to ask the control panel to display a dialog.
|
||||
// At present, the standard floppy disk buttons, power button, etc are under
|
||||
// control of Bochs, NOT the control panel. Bochs uses the callback to tell
|
||||
// the control panel that one of these buttons has been pressed.
|
||||
typedef BxEvent* (*sim_interface_callback_t)(void *theclass, BxEvent *event);
|
||||
virtual void set_notify_callback (sim_interface_callback_t func, void *arg) {}
|
||||
|
||||
// send an event from the simulator to the GUI.
|
||||
virtual BxEvent* sim_to_gui_event (BxEvent *event) {return NULL;}
|
||||
|
||||
// this "notify arg" passing is very ugly and Bryce needs to clean it up!
|
||||
virtual int log_msg (const char *prefix, int level, char *msg) {return -1;}
|
||||
// called by gui.cc event handler when a button is pressed.
|
||||
virtual int ask_param (bx_id param) {return -1;}
|
||||
|
||||
virtual int get_enabled () {return -1;}
|
||||
virtual void set_enabled (int enabled) {}
|
||||
// ask the user for a pathname
|
||||
virtual int ask_filename (char *filename, int maxlen, char *prompt, char *the_default, int flags) {return -1;}
|
||||
// called at a regular interval, currently by the keyboard handler.
|
||||
virtual void periodic () {}
|
||||
};
|
||||
|
||||
extern bx_simulator_interface_c *SIM;
|
||||
|
||||
extern void init_siminterface ();
|
||||
extern void bx_init_siminterface ();
|
||||
extern void bx_init_main ();
|
||||
extern int bx_continue_after_control_panel (int argc, char *argv[]);
|
||||
|
1547
bochs/gui/wx.cc
Normal file
1547
bochs/gui/wx.cc
Normal file
File diff suppressed because it is too large
Load Diff
670
bochs/gui/wxmain.cc
Normal file
670
bochs/gui/wxmain.cc
Normal file
@ -0,0 +1,670 @@
|
||||
//
|
||||
// gui/wxmain.cc
|
||||
// $Id: wxmain.cc,v 1.2 2002-04-18 00:22:19 bdenney Exp $
|
||||
//
|
||||
// wxmain.cc implements the wxWindows frame, toolbar, menus, and dialogs.
|
||||
// When the application starts, the user is given a chance to choose/edit/save
|
||||
// a configuration. When they decide to start the simulation, functions in
|
||||
// main.cc are called in a separate thread to initialize and run the Bochs
|
||||
// simulator.
|
||||
//
|
||||
// The wxWindows port of the VGA display is implemented in wx.cc. The
|
||||
// separation between wxmain.cc and wx.cc is as follows:
|
||||
// - wxmain.cc implements a Bochs configuration interface, which is
|
||||
// the wxWindows equivalent of control.cc. wxmain creates a
|
||||
// frame with several menus and a toolbar, and allows the user to
|
||||
// choose the machine configuration and start the simulation.
|
||||
// - wx.cc implements a VGA display screen using wxWindows. It is
|
||||
// is the wxWindows equivalent of x.cc, win32.cc, macos.cc, etc.
|
||||
// wx.cc includes bochs.h and has access to all Bochs devices.
|
||||
// The VGA panel accepts only paint, key, and mouse events. As it
|
||||
// receives events, it builds BxEvents and places them into a
|
||||
// thread-safe BxEvent queue. The simulation thread periodically
|
||||
// processes events from the BxEvent queue (bx_gui_c::handle_events)
|
||||
// and notifies the appropriate emulated I/O device.
|
||||
//
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// includes
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
// For compilers that support precompilation, includes "wx/wx.h".
|
||||
#include "wx/wxprec.h"
|
||||
#ifdef __BORLANDC__
|
||||
#pragma hdrstop
|
||||
#endif
|
||||
#ifndef WX_PRECOMP
|
||||
#include "wx/wx.h"
|
||||
#endif
|
||||
#include "wx/image.h"
|
||||
|
||||
#include "config.h" // definitions based on configure script
|
||||
#include "osdep.h" // workarounds for missing stuff
|
||||
#include "gui/siminterface.h" // interface to the simulator
|
||||
#include "bxversion.h" // get version string
|
||||
#include "wxmain.h" // interface to the gui
|
||||
|
||||
// include XPM icons
|
||||
#include "bitmaps/cdromd.xpm"
|
||||
#include "bitmaps/copy.xpm"
|
||||
#include "bitmaps/floppya.xpm"
|
||||
#include "bitmaps/floppyb.xpm"
|
||||
#include "bitmaps/paste.xpm"
|
||||
#include "bitmaps/power.xpm"
|
||||
#include "bitmaps/reset.xpm"
|
||||
#include "bitmaps/snapshot.xpm"
|
||||
#include "bitmaps/mouse.xpm"
|
||||
#include "bitmaps/configbutton.xpm"
|
||||
|
||||
// FIXME: ugly global variables that the bx_gui_c object in wx.cc can use
|
||||
// to access the MyFrame and the MyPanel.
|
||||
MyFrame *theFrame = NULL;
|
||||
MyPanel *thePanel = NULL;
|
||||
|
||||
enum
|
||||
{
|
||||
ID_Quit = 1,
|
||||
ID_Config_New,
|
||||
ID_Config_Read,
|
||||
ID_Config_Save,
|
||||
ID_Edit_Disks,
|
||||
ID_Edit_Boot,
|
||||
ID_Edit_Vga,
|
||||
ID_Edit_Memory,
|
||||
ID_Edit_Sound,
|
||||
ID_Edit_Network,
|
||||
ID_Edit_Keyboard,
|
||||
ID_Edit_Other,
|
||||
ID_Simulate_Start,
|
||||
ID_Simulate_PauseResume,
|
||||
ID_Simulate_Stop,
|
||||
ID_Simulate_Speed,
|
||||
ID_Debug_ShowCpu,
|
||||
ID_Debug_ShowMemory,
|
||||
ID_Log_View,
|
||||
ID_Log_Prefs,
|
||||
ID_Log_PrefsDevice,
|
||||
ID_Help_About,
|
||||
ID_Sim2Gui_Event,
|
||||
// ids for Bochs toolbar
|
||||
ID_Toolbar_FloppyA,
|
||||
ID_Toolbar_FloppyB,
|
||||
ID_Toolbar_CdromD,
|
||||
ID_Toolbar_Reset,
|
||||
ID_Toolbar_Power,
|
||||
ID_Toolbar_Copy,
|
||||
ID_Toolbar_Paste,
|
||||
ID_Toolbar_Snapshot,
|
||||
ID_Toolbar_Config,
|
||||
ID_Toolbar_Mouse_en
|
||||
};
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// class declarations
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
class MyApp: public wxApp
|
||||
{
|
||||
virtual bool OnInit();
|
||||
};
|
||||
|
||||
class SimThread: public wxThread
|
||||
{
|
||||
MyFrame *frame;
|
||||
|
||||
// when the sim thread sends a synchronous event to the GUI thread, the
|
||||
// response is stored in sim2gui_mailbox.
|
||||
// FIXME: this would be cleaner and more reusable if I made a general
|
||||
// thread-safe mailbox class.
|
||||
BxEvent *sim2gui_mailbox;
|
||||
wxCriticalSection sim2gui_mailbox_lock;
|
||||
|
||||
public:
|
||||
SimThread (MyFrame *_frame) { frame = _frame; sim2gui_mailbox = NULL; }
|
||||
virtual ExitCode Entry ();
|
||||
void OnExit ();
|
||||
// called by the siminterface code, with the pointer to the sim thread
|
||||
// in the thisptr arg.
|
||||
static BxEvent *SiminterfaceCallback (void *thisptr, BxEvent *event);
|
||||
BxEvent *SiminterfaceCallback2 (BxEvent *event);
|
||||
// methods to coordinate synchronous response mailbox
|
||||
void ClearSyncResponse ();
|
||||
void SendSyncResponse (BxEvent *);
|
||||
BxEvent *GetSyncResponse ();
|
||||
};
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// MyApp: the wxWindows application
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
IMPLEMENT_APP(MyApp)
|
||||
|
||||
bool MyApp::OnInit()
|
||||
{
|
||||
//wxLog::AddTraceMask (_T("mime"));
|
||||
bx_init_siminterface ();
|
||||
bx_init_main ();
|
||||
MyFrame *frame = new MyFrame( "Bochs x86 Emulator", wxPoint(50,50), wxSize(450,340), wxMINIMIZE_BOX | wxSYSTEM_MENU | wxCAPTION );
|
||||
theFrame = frame; // hack alert
|
||||
frame->Show( TRUE );
|
||||
SetTopWindow( frame );
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// MyFrame: the main frame for the Bochs application
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
BEGIN_EVENT_TABLE(MyFrame, wxFrame)
|
||||
EVT_MENU(ID_Quit, MyFrame::OnQuit)
|
||||
EVT_MENU(ID_Help_About, MyFrame::OnAbout)
|
||||
EVT_MENU(ID_Simulate_Start, MyFrame::OnStartSim)
|
||||
EVT_MENU(ID_Simulate_PauseResume, MyFrame::OnPauseResumeSim)
|
||||
EVT_MENU(ID_Simulate_Stop, MyFrame::OnKillSim)
|
||||
EVT_MENU(ID_Sim2Gui_Event, MyFrame::OnSim2GuiEvent)
|
||||
// toolbar events
|
||||
EVT_TOOL(ID_Toolbar_FloppyA, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_FloppyB, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_CdromD, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_Reset, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_Power, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_Copy, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_Paste, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_Snapshot, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_Config, MyFrame::OnToolbarClick)
|
||||
EVT_TOOL(ID_Toolbar_Mouse_en, MyFrame::OnToolbarClick)
|
||||
END_EVENT_TABLE()
|
||||
|
||||
|
||||
MyFrame::MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size, const long style)
|
||||
: wxFrame((wxFrame *)NULL, -1, title, pos, size, style)
|
||||
{
|
||||
// init variables
|
||||
sim_thread = NULL;
|
||||
start_bochs_times = 0;
|
||||
|
||||
// set up the gui
|
||||
menuConfiguration = new wxMenu;
|
||||
menuConfiguration->Append( ID_Config_New, "&New Configuration" );
|
||||
menuConfiguration->Append( ID_Config_Read, "&Read Configuration" );
|
||||
menuConfiguration->Append( ID_Config_Save, "&Save Configuration" );
|
||||
menuConfiguration->AppendSeparator ();
|
||||
menuConfiguration->Append (ID_Quit, "&Quit");
|
||||
|
||||
menuEdit = new wxMenu;
|
||||
menuEdit->Append( ID_Edit_Disks, "&Disks..." );
|
||||
menuEdit->Append( ID_Edit_Boot, "&Boot..." );
|
||||
menuEdit->Append( ID_Edit_Vga, "&VGA..." );
|
||||
menuEdit->Append( ID_Edit_Memory, "&Memory..." );
|
||||
menuEdit->Append( ID_Edit_Sound, "&Sound..." );
|
||||
menuEdit->Append( ID_Edit_Network, "&Network..." );
|
||||
menuEdit->Append( ID_Edit_Keyboard, "&Keyboard..." );
|
||||
menuEdit->Append( ID_Edit_Other, "&Other..." );
|
||||
|
||||
menuSimulate = new wxMenu;
|
||||
menuSimulate->Append( ID_Simulate_Start, "&Start...");
|
||||
menuSimulate->Append( ID_Simulate_PauseResume, "&Pause...");
|
||||
menuSimulate->Append( ID_Simulate_Stop, "S&top...");
|
||||
menuSimulate->AppendSeparator ();
|
||||
menuSimulate->Append( ID_Simulate_Speed, "S&peed...");
|
||||
menuSimulate->Enable (ID_Simulate_PauseResume, FALSE);
|
||||
menuSimulate->Enable (ID_Simulate_Stop, FALSE);
|
||||
|
||||
menuDebug = new wxMenu;
|
||||
menuDebug->Append (ID_Debug_ShowCpu, "Show &CPU");
|
||||
menuDebug->Append (ID_Debug_ShowMemory, "Show &memory");
|
||||
|
||||
menuLog = new wxMenu;
|
||||
menuLog->Append (ID_Log_View, "&View");
|
||||
menuLog->Append (ID_Log_Prefs, "&Preferences...");
|
||||
menuLog->Append (ID_Log_PrefsDevice, "By &Device...");
|
||||
|
||||
menuHelp = new wxMenu;
|
||||
menuHelp->Append( ID_Help_About, "&About..." );
|
||||
|
||||
wxMenuBar *menuBar = new wxMenuBar;
|
||||
menuBar->Append( menuConfiguration, "&File" );
|
||||
menuBar->Append( menuEdit, "&Edit" );
|
||||
menuBar->Append( menuSimulate, "&Simulate" );
|
||||
menuBar->Append( menuDebug, "&Debug" );
|
||||
menuBar->Append( menuLog, "&Log" );
|
||||
menuBar->Append( menuHelp, "&Help" );
|
||||
SetMenuBar( menuBar );
|
||||
CreateStatusBar();
|
||||
SetStatusText( "Welcome to wxWindows!" );
|
||||
|
||||
CreateToolBar(wxNO_BORDER|wxHORIZONTAL|wxTB_FLAT);
|
||||
wxToolBar *tb = GetToolBar();
|
||||
tb->SetToolBitmapSize(wxSize(16, 16));
|
||||
|
||||
int currentX = 5;
|
||||
#define BX_ADD_TOOL(id, xpm_name, tooltip) \
|
||||
do {tb->AddTool(id, wxBitmap(xpm_name), wxNullBitmap, FALSE, currentX, -1, (wxObject *)NULL, tooltip); currentX += 34; } while (0)
|
||||
|
||||
BX_ADD_TOOL(ID_Toolbar_FloppyA, floppya_xpm, "Change Floppy A");
|
||||
BX_ADD_TOOL(ID_Toolbar_FloppyB, floppyb_xpm, "Change Floppy B");
|
||||
BX_ADD_TOOL(ID_Toolbar_CdromD, cdromd_xpm, "Change CDROM");
|
||||
BX_ADD_TOOL(ID_Toolbar_Reset, reset_xpm, "Reset the system");
|
||||
BX_ADD_TOOL(ID_Toolbar_Power, power_xpm, "Turn power on/off");
|
||||
|
||||
BX_ADD_TOOL(ID_Toolbar_Copy, copy_xpm, "Copy to clipboard");
|
||||
BX_ADD_TOOL(ID_Toolbar_Paste, paste_xpm, "Paste from clipboard");
|
||||
BX_ADD_TOOL(ID_Toolbar_Snapshot, snapshot_xpm, "Save screen snapshot");
|
||||
BX_ADD_TOOL(ID_Toolbar_Config, configbutton_xpm, "Runtime Configuration");
|
||||
BX_ADD_TOOL(ID_Toolbar_Mouse_en, mouse_xpm, "Mouse Enable/Disable");
|
||||
|
||||
tb->Realize();
|
||||
|
||||
// create a MyPanel that covers the whole frame
|
||||
panel = new MyPanel (this, -1);
|
||||
panel->SetBackgroundColour (wxColour (0,0,0));
|
||||
wxGridSizer *sz = new wxGridSizer (1, 1);
|
||||
sz->Add (panel, 0, wxGROW);
|
||||
SetAutoLayout (TRUE);
|
||||
SetSizer (sz);
|
||||
|
||||
thePanel = panel;
|
||||
}
|
||||
|
||||
void MyFrame::OnQuit(wxCommandEvent& event)
|
||||
{
|
||||
Close( TRUE );
|
||||
OnKillSim (event);
|
||||
#if 0
|
||||
if (SIM)
|
||||
SIM->quit_sim(0); // give bochs a chance to shut down
|
||||
#endif
|
||||
}
|
||||
|
||||
void MyFrame::OnAbout(wxCommandEvent& WXUNUSED(event))
|
||||
{
|
||||
wxString str;
|
||||
str.Printf ("Bochs x86 Emulator version %s (wxWindows port)", VER_STRING);
|
||||
wxMessageBox( str, "About Bochs", wxOK | wxICON_INFORMATION );
|
||||
}
|
||||
|
||||
void MyFrame::OnStartSim(wxCommandEvent& WXUNUSED(event))
|
||||
{
|
||||
wxCriticalSectionLocker lock(sim_thread_lock);
|
||||
if (sim_thread != NULL) {
|
||||
wxMessageBox (
|
||||
"Can't start Bochs simulator, because it is already running",
|
||||
"Already Running", wxOK | wxICON_ERROR);
|
||||
return;
|
||||
}
|
||||
wxLogStatus ("Starting a Bochs simulation");
|
||||
start_bochs_times++;
|
||||
if (start_bochs_times>1) {
|
||||
wxMessageBox (
|
||||
"You have already started the simulator once this session. Due to memory leaks, you may get unstable behavior.",
|
||||
"2nd time warning", wxOK | wxICON_WARNING);
|
||||
}
|
||||
num_events = 0; // clear the queue of events for bochs to handle
|
||||
sim_thread = new SimThread (this);
|
||||
sim_thread->Create ();
|
||||
sim_thread->Run ();
|
||||
wxLogDebug ("Simulator thread has started.");
|
||||
// set up callback for events from simulator thread
|
||||
SIM->set_notify_callback (&SimThread::SiminterfaceCallback, sim_thread);
|
||||
// fix up menu choices
|
||||
menuSimulate->Enable (ID_Simulate_Start, FALSE);
|
||||
menuSimulate->Enable (ID_Simulate_PauseResume, TRUE);
|
||||
menuSimulate->Enable (ID_Simulate_Stop, TRUE);
|
||||
menuSimulate->SetLabel (ID_Simulate_PauseResume, "&Pause");
|
||||
}
|
||||
|
||||
void MyFrame::OnPauseResumeSim(wxCommandEvent& WXUNUSED(event))
|
||||
{
|
||||
wxCriticalSectionLocker lock(sim_thread_lock);
|
||||
if (sim_thread) {
|
||||
if (sim_thread->IsPaused ()) {
|
||||
SetStatusText ("Resuming the Bochs simulation");
|
||||
sim_thread->Resume ();
|
||||
menuSimulate->SetLabel (ID_Simulate_PauseResume, "&Pause");
|
||||
} else {
|
||||
SetStatusText ("Pausing the Bochs simulation");
|
||||
sim_thread->Pause ();
|
||||
menuSimulate->SetLabel (ID_Simulate_PauseResume, "&Resume");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void MyFrame::OnKillSim(wxCommandEvent& WXUNUSED(event))
|
||||
{
|
||||
// DON'T use a critical section here. Delete implicitly calls
|
||||
// OnSimThreadExit, which also tries to lock sim_thread_lock.
|
||||
// If we grab the lock at this level, deadlock results.
|
||||
if (sim_thread) {
|
||||
SetStatusText ("Killing the Bochs simulation");
|
||||
sim_thread->Delete ();
|
||||
menuSimulate->Enable (ID_Simulate_Start, TRUE);
|
||||
menuSimulate->Enable (ID_Simulate_PauseResume, FALSE);
|
||||
menuSimulate->Enable (ID_Simulate_Stop, FALSE);
|
||||
menuSimulate->SetLabel (ID_Simulate_PauseResume, "&Pause");
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
MyFrame::OnSimThreadExit () {
|
||||
wxCriticalSectionLocker lock (sim_thread_lock);
|
||||
sim_thread = NULL;
|
||||
}
|
||||
|
||||
int
|
||||
MyFrame::HandleAskParamString (bx_param_string_c *param)
|
||||
{
|
||||
wxLogDebug ("HandleAskParamString start");
|
||||
bx_param_num_c *opt = param->get_options ();
|
||||
wxASSERT (opt != NULL);
|
||||
int n_opt = opt->get ();
|
||||
char *msg = param->get_ask_format ();
|
||||
if (!msg) msg = param->get_description ();
|
||||
char *newval = NULL;
|
||||
wxDialog *dialog = NULL;
|
||||
if (n_opt & param->BX_IS_FILENAME) {
|
||||
// use file open dialog
|
||||
long style =
|
||||
(n_opt & param->BX_SAVE_FILE_DIALOG) ? wxSAVE|wxOVERWRITE_PROMPT : wxOPEN;
|
||||
wxLogDebug ("HandleAskParamString: create dialog");
|
||||
wxFileDialog *fdialog = new wxFileDialog (this, msg, "", "", "*.*", style);
|
||||
wxLogDebug ("HandleAskParamString: before showmodal");
|
||||
if (fdialog->ShowModal() == wxID_OK)
|
||||
newval = (char *)fdialog->GetPath().c_str ();
|
||||
wxLogDebug ("HandleAskParamString: after showmodal");
|
||||
dialog = fdialog; // so I can delete it
|
||||
} else {
|
||||
// use simple string dialog
|
||||
long style = wxOK|wxCANCEL;
|
||||
wxTextEntryDialog *tdialog = new wxTextEntryDialog (this, msg, "Enter new value", wxString(param->getptr ()), style);
|
||||
if (tdialog->ShowModal() == wxID_OK)
|
||||
newval = (char *)tdialog->GetValue().c_str ();
|
||||
dialog = tdialog; // so I can delete it
|
||||
}
|
||||
// newval points to memory inside the dialg. As soon as dialog is deleted, newval points
|
||||
// to junk. So be sure to copy the text out before deleting it!
|
||||
if (newval && strlen(newval)>0) {
|
||||
// change floppy path to this value.
|
||||
wxLogDebug ("Setting param %s to '%s'", param->get_name (), newval);
|
||||
param->set (newval);
|
||||
delete dialog;
|
||||
return 1;
|
||||
}
|
||||
delete dialog;
|
||||
return -1;
|
||||
}
|
||||
|
||||
// This is called when the simulator needs to ask the user to choose
|
||||
// a value or setting. For example, when the user indicates that he wants
|
||||
// to change the floppy disk image for drive A, an ask-param event is created
|
||||
// with the parameter id set to BXP_FLOPPYA_PATH. The simulator blocks until
|
||||
// the gui has displayed a dialog and received a selection from the user.
|
||||
// In the current implemention, the GUI will look up the parameter's
|
||||
// data structure using SIM->get_param() and then call the set method on the
|
||||
// parameter to change the param. The return value only needs to return
|
||||
// success or failure (failure = cancelled, or not implemented).
|
||||
// Returns 1 if the user chose a value and the param was modified.
|
||||
// Returns 0 if the user cancelled.
|
||||
// Returns -1 if the gui doesn't know how to ask for that param.
|
||||
int
|
||||
MyFrame::HandleAskParam (BxEvent *event)
|
||||
{
|
||||
wxASSERT (event->type == BX_SYNC_EVT_ASK_PARAM);
|
||||
|
||||
bx_param_c *param = event->u.param.param;
|
||||
Raise (); // bring control panel to front so that you will see the dialog
|
||||
switch (param->get_type ())
|
||||
{
|
||||
case BXT_PARAM_STRING:
|
||||
return HandleAskParamString ((bx_param_string_c *)param);
|
||||
default:
|
||||
{
|
||||
wxString msg;
|
||||
msg.Printf ("ask param for parameter type %d is not implemented in wxWindows");
|
||||
wxMessageBox( msg, "not implemented", wxOK | wxICON_ERROR );
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
#if 0
|
||||
switch (param) {
|
||||
case BXP_FLOPPYA_PATH:
|
||||
case BXP_FLOPPYB_PATH:
|
||||
case BXP_DISKC_PATH:
|
||||
case BXP_DISKD_PATH:
|
||||
case BXP_CDROM_PATH:
|
||||
{
|
||||
Raise(); // bring the control panel to front so dialog shows
|
||||
char *msg;
|
||||
if (param==BXP_FLOPPYA_PATH || param==BXP_FLOPPYB_PATH)
|
||||
msg = "Choose new floppy disk image file";
|
||||
else if (param==BXP_DISKC_PATH || param==BXP_DISKD_PATH)
|
||||
msg = "Choose new hard disk image file";
|
||||
else if (param==BXP_CDROM_PATH)
|
||||
msg = "Choose new CDROM image file";
|
||||
else
|
||||
msg = "Choose new image file";
|
||||
wxFileDialog dialog(this, msg, "", "", "*.*", 0);
|
||||
int ret = dialog.ShowModal();
|
||||
if (ret == wxID_OK)
|
||||
{
|
||||
char *newpath = (char *)dialog.GetPath().c_str ();
|
||||
if (newpath && strlen(newpath)>0) {
|
||||
// change floppy path to this value.
|
||||
bx_param_string_c *Opath = SIM->get_param_string (param);
|
||||
assert (Opath != NULL);
|
||||
wxLogDebug ("Setting floppy %c path to '%s'",
|
||||
param == BXP_FLOPPYA_PATH ? 'A' : 'B',
|
||||
newpath);
|
||||
Opath->set (newpath);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
default:
|
||||
wxLogError ("HandleAskParam: parameter %d, not implemented", event->u.param.id);
|
||||
}
|
||||
#endif
|
||||
return -1; // could not display
|
||||
}
|
||||
|
||||
// This is called when a Sim2Gui event is discovered on the GUI thread's
|
||||
// event queue. (It got there via wxPostEvent in SiminterfaceCallback2,
|
||||
// which is executed in the simulator Thread.)
|
||||
void
|
||||
MyFrame::OnSim2GuiEvent (wxCommandEvent& event)
|
||||
{
|
||||
wxLogDebug ("received a bochs event in the GUI thread");
|
||||
BxEvent *be = (BxEvent *) event.GetEventObject ();
|
||||
wxLogDebug ("event type = %d", (int) be->type);
|
||||
// all cases should return. sync event handlers MUST send back a
|
||||
// response.
|
||||
switch (be->type) {
|
||||
case BX_SYNC_EVT_ASK_PARAM:
|
||||
wxLogDebug ("before HandleAskParam");
|
||||
be->retcode = HandleAskParam (be);
|
||||
wxLogDebug ("after HandleAskParam");
|
||||
// sync must return something; just return a copy of the event.
|
||||
sim_thread->SendSyncResponse(be);
|
||||
wxLogDebug ("after SendSyncResponse");
|
||||
return;
|
||||
case BX_ASYNC_EVT_SHUTDOWN_GUI:
|
||||
wxLogDebug ("control panel is exiting");
|
||||
Close (TRUE);
|
||||
wxExit ();
|
||||
return;
|
||||
case BX_ASYNC_EVT_LOG_MSG:
|
||||
wxLogDebug ("log msg: level=%d, prefix='%s', msg='%s'",
|
||||
be->u.logmsg.level,
|
||||
be->u.logmsg.prefix,
|
||||
be->u.logmsg.msg);
|
||||
return;
|
||||
default:
|
||||
wxLogDebug ("OnSim2GuiEvent: event type %d ignored", (int)be->type);
|
||||
// assume it's a synchronous event and send back a response, to avoid
|
||||
// potential deadlock.
|
||||
sim_thread->SendSyncResponse(be);
|
||||
return;
|
||||
}
|
||||
// it is critical to send a response back eventually since the sim thread
|
||||
// is blocking.
|
||||
wxASSERT_MSG (0, "switch stmt should have returned");
|
||||
}
|
||||
|
||||
void MyFrame::OnToolbarClick(wxCommandEvent& event)
|
||||
{
|
||||
wxLogDebug ("clicked toolbar thingy");
|
||||
bx_toolbar_buttons which = BX_TOOLBAR_UNDEFINED;
|
||||
int id = event.GetId ();
|
||||
switch (id) {
|
||||
case ID_Toolbar_Power:which = BX_TOOLBAR_POWER; break;
|
||||
case ID_Toolbar_Reset: which = BX_TOOLBAR_RESET; break;
|
||||
case ID_Toolbar_FloppyA: which = BX_TOOLBAR_FLOPPYA; break;
|
||||
case ID_Toolbar_FloppyB: which = BX_TOOLBAR_FLOPPYB; break;
|
||||
case ID_Toolbar_CdromD: which = BX_TOOLBAR_CDROMD; break;
|
||||
case ID_Toolbar_Copy: which = BX_TOOLBAR_COPY; break;
|
||||
case ID_Toolbar_Paste: which = BX_TOOLBAR_PASTE; break;
|
||||
case ID_Toolbar_Snapshot: which = BX_TOOLBAR_SNAPSHOT; break;
|
||||
case ID_Toolbar_Config: which = BX_TOOLBAR_CONFIG; break;
|
||||
case ID_Toolbar_Mouse_en: which = BX_TOOLBAR_MOUSE_EN; break;
|
||||
default:
|
||||
wxLogError ("unknown toolbar id %d", id);
|
||||
}
|
||||
if (num_events < MAX_EVENTS) {
|
||||
event_queue[num_events].type = BX_ASYNC_EVT_TOOLBAR;
|
||||
event_queue[num_events].u.toolbar.button = which;
|
||||
num_events++;
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// Simulation Thread
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
||||
void *
|
||||
SimThread::Entry (void)
|
||||
{
|
||||
int argc=1;
|
||||
char *argv[] = {"bochs"};
|
||||
wxLogDebug ("in SimThread, starting at bx_continue_after_control_panel");
|
||||
// run all the rest of the Bochs simulator code. This function will
|
||||
// run forever, unless a "kill_bochs_request" is issued. The procedure
|
||||
// is as follows:
|
||||
// - user selects "Kill Simulation" or GUI decides to kill bochs
|
||||
// - GUI calls sim_thread->Delete ()
|
||||
// - sim continues to run until the next time it reaches SIM->periodic().
|
||||
// - SIM->periodic() sends a synchronous tick event to the GUI, which
|
||||
// finally calls TestDestroy() and realizes it needs to stop. It
|
||||
// sets the sync event return code to -1. SIM->periodic() sets the
|
||||
// kill_bochs_request flag in cpu #0.
|
||||
// - cpu loop notices kill_bochs_request and returns to main.cc:
|
||||
// bx_continue_after_control_panel(), which notices the
|
||||
// kill_bochs_request and returns back to this Entry() function.
|
||||
// - Entry() exits and the thread stops. Whew.
|
||||
bx_continue_after_control_panel (argc, argv);
|
||||
wxLogDebug ("in SimThread, bx_continue_after_control_panel exited");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void
|
||||
SimThread::OnExit ()
|
||||
{
|
||||
// notify the MyFrame that the bochs thread has died. I can't adjust
|
||||
// the sim_thread directly because it's private.
|
||||
frame->OnSimThreadExit ();
|
||||
// don't use this SimThread's callback function anymore.
|
||||
SIM->set_notify_callback (NULL, NULL);
|
||||
}
|
||||
|
||||
// This function is declared static so that I can get a usable function
|
||||
// pointer for it. The function pointer is passed to SIM->set_notify_callback
|
||||
// so that the siminterface can call this function when it needs to contact
|
||||
// the gui. It will always be called with a pointer to the SimThread
|
||||
// as the first argument.
|
||||
BxEvent *
|
||||
SimThread::SiminterfaceCallback (void *thisptr, BxEvent *event)
|
||||
{
|
||||
SimThread *me = (SimThread *)thisptr;
|
||||
// call the normal non-static method now that we know the this pointer.
|
||||
return me->SiminterfaceCallback2 (event);
|
||||
}
|
||||
|
||||
// callback function for sim thread events. This is called from
|
||||
// the sim thread, not the GUI thread. So any GUI actions must be
|
||||
// thread safe. Most events are handled by packaging up the event
|
||||
// in a wxEvent of some kind, and posting it to the GUI thread for
|
||||
// processing.
|
||||
BxEvent *
|
||||
SimThread::SiminterfaceCallback2 (BxEvent *event)
|
||||
{
|
||||
//wxLogDebug ("SiminterfaceCallback with event type=%d", (int)event->type);
|
||||
event->retcode = 0; // default return code
|
||||
int async = BX_EVT_IS_ASYNC(event->type);
|
||||
if (!async) {
|
||||
// for synchronous events, clear away any previous response. There
|
||||
// can only be one synchronous event pending at a time.
|
||||
ClearSyncResponse ();
|
||||
event->retcode = -1; // default to error
|
||||
}
|
||||
|
||||
// tick event must be handled right here in the bochs thread.
|
||||
if (event->type == BX_SYNC_EVT_TICK) {
|
||||
if (TestDestroy ()) {
|
||||
// tell simulator to quit
|
||||
event->retcode = -1;
|
||||
} else {
|
||||
event->retcode = 0;
|
||||
}
|
||||
return event;
|
||||
}
|
||||
|
||||
//encapsulate the bxevent in a wxwindows event
|
||||
wxCommandEvent wxevent (wxEVT_COMMAND_MENU_SELECTED, ID_Sim2Gui_Event);
|
||||
wxevent.SetEventObject ((wxEvent *)event);
|
||||
wxLogDebug ("Sending an event to the window");
|
||||
wxPostEvent (frame, wxevent);
|
||||
// if it is an asynchronous event, return immediately
|
||||
if (async) return NULL;
|
||||
wxLogDebug ("SiminterfaceCallback2: synchronous event; waiting for response");
|
||||
// now wait forever for the GUI to post a response.
|
||||
BxEvent *response = NULL;
|
||||
while (response == NULL) {
|
||||
response = GetSyncResponse ();
|
||||
if (!response) {
|
||||
wxLogDebug ("no sync response yet, waiting");
|
||||
this->Sleep(500);
|
||||
}
|
||||
}
|
||||
wxASSERT (response != NULL);
|
||||
return response;
|
||||
}
|
||||
|
||||
void
|
||||
SimThread::ClearSyncResponse ()
|
||||
{
|
||||
wxCriticalSectionLocker lock(sim2gui_mailbox_lock);
|
||||
if (sim2gui_mailbox != NULL) {
|
||||
wxLogDebug ("WARNING: ClearSyncResponse is throwing away an event that was previously in the mailbox");
|
||||
}
|
||||
sim2gui_mailbox = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
SimThread::SendSyncResponse (BxEvent *event)
|
||||
{
|
||||
wxCriticalSectionLocker lock(sim2gui_mailbox_lock);
|
||||
if (sim2gui_mailbox != NULL) {
|
||||
wxLogDebug ("WARNING: SendSyncResponse is throwing away an event that was previously in the mailbox");
|
||||
}
|
||||
sim2gui_mailbox = event;
|
||||
}
|
||||
|
||||
BxEvent *
|
||||
SimThread::GetSyncResponse ()
|
||||
{
|
||||
wxCriticalSectionLocker lock(sim2gui_mailbox_lock);
|
||||
BxEvent *event = sim2gui_mailbox;
|
||||
sim2gui_mailbox = NULL;
|
||||
return event;
|
||||
}
|
||||
|
76
bochs/gui/wxmain.h
Normal file
76
bochs/gui/wxmain.h
Normal file
@ -0,0 +1,76 @@
|
||||
// this file should be included only by wx.cc and wxmain.cc.
|
||||
|
||||
// forward class declaration so that each class can have a pointer to
|
||||
// the others.
|
||||
class MyFrame;
|
||||
class MyPanel;
|
||||
class SimThread;
|
||||
|
||||
//hack alert; yuck; FIXME
|
||||
extern MyFrame *theFrame;
|
||||
extern MyPanel *thePanel;
|
||||
|
||||
#define MAX_EVENTS 256
|
||||
extern unsigned long num_events;
|
||||
extern BxEvent event_queue[MAX_EVENTS];
|
||||
|
||||
// to show debug messages, change these defines to x. To hide them,
|
||||
// change the defines to return nothing.
|
||||
#define IFDBG_VGA(x) /* nothing */
|
||||
//#define IFDBG_VGA(x) x
|
||||
|
||||
#define IFDBG_KEY(x) /* nothing */
|
||||
//#define IFDBG_KEY(x) x
|
||||
|
||||
|
||||
/// the MyPanel methods are defined in wx.cc
|
||||
class MyPanel: public wxPanel
|
||||
{
|
||||
Boolean fillBxKeyEvent (wxKeyEvent& event, BxKeyEvent& bxev, Boolean release); // for all platforms
|
||||
Boolean fillBxKeyEvent_MSW (wxKeyEvent& event, BxKeyEvent& bxev, Boolean release);
|
||||
Boolean fillBxKeyEvent_GTK (wxKeyEvent& event, BxKeyEvent& bxev, Boolean release);
|
||||
public:
|
||||
MyPanel(wxWindow* parent, wxWindowID id, const wxPoint& pos = wxDefaultPosition, const wxSize& size = wxDefaultSize, long style = wxTAB_TRAVERSAL, const wxString& name = "panel")
|
||||
: wxPanel (parent, id, pos, size, style, name)
|
||||
{ wxLogDebug ("MyPanel constructor"); }
|
||||
void OnKeyDown(wxKeyEvent& event);
|
||||
void OnKeyUp(wxKeyEvent& event);
|
||||
void OnPaint(wxPaintEvent& event);
|
||||
void MyRefresh ();
|
||||
private:
|
||||
DECLARE_EVENT_TABLE()
|
||||
};
|
||||
|
||||
/// the MyFrame methods are defined in wxmain.cc
|
||||
class MyFrame: public wxFrame
|
||||
{
|
||||
MyPanel *panel;
|
||||
public:
|
||||
MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size, const long style);
|
||||
void OnQuit(wxCommandEvent& event);
|
||||
void OnAbout(wxCommandEvent& event);
|
||||
void OnStartSim(wxCommandEvent& event);
|
||||
void OnPauseResumeSim(wxCommandEvent& event);
|
||||
void OnKillSim(wxCommandEvent& event);
|
||||
void OnSim2GuiEvent(wxCommandEvent& event);
|
||||
void OnToolbarClick(wxCommandEvent& event);
|
||||
int HandleAskParam (BxEvent *event);
|
||||
int HandleAskParamString (bx_param_string_c *param);
|
||||
|
||||
// called from the sim thread's OnExit() method.
|
||||
void OnSimThreadExit ();
|
||||
|
||||
private:
|
||||
wxCriticalSection sim_thread_lock;
|
||||
SimThread *sim_thread; // get the lock before accessing sim_thread
|
||||
int start_bochs_times;
|
||||
wxMenu *menuConfiguration;
|
||||
wxMenu *menuEdit;
|
||||
wxMenu *menuSimulate;
|
||||
wxMenu *menuDebug;
|
||||
wxMenu *menuLog;
|
||||
wxMenu *menuHelp;
|
||||
|
||||
DECLARE_EVENT_TABLE()
|
||||
};
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: x.cc,v 1.40 2002-04-05 12:10:50 cbothamy Exp $
|
||||
// $Id: x.cc,v 1.41 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2002 MandrakeSoft S.A.
|
||||
@ -1337,6 +1337,7 @@ headerbar_click(int x, int y)
|
||||
void
|
||||
bx_gui_c::exit(void)
|
||||
{
|
||||
XCloseDisplay (bx_x_display);
|
||||
BX_INFO(("Exit."));
|
||||
}
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: cdrom.cc,v 1.31 2002-04-10 05:38:34 bdenney Exp $
|
||||
// $Id: cdrom.cc,v 1.32 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2002 MandrakeSoft S.A.
|
||||
@ -203,7 +203,7 @@ cdrom_interface::cdrom_interface(char *dev)
|
||||
|
||||
void
|
||||
cdrom_interface::init(void) {
|
||||
BX_DEBUG(("Init $Id: cdrom.cc,v 1.31 2002-04-10 05:38:34 bdenney Exp $"));
|
||||
BX_DEBUG(("Init $Id: cdrom.cc,v 1.32 2002-04-18 00:22:19 bdenney Exp $"));
|
||||
BX_INFO(("file = '%s'",path));
|
||||
}
|
||||
|
||||
@ -250,7 +250,7 @@ cdrom_interface::insert_cdrom(char *dev)
|
||||
{
|
||||
strcpy(drive,path);
|
||||
using_file = 1;
|
||||
bUseASPI = FALSE;
|
||||
bUseASPI = FALSE;
|
||||
BX_INFO (("Opening image file as a cd"));
|
||||
}
|
||||
if(bUseASPI) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: keyboard.cc,v 1.54 2002-04-11 00:28:55 instinc Exp $
|
||||
// $Id: keyboard.cc,v 1.55 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2002 MandrakeSoft S.A.
|
||||
@ -70,7 +70,7 @@ bx_keyb_c::bx_keyb_c(void)
|
||||
memset( &s, 0, sizeof(s) );
|
||||
BX_KEY_THIS put("KBD");
|
||||
BX_KEY_THIS settype(KBDLOG);
|
||||
BX_DEBUG(("Init $Id: keyboard.cc,v 1.54 2002-04-11 00:28:55 instinc Exp $"));
|
||||
BX_DEBUG(("Init $Id: keyboard.cc,v 1.55 2002-04-18 00:22:19 bdenney Exp $"));
|
||||
}
|
||||
|
||||
bx_keyb_c::~bx_keyb_c(void)
|
||||
@ -110,7 +110,7 @@ bx_keyb_c::resetinternals(Boolean powerup)
|
||||
void
|
||||
bx_keyb_c::init(bx_devices_c *d, bx_cmos_c *cmos)
|
||||
{
|
||||
BX_DEBUG(("Init $Id: keyboard.cc,v 1.54 2002-04-11 00:28:55 instinc Exp $"));
|
||||
BX_DEBUG(("Init $Id: keyboard.cc,v 1.55 2002-04-18 00:22:19 bdenney Exp $"));
|
||||
Bit32u i;
|
||||
|
||||
BX_KEY_THIS devices = d;
|
||||
@ -1099,6 +1099,8 @@ bx_keyb_c::periodic( Bit32u usec_delta )
|
||||
if ( ++multiple==10)
|
||||
{
|
||||
multiple=0;
|
||||
SIM->periodic ();
|
||||
if (BX_CPU_THIS_PTR kill_bochs_request) return 0;
|
||||
bx_gui.handle_events();
|
||||
}
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: load32bitOShack.cc,v 1.7 2001-10-03 13:10:37 bdenney Exp $
|
||||
// $Id: load32bitOShack.cc,v 1.8 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
@ -268,12 +268,12 @@ bx_load_kernel_image(char *path, Bit32u paddr)
|
||||
);
|
||||
if (fd < 0) {
|
||||
BX_INFO(( "load_kernel_image: couldn't open image file '%s'.", path ));
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
ret = fstat(fd, &stat_buf);
|
||||
if (ret) {
|
||||
BX_INFO(( "load_kernel_image: couldn't stat image file '%s'.", path ));
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
|
||||
size = stat_buf.st_size;
|
||||
@ -282,7 +282,7 @@ bx_load_kernel_image(char *path, Bit32u paddr)
|
||||
BX_MEM_C *mem = BX_MEM(0);
|
||||
if ( (paddr + size) > mem->len ) {
|
||||
BX_INFO(( "load_kernel_image: address range > physical memsize!" ));
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
|
||||
offset = 0;
|
||||
@ -290,7 +290,7 @@ bx_load_kernel_image(char *path, Bit32u paddr)
|
||||
ret = read(fd, (bx_ptr_t) &mem->vector[paddr + offset], size);
|
||||
if (ret <= 0) {
|
||||
BX_INFO(( "load_kernel_image: read failed on image" ));
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
size -= ret;
|
||||
offset += ret;
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: logio.cc,v 1.16 2002-01-07 16:10:11 bdenney Exp $
|
||||
// $Id: logio.cc,v 1.17 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
@ -363,7 +363,7 @@ logfunctions::ask (int level, const char *prefix, const char *fmt, va_list ap)
|
||||
vsprintf (buf1, fmt, ap);
|
||||
sprintf (buf2, "%s %s", prefix, buf1);
|
||||
// FIXME: facility set to 0 because it's unknown.
|
||||
int val = SIM->LOCAL_log_msg (prefix, level, buf2);
|
||||
int val = SIM->log_msg (prefix, level, buf2);
|
||||
switch (val)
|
||||
{
|
||||
case 0: // user chose continue
|
||||
@ -398,7 +398,7 @@ logfunctions::ask (int level, const char *prefix, const char *fmt, va_list ap)
|
||||
default:
|
||||
// this happens if panics happen before the callback is initialized
|
||||
// in gui/control.cc.
|
||||
fprintf (stderr, "WARNING: LOCAL_log_msg returned unexpected value %d\n", val);
|
||||
fprintf (stderr, "WARNING: log_msg returned unexpected value %d\n", val);
|
||||
}
|
||||
}
|
||||
|
||||
@ -424,7 +424,7 @@ logfunctions::fatal (const char *prefix, const char *fmt, va_list ap)
|
||||
fgets (buf, 8, stdin);
|
||||
#endif
|
||||
#if !BX_DEBUGGER
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
#else
|
||||
static Boolean dbg_exit_called = 0;
|
||||
if (dbg_exit_called == 0) {
|
||||
|
134
bochs/main.cc
134
bochs/main.cc
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: main.cc,v 1.96 2002-03-29 23:37:07 instinc Exp $
|
||||
// $Id: main.cc,v 1.97 2002-04-18 00:22:19 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
@ -109,6 +109,7 @@ bx_options_t bx_options = {
|
||||
static void parse_line_unformatted(char *context, char *line);
|
||||
static void parse_line_formatted(char *context, int num_params, char *params[]);
|
||||
static int parse_bochsrc(char *rcfile);
|
||||
static void bx_do_text_config_interface (int argc, char *argv[]);
|
||||
|
||||
static Bit32s
|
||||
bx_param_handler (bx_param_c *param, int set, Bit32s val)
|
||||
@ -319,11 +320,15 @@ void bx_init_options ()
|
||||
bx_list_c *menu;
|
||||
|
||||
// floppya
|
||||
bx_options.floppya.Opath = new bx_param_string_c (BXP_FLOPPYA_PATH,
|
||||
bx_options.floppya.Opath = new bx_param_filename_c (BXP_FLOPPYA_PATH,
|
||||
"Floppy A image",
|
||||
"Pathname of first floppy image file or device. If you're booting from floppy, this should be a bootable floppy.",
|
||||
"", BX_PATHNAME_LEN);
|
||||
#if BX_WITH_WX
|
||||
bx_options.floppya.Opath->set_ask_format ("Filename of first floppy image");
|
||||
#else
|
||||
bx_options.floppya.Opath->set_ask_format ("Enter new filename, or 'none' for no disk: [%s] ");
|
||||
#endif
|
||||
bx_options.floppya.Otype = new bx_param_enum_c (BXP_FLOPPYA_TYPE,
|
||||
"floppya:type",
|
||||
"Type of floppy disk",
|
||||
@ -353,11 +358,15 @@ void bx_init_options ()
|
||||
bx_options.floppya.Opath->set ("none");
|
||||
bx_options.floppya.Oinitial_status->set_handler (bx_param_handler);
|
||||
|
||||
bx_options.floppyb.Opath = new bx_param_string_c (BXP_FLOPPYB_PATH,
|
||||
bx_options.floppyb.Opath = new bx_param_filename_c (BXP_FLOPPYB_PATH,
|
||||
"floppyb:path",
|
||||
"Pathname of second floppy image file or device.",
|
||||
"", BX_PATHNAME_LEN);
|
||||
#if BX_WITH_WX
|
||||
bx_options.floppyb.Opath->set_ask_format ("Filename of second floppy image");
|
||||
#else
|
||||
bx_options.floppyb.Opath->set_ask_format ("Enter new filename, or 'none' for no disk: [%s] ");
|
||||
#endif
|
||||
bx_options.floppyb.Otype = new bx_param_enum_c (BXP_FLOPPYB_TYPE,
|
||||
"floppyb:type",
|
||||
"Type of floppy disk",
|
||||
@ -393,7 +402,7 @@ void bx_init_options ()
|
||||
"diskc:present",
|
||||
"Controls whether diskc is installed or not",
|
||||
0);
|
||||
bx_options.diskc.Opath = new bx_param_string_c (BXP_DISKC_PATH,
|
||||
bx_options.diskc.Opath = new bx_param_filename_c (BXP_DISKC_PATH,
|
||||
"",
|
||||
"Pathname of the hard drive image",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -439,7 +448,7 @@ void bx_init_options ()
|
||||
"diskd:present",
|
||||
"Controls whether diskd is installed or not",
|
||||
0);
|
||||
bx_options.diskd.Opath = new bx_param_string_c (BXP_DISKD_PATH,
|
||||
bx_options.diskd.Opath = new bx_param_filename_c (BXP_DISKD_PATH,
|
||||
"diskd:path",
|
||||
"Pathname of the hard drive image",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -484,7 +493,7 @@ void bx_init_options ()
|
||||
"",
|
||||
0);
|
||||
|
||||
bx_options.com1.Odev = new bx_param_string_c (BXP_COM1_PATH,
|
||||
bx_options.com1.Odev = new bx_param_filename_c (BXP_COM1_PATH,
|
||||
"Pathname of the serial device for COM1",
|
||||
"",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -496,7 +505,7 @@ void bx_init_options ()
|
||||
"Controls whether com2 is installed or not",
|
||||
0);
|
||||
|
||||
bx_options.com2.Odev = new bx_param_string_c (BXP_COM2_PATH,
|
||||
bx_options.com2.Odev = new bx_param_filename_c (BXP_COM2_PATH,
|
||||
"",
|
||||
"",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -507,7 +516,7 @@ void bx_init_options ()
|
||||
"",
|
||||
0);
|
||||
|
||||
bx_options.com3.Odev = new bx_param_string_c (BXP_COM3_PATH,
|
||||
bx_options.com3.Odev = new bx_param_filename_c (BXP_COM3_PATH,
|
||||
"Pathname of the serial device for COM3",
|
||||
"",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -518,7 +527,7 @@ void bx_init_options ()
|
||||
"",
|
||||
0);
|
||||
|
||||
bx_options.com4.Odev = new bx_param_string_c (BXP_COM4_PATH,
|
||||
bx_options.com4.Odev = new bx_param_filename_c (BXP_COM4_PATH,
|
||||
"Pathname of the serial device for COM4",
|
||||
"",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -530,12 +539,14 @@ void bx_init_options ()
|
||||
"CDROM is present",
|
||||
"Controls whether cdromd is installed or not",
|
||||
0);
|
||||
bx_options.cdromd.Opath = new bx_param_string_c (BXP_CDROM_PATH,
|
||||
bx_options.cdromd.Opath = new bx_param_filename_c (BXP_CDROM_PATH,
|
||||
"CDROM image filename",
|
||||
"Pathname of the cdrom device or image",
|
||||
"", BX_PATHNAME_LEN);
|
||||
bx_options.cdromd.Opath->set_format ("%s");
|
||||
#if BX_UI_TEXT
|
||||
bx_options.cdromd.Opath->set_ask_format ("Enter new filename, or 'none' for no CDROM: [%s] ");
|
||||
#endif
|
||||
bx_options.cdromd.Oinserted = new bx_param_enum_c (BXP_CDROM_INSERTED,
|
||||
"Is the CDROM inserted or ejected",
|
||||
"Inserted or ejected",
|
||||
@ -596,7 +607,7 @@ void bx_init_options ()
|
||||
"Enables the first parallel port",
|
||||
0);
|
||||
bx_options.par1.Oenable->set_handler (bx_param_handler);
|
||||
bx_options.par1.Ooutfile = new bx_param_string_c (BXP_PARPORT1_OUTFILE,
|
||||
bx_options.par1.Ooutfile = new bx_param_filename_c (BXP_PARPORT1_OUTFILE,
|
||||
"Parallel port #1 output file",
|
||||
"Data written to parport#1 by the guest OS is written to this file",
|
||||
"parport.out", BX_PATHNAME_LEN);
|
||||
@ -606,7 +617,7 @@ void bx_init_options ()
|
||||
"Enables the second parallel port",
|
||||
0);
|
||||
bx_options.par2.Oenable->set_handler (bx_param_handler);
|
||||
bx_options.par2.Ooutfile = new bx_param_string_c (BXP_PARPORT2_OUTFILE,
|
||||
bx_options.par2.Ooutfile = new bx_param_filename_c (BXP_PARPORT2_OUTFILE,
|
||||
"Parallel port #2 output file",
|
||||
"Data written to parport#2 by the guest OS is written to this file",
|
||||
"parport2.out", BX_PATHNAME_LEN);
|
||||
@ -629,7 +640,7 @@ void bx_init_options ()
|
||||
menu = new bx_list_c (BXP_MENU_SERIAL_PARALLEL, "Serial and Parallel Port Options", "serial_parallel_menu", parport_init_list);
|
||||
menu->get_options ()->set (menu->BX_SHOW_PARENT);
|
||||
|
||||
bx_options.rom.Opath = new bx_param_string_c (BXP_ROM_PATH,
|
||||
bx_options.rom.Opath = new bx_param_filename_c (BXP_ROM_PATH,
|
||||
"romimage",
|
||||
"Pathname of ROM image to load",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -641,7 +652,7 @@ void bx_init_options ()
|
||||
0);
|
||||
bx_options.rom.Oaddress->set_format ("ROM BIOS address: 0x%05x");
|
||||
bx_options.rom.Oaddress->set_base (16);
|
||||
bx_options.vgarom.Opath = new bx_param_string_c (BXP_VGA_ROM_PATH,
|
||||
bx_options.vgarom.Opath = new bx_param_filename_c (BXP_VGA_ROM_PATH,
|
||||
"vgaromimage",
|
||||
"Pathname of VGA ROM image to load",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -752,15 +763,15 @@ void bx_init_options ()
|
||||
"SB16 is present",
|
||||
"to be written",
|
||||
0);
|
||||
bx_options.sb16.Omidifile = new bx_param_string_c (BXP_SB16_MIDIFILE,
|
||||
bx_options.sb16.Omidifile = new bx_param_filename_c (BXP_SB16_MIDIFILE,
|
||||
"Midi file",
|
||||
"to be written",
|
||||
"", BX_PATHNAME_LEN);
|
||||
bx_options.sb16.Owavefile = new bx_param_string_c (BXP_SB16_WAVEFILE,
|
||||
bx_options.sb16.Owavefile = new bx_param_filename_c (BXP_SB16_WAVEFILE,
|
||||
"Wave file",
|
||||
"to be written",
|
||||
"", BX_PATHNAME_LEN);
|
||||
bx_options.sb16.Ologfile = new bx_param_string_c (BXP_SB16_LOGFILE,
|
||||
bx_options.sb16.Ologfile = new bx_param_filename_c (BXP_SB16_LOGFILE,
|
||||
"Log file",
|
||||
"to be written",
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -800,7 +811,7 @@ void bx_init_options ()
|
||||
bx_options.sb16.Opresent->set_handler (bx_param_handler);
|
||||
bx_options.sb16.Opresent->set (0);
|
||||
|
||||
bx_options.log.Ofilename = new bx_param_string_c (BXP_LOG_FILENAME,
|
||||
bx_options.log.Ofilename = new bx_param_filename_c (BXP_LOG_FILENAME,
|
||||
"log:filename",
|
||||
"Pathname of bochs log file",
|
||||
"-", BX_PATHNAME_LEN);
|
||||
@ -813,15 +824,15 @@ void bx_init_options ()
|
||||
loader_os_names,
|
||||
Load32bitOSNone,
|
||||
Load32bitOSNone);
|
||||
bx_options.load32bitOSImage.Opath = new bx_param_string_c (BXP_LOAD32BITOS_PATH,
|
||||
bx_options.load32bitOSImage.Opath = new bx_param_filename_c (BXP_LOAD32BITOS_PATH,
|
||||
"Pathname of OS to load",
|
||||
NULL,
|
||||
"", BX_PATHNAME_LEN);
|
||||
bx_options.load32bitOSImage.Oiolog = new bx_param_string_c (BXP_LOAD32BITOS_IOLOG,
|
||||
bx_options.load32bitOSImage.Oiolog = new bx_param_filename_c (BXP_LOAD32BITOS_IOLOG,
|
||||
"Pathname of I/O log file",
|
||||
NULL,
|
||||
"", BX_PATHNAME_LEN);
|
||||
bx_options.load32bitOSImage.Oinitrd = new bx_param_string_c (BXP_LOAD32BITOS_INITRD,
|
||||
bx_options.load32bitOSImage.Oinitrd = new bx_param_filename_c (BXP_LOAD32BITOS_INITRD,
|
||||
"Pathname of initrd",
|
||||
NULL,
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -870,7 +881,7 @@ void bx_init_options ()
|
||||
"Use a CMOS image",
|
||||
NULL,
|
||||
0);
|
||||
bx_options.cmos.Opath = new bx_param_string_c (BXP_CMOS_PATH,
|
||||
bx_options.cmos.Opath = new bx_param_filename_c (BXP_CMOS_PATH,
|
||||
"Pathname of CMOS image",
|
||||
NULL,
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -885,7 +896,7 @@ void bx_init_options ()
|
||||
"Use keyboard mapping",
|
||||
NULL,
|
||||
0);
|
||||
bx_options.keyboard.Okeymap = new bx_param_string_c (BXP_KEYBOARD_MAP,
|
||||
bx_options.keyboard.Okeymap = new bx_param_filename_c (BXP_KEYBOARD_MAP,
|
||||
"Keymap filename",
|
||||
NULL,
|
||||
"", BX_PATHNAME_LEN);
|
||||
@ -967,10 +978,22 @@ static void setupWorkingDirectory (char *path)
|
||||
}
|
||||
#endif
|
||||
|
||||
int
|
||||
main(int argc, char *argv[])
|
||||
#if !BX_WITH_WX
|
||||
// main() is the entry point for all configurations, except for
|
||||
// wxWindows.
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
bx_init_siminterface ();
|
||||
bx_init_main ();
|
||||
bx_do_text_config_interface (argc, argv);
|
||||
bx_control_panel (BX_CPANEL_INIT);
|
||||
bx_continue_after_control_panel (argc, argv);
|
||||
}
|
||||
#endif
|
||||
|
||||
void
|
||||
bx_init_main ()
|
||||
{
|
||||
int arg = 1;
|
||||
// To deal with initialization order problems inherent in C++, use the macros
|
||||
// SAFE_GET_IOFUNC and SAFE_GET_GENLOG to retrieve "io" and "genlog" in all
|
||||
// constructors or functions called by constructors. The macros test for
|
||||
@ -982,7 +1005,7 @@ main(int argc, char *argv[])
|
||||
|
||||
bx_print_header ();
|
||||
bx_init_bx_dbg ();
|
||||
|
||||
bx_init_options ();
|
||||
#if BX_WITH_CARBON
|
||||
/* "-psn" is passed if we are launched by double-clicking */
|
||||
if ( argc >= 2 && strncmp (argv[1], "-psn", 4) == 0 ) {
|
||||
@ -1004,12 +1027,13 @@ main(int argc, char *argv[])
|
||||
getwd (cwd);
|
||||
BX_INFO (("Now my working directory is %s", cwd));
|
||||
#endif
|
||||
}
|
||||
|
||||
init_siminterface ();
|
||||
bx_control_panel (BX_CPANEL_INIT);
|
||||
bx_init_options ();
|
||||
|
||||
static void
|
||||
bx_do_text_config_interface (int argc, char *argv[])
|
||||
{
|
||||
// detect -nocontrolpanel or -nocp argument before anything else
|
||||
int arg = 1;
|
||||
if (argc > 1 &&
|
||||
((!strcmp ("-nocontrolpanel", argv[1]))
|
||||
|| (!strcmp ("-nocp", argv[1])))) {
|
||||
@ -1022,8 +1046,8 @@ main(int argc, char *argv[])
|
||||
enable_control_panel = 0;
|
||||
#endif
|
||||
|
||||
if (!enable_control_panel) {
|
||||
// if we don't intend to run the control panel, parse the .bochsrc now.
|
||||
if (!enable_control_panel || BX_WITH_WX) {
|
||||
/* parse configuration file and command line arguments */
|
||||
char *bochsrc = bx_find_bochsrc ();
|
||||
if (bochsrc)
|
||||
bx_read_configuration (bochsrc);
|
||||
@ -1045,7 +1069,7 @@ main(int argc, char *argv[])
|
||||
fprintf (stderr, " cd /usr/local/bochs/dlxlinux\n");
|
||||
fprintf (stderr, " bochs\n");
|
||||
#endif
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1064,8 +1088,29 @@ main(int argc, char *argv[])
|
||||
}
|
||||
// Display the pre-simulation control panel.
|
||||
SIM->set_enabled (1);
|
||||
#if !BX_WITH_WX
|
||||
// unless wxwindows interface in use, show the control panel now
|
||||
bx_control_panel (BX_CPANEL_START_MENU);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
bx_continue_after_control_panel (int argc, char *argv[])
|
||||
{
|
||||
#if BX_WITH_WX
|
||||
// FIXME: load default bochsrc right now. When the wxWindows interface
|
||||
// is more complete, you will be able to load a bochsrc using the
|
||||
// interface.
|
||||
char *bochsrc = bx_find_bochsrc ();
|
||||
if (bochsrc) {
|
||||
bx_read_configuration (bochsrc);
|
||||
free (bochsrc);
|
||||
} else {
|
||||
BX_PANIC (("Could not load a .bochsrc"));
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#if BX_DEBUGGER
|
||||
// If using the debugger, it will take control and call
|
||||
@ -1092,7 +1137,8 @@ main(int argc, char *argv[])
|
||||
// only one processor, run as fast as possible by not messing with
|
||||
// quantums and loops.
|
||||
BX_CPU(0)->cpu_loop(1);
|
||||
BX_PANIC (("cpu_loop should never return in a single-processor simulation"));
|
||||
// for one processor, the only reason for cpu_loop to return is
|
||||
// that kill_bochs_request was set by the GUI interface.
|
||||
} else {
|
||||
// SMP simulation: do a few instructions on each processor, then switch
|
||||
// to another. Increasing quantum speeds up overall performance, but
|
||||
@ -1103,15 +1149,19 @@ main(int argc, char *argv[])
|
||||
// do some instructions in each processor
|
||||
BX_CPU(processor)->cpu_loop(quantum);
|
||||
processor = (processor+1) % BX_SMP_PROCESSORS;
|
||||
if (BX_CPU(0)->kill_bochs_request)
|
||||
break;
|
||||
if (processor == 0)
|
||||
BX_TICKN(quantum);
|
||||
BX_TICKN(quantum);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
BX_INFO (("cpu loop quit, shutting down simulator"));
|
||||
bx_atexit ();
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
bx_read_configuration (char *rcfile)
|
||||
{
|
||||
@ -1254,16 +1304,15 @@ bx_init_bx_dbg (void)
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
int
|
||||
bx_atexit(void)
|
||||
{
|
||||
static Boolean been_here = 0;
|
||||
|
||||
if (been_here) return 1; // protect from reentry
|
||||
been_here = 1;
|
||||
|
||||
#if BX_PROVIDE_DEVICE_MODELS==1
|
||||
if (been_here == 0) {
|
||||
bx_pc_system.exit();
|
||||
}
|
||||
bx_pc_system.exit();
|
||||
#endif
|
||||
|
||||
#if BX_DEBUGGER == 0
|
||||
@ -1276,6 +1325,7 @@ bx_atexit(void)
|
||||
bx_devices.pci->print_i440fx_state();
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
#if (BX_PROVIDE_CPU_MEMORY==1) && (BX_EMULATE_HGA_DUMPS>0)
|
||||
|
@ -1,5 +1,5 @@
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
// $Id: misc_mem.cc,v 1.18 2002-04-09 20:12:39 bdenney Exp $
|
||||
// $Id: misc_mem.cc,v 1.19 2002-04-18 00:22:20 bdenney Exp $
|
||||
/////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Copyright (C) 2001 MandrakeSoft S.A.
|
||||
@ -90,7 +90,7 @@ BX_MEM_C::~BX_MEM_C(void)
|
||||
void
|
||||
BX_MEM_C::init_memory(int memsize)
|
||||
{
|
||||
BX_DEBUG(("Init $Id: misc_mem.cc,v 1.18 2002-04-09 20:12:39 bdenney Exp $"));
|
||||
BX_DEBUG(("Init $Id: misc_mem.cc,v 1.19 2002-04-18 00:22:20 bdenney Exp $"));
|
||||
// you can pass 0 if memory has been allocated already through
|
||||
// the constructor, or the desired size of memory if it hasn't
|
||||
|
||||
@ -137,19 +137,19 @@ BX_MEM_C::load_ROM(const char *path, Bit32u romaddress)
|
||||
);
|
||||
if (fd < 0) {
|
||||
BX_INFO(( "ROM: couldn't open ROM image file '%s'.", path));
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
ret = fstat(fd, &stat_buf);
|
||||
if (ret) {
|
||||
BX_INFO(( "ROM: couldn't stat ROM image file '%s'.", path));
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
|
||||
size = stat_buf.st_size;
|
||||
|
||||
if ( (romaddress + size) > BX_MEM_THIS len ) {
|
||||
BX_INFO(( "ROM: ROM address range > physical memsize!"));
|
||||
exit(1);
|
||||
BX_EXIT(1);
|
||||
}
|
||||
|
||||
offset = 0;
|
||||
|
Binary file not shown.
1
bochs/wxbochs.rc
Normal file
1
bochs/wxbochs.rc
Normal file
@ -0,0 +1 @@
|
||||
#include "wx/msw/wx.rc"
|
Loading…
Reference in New Issue
Block a user