2 Skelton for retropc emulator
4 Author : Kyuma.Ohta <whatisthis.sowhat _at_ gmail.com>
7 [ interface for emulation i/f ]
16 #include "osdcall_types.h"
18 //#include "vm/vm_template.h"
23 #elif defined(_USE_SDL)
39 #include "qt/osd_base.h"
44 class CSP_DebuggerThread;
49 class DrawThreadClass;
63 bool request_terminate;
72 bool request_terminate;
75 class DLL_PREFIX EMU_TEMPLATE {
79 std::shared_ptr<CSP_Logger> csp_logger;
81 _TCHAR app_path[_MAX_PATH];
83 int sound_frequency, sound_latency;
84 int sound_rate, sound_samples;
94 FIFO* auto_key_buffer;
95 int auto_key_phase, auto_key_shift;
98 uint32_t joy_status[4];
101 _TCHAR path[_MAX_PATH];
107 media_status_t cart_status[16];
108 media_status_t floppy_disk_status[16];
109 media_status_t quick_disk_status[16];
110 media_status_t hard_disk_status[16];
111 media_status_t tape_status[16];
112 media_status_t compact_disc_status[16];
113 media_status_t laser_disc_status[16];
114 media_status_t bubble_casette_status[16];
117 uint8_t dummy_key_buffer[256];
118 uint32_t dummy_joy_buffer[8];
119 int dummy_mouse_buffer[4];
121 // ----------------------------------------
123 // ---------------------------------------
125 EMU_TEMPLATE(class Ui_MainWindow *hwnd, GLDrawClass *hinst, std::shared_ptr<CSP_Logger> p_logger, std::shared_ptr<USING_FLAGS> p)
126 #elif defined(OSD_WIN32)
127 EMU_TEMPLATE(HWND hwnd, HINSTANCE hinst)
132 memset(dummy_key_buffer, 0x00, sizeof(dummy_key_buffer));
133 memset(dummy_joy_buffer, 0x00, sizeof(dummy_joy_buffer));
134 memset(dummy_mouse_buffer, 0x00, sizeof(dummy_mouse_buffer));
135 memset(message, 0x00, sizeof(message));
137 now_debugging = false;
138 memset(&debugger_thread_param, 0x00, sizeof(debugger_thread_t));
140 memset(app_path, 0x00, sizeof(app_path));
142 sound_frequency = 44100;
145 sound_samples = 4410;
148 dipswitch = 0x00000000;
153 now_suspended = false;
155 auto_key_buffer = NULL;
158 shift_pressed = false;
160 memset(joy_status, 0x00, sizeof(joy_status));
161 for(int i = 0; i < 16; i++) {
162 memset(&(cart_status[i]), 0x00, sizeof(media_status_t));
163 memset(&(floppy_disk_status[i]), 0x00, sizeof(media_status_t));
164 memset(&(quick_disk_status[i]), 0x00, sizeof(media_status_t));
165 memset(&(hard_disk_status[i]), 0x00, sizeof(media_status_t));
166 memset(&(tape_status[i]), 0x00, sizeof(media_status_t));
167 memset(&(compact_disc_status[i]), 0x00, sizeof(media_status_t));
168 memset(&(laser_disc_status[i]), 0x00, sizeof(media_status_t));
169 memset(&(bubble_casette_status[i]), 0x00, sizeof(media_status_t));
173 csp_logger = p_logger;
174 debugger_thread_id = (pthread_t)0;
176 // ToDo: Multiple debugger 20221105 K.O
178 #elif defined(OSD_WIN32)
179 hDebuggerThread = (HANDLE)0;
181 debugger_thread_id = 0;
187 virtual ~EMU_TEMPLATE() {}
189 // ----------------------------------------
191 // ----------------------------------------
192 virtual VM_TEMPLATE *get_vm() { return NULL; }
193 virtual OSD_BASE *get_osd() { return NULL; }
197 virtual EmuThreadClass *get_parent_handler() { return NULL; }
198 virtual void set_parent_handler(EmuThreadClass *p, DrawThreadClass *q) {}
199 virtual void set_host_cpus(int v) {}
200 virtual int get_host_cpus() { return 1; }
202 virtual double get_frame_rate() { return 59.94; }
203 virtual int get_frame_interval() { return 1; }
204 virtual bool is_frame_skippable() { return false; }
205 virtual const bool is_use_state() { return false; }
207 virtual int run() { return 1; }
209 virtual void reset() {}
210 virtual void special_reset(int num) {}
211 virtual void notify_power_off() {}
212 virtual void power_off() {}
213 virtual void suspend() {}
215 // around locking VM, these are useful for multi-threaded environment.
216 virtual void lock_vm() {}
217 virtual void unlock_vm() {}
218 virtual void force_unlock_vm() {}
219 virtual bool is_vm_locked() { return false; }
223 virtual void key_down(int code, bool extended, bool repeat) {}
224 virtual void key_up(int code, bool extended) {}
225 virtual void key_char(char code) {}
227 virtual bool get_caps_locked() { return false; }
228 virtual bool get_kana_locked() { return false; }
229 virtual void key_lost_focus() {}
230 virtual void press_button(int num) {}
233 virtual void set_auto_key_list(char *buf, int size) {}
234 virtual void set_auto_key_char(char code) {}
235 virtual void start_auto_key() {}
236 virtual void stop_auto_key() {}
237 virtual bool is_auto_key_running() { return false; }
238 virtual FIFO* get_auto_key_buffer() { return NULL; }
240 virtual const uint8_t* get_key_buffer() { return dummy_key_buffer; }
241 // Joystick buffer should be with locking and sampling.
242 virtual const uint32_t* get_joy_buffer() { return dummy_joy_buffer; }
243 virtual void release_joy_buffer(const uint32_t* ptr) { };
245 // Mouse buffer should be with locking and sampling.
246 virtual const int32_t* get_mouse_buffer() { return dummy_mouse_buffer; }
247 virtual const int32_t get_mouse_button() { return 0; }
248 virtual void release_mouse_buffer(const int32_t* ptr) { };
249 virtual void enable_mouse() {}
250 virtual void disable_mouse() {}
251 virtual void toggle_mouse() {}
252 virtual bool is_mouse_enabled() { return false; }
255 virtual double get_window_mode_power(int mode) { return 1.0; }
256 virtual int get_window_mode_width(int mode) { return 640; }
257 virtual int get_window_mode_height(int mode) { return 200; }
258 virtual void set_host_window_size(int window_width, int window_height,
260 virtual void set_vm_screen_size(int screen_width, int screen_height,
261 int window_width, int window_height,
262 int window_width_aspect, int window_height_aspect) {}
263 virtual void set_vm_screen_lines(int lines) {}
264 virtual int get_vm_window_width() { return 640; }
265 virtual int get_vm_window_height() { return 200; }
266 virtual int get_vm_window_width_aspect() { return 640; }
267 virtual int get_vm_window_height_aspect() { return 200; }
268 virtual bool is_screen_changed() { return true; }
269 virtual int draw_screen() { return 1; }
270 virtual scrntype_t* get_screen_buffer(int y) { return NULL;}
271 virtual void screen_skip_line(bool skip_line) {}
273 // One-board-micro-computer
274 virtual void get_invalidated_rect(int *left, int *top, int *right, int *bottom) {}
275 virtual void reload_bitmap() {}
278 virtual void invalidate_screen() {}
279 virtual void update_screen(HDC hdc) {}
281 // Screen capture and recording.Will update API.
282 virtual void capture_screen() {}
283 virtual bool start_record_video(int fps) { return false;}
284 virtual void stop_record_video() {}
285 virtual bool is_video_recording() { return false; }
288 virtual int get_sound_rate() { return 44100; }
289 virtual void mute_sound() {}
290 virtual void start_record_sound() {}
291 virtual void stop_record_sound() {}
292 virtual bool is_sound_recording() { return false; }
295 virtual void get_video_buffer() {}
296 virtual void mute_video_dev(bool l, bool r) {}
299 virtual bool open_movie_file(const _TCHAR* file_path) { return false; }
300 virtual void close_movie_file() {}
301 virtual void play_movie() {}
302 virtual void stop_movie() {}
303 virtual void pause_movie() {}
304 virtual double get_movie_frame_rate() { return 29.97; }
305 virtual int get_movie_sound_rate() { return 44100; }
306 virtual void set_cur_movie_frame(int frame, bool relative) {}
307 virtual uint32_t get_cur_movie_frame() { return 0; }
310 virtual int get_cur_capture_dev_index() { return 0; }
311 virtual int get_num_capture_devs() { return 0; }
312 virtual _TCHAR* get_capture_dev_name(int index) { return (_TCHAR*)_T("DUMMY"); }
313 virtual void open_capture_dev(int index, bool pin) {}
314 virtual void close_capture_dev() {}
315 virtual void show_capture_dev_filter() {}
316 virtual void show_capture_dev_pin() {}
317 virtual void show_capture_dev_source() {}
318 virtual void set_capture_dev_channel(int ch) {}
321 virtual void create_bitmap(bitmap_t *bitmap, int width, int height) {}
322 virtual void release_bitmap(bitmap_t *bitmap) {}
323 virtual void create_font(font_t *font,
324 const _TCHAR *family,
325 int width, int height,
326 int rotate, bool bold, bool italic) {}
327 virtual void release_font(font_t *font) {}
328 virtual void create_pen(pen_t *pen, int width,
329 uint8_t r, uint8_t g, uint8_t b) {}
330 virtual void release_pen(pen_t *pen) {}
331 virtual void clear_bitmap(bitmap_t *bitmap,
332 uint8_t r, uint8_t g, uint8_t b) {}
333 virtual int get_text_width(bitmap_t *bitmap,
334 font_t *font, const char *text) { return 16; }
335 virtual void draw_text_to_bitmap(bitmap_t *bitmap, font_t *font,
336 int x, int y, const char *text,
337 uint8_t r, uint8_t g, uint8_t b) {}
338 virtual void draw_line_to_bitmap(bitmap_t *bitmap, pen_t *pen,
339 int sx, int sy, int ex, int ey) {}
340 virtual void draw_rectangle_to_bitmap(bitmap_t *bitmap,
342 int width, int height,
343 uint8_t r, uint8_t g, uint8_t b) {}
344 virtual void draw_point_to_bitmap(bitmap_t *bitmap,
346 uint8_t r, uint8_t g, uint8_t b) {}
347 virtual void stretch_bitmap(bitmap_t *dest, int dest_x, int dest_y,
348 int dest_width, int dest_height,
350 int source_x, int source_y, int source_width,
351 int source_height) {}
352 virtual void write_bitmap_to_file(bitmap_t *bitmap, const _TCHAR *file_path) {}
355 virtual SOCKET get_socket(int ch) { return (SOCKET)0; }
356 virtual void notify_socket_connected(int ch) {}
357 virtual void notify_socket_disconnected(int ch) {}
358 virtual bool initialize_socket_tcp(int ch) { return false; }
359 virtual bool initialize_socket_udp(int ch) { return false; }
361 virtual bool connect_socket(int ch, uint32_t ipaddr, int port) {return false;}
362 virtual void disconnect_socket(int ch) {}
364 virtual bool listen_socket(int ch) { return false; }
365 virtual void send_socket_data_tcp(int ch) {}
366 virtual void send_socket_data_udp(int ch, uint32_t ipaddr, int port) {}
368 virtual void send_socket_data(int ch) {}
369 virtual void recv_socket_data(int ch) {}
372 // Note: OSD's API will be different from upstream.
373 // Because, will use libPortMidi to access devices,
374 // seems to need timestamp (to send data).
375 // See, https://portmedia.sourceforge.net/portmidi/ .
376 // Optionally, set timestamp for relative usec at VM.
378 virtual void __FASTCALL send_to_midi(uint8_t data, int ch = 0, double timestamp_usec = 0.0) {}
379 virtual bool __FASTCALL recv_from_midi(uint8_t* data, int ch = 0, double timestamp_usec = 0.0) { return false; }
381 // Send / Receive with timeout.
382 // If timeout (no connection) , OSD calls EMU::notify_timeout_*_midi(ch) .
383 // If Success to communication, OSD calls ready_*_midi(ch, timestamp).
384 virtual bool __FASTCALL send_to_midi_timeout(uint8_t data, int ch = 0, uint64_t timeout_ms = 0, double timestamp_usec = 0.0) { return true; /* dummy send. */ }
385 virtual bool __FASTCALL recv_from_midi_timeout(uint8_t* data, int ch = 0, uint64_t timeout_ms = 0, double timestamp_usec = 0.0) { return false; }
387 //virtual void __FASTCALL notify_timeout_sending_to_midi(int ch = 0) {}
388 //virtual void __FASTCALL notify_timeout_receiving_from_midi(int ch = 0) {}
390 // Reset physical midi device(s). nagative value will reset all.
391 virtual void __FASTCALL reset_to_midi(int ch = -1, double timestamp_usec = 0.0) {}
392 // Belows are interface between osd and vm/devices.
393 // Some interface devices on VM may have handshake (maybe via UART).
394 virtual void __FASTCALL initialize_midi_device(bool handshake_from_midi = false,
395 bool handshake_to_midi = false,
398 //virtual void __FASTCALL ready_receive_from_midi(int ch = 0, double timestamp_usec = 0.0) {}
399 virtual void __FASTCALL ready_send_to_midi(int ch = 0, double timestamp_usec = 0.0) {}
400 virtual void __FASTCALL request_stop_to_receive_from_midi(int ch = 0, double timestamp_usec = 0.0) {}
401 //virtual void __FASTCALL request_stop_to_send_to_midi(int ch = 0, double timestamp_usec = 0.0) {}
404 virtual void initialize_debugger() { }
405 virtual void release_debugger() { }
407 virtual void open_debugger(int cpu_index) {}
408 virtual void close_debugger(int cpu_index) {}
409 virtual bool is_debugger_enabled(int cpu_index) { return false; }
412 int debugger_cpu_index, debugger_target_id;
413 int request_save_state, request_load_state;
414 debugger_thread_t debugger_thread_param;
417 // ToDo: Multiple debugger 20221105 K.O
418 pthread_t debugger_thread_id;
419 std::shared_ptr<CSP_Debugger>hDebugger;
420 #elif defined(OSD_WIN32)
421 HANDLE hDebuggerThread;
423 int debugger_thread_id;
426 virtual void start_waiting_in_debugger() {}
427 virtual void finish_waiting_in_debugger() {}
428 virtual void process_waiting_in_debugger() {}
429 bool now_waiting_in_debugger;
432 virtual void out_debug_log(const _TCHAR* format, ...) {}
433 virtual void force_out_debug_log(const _TCHAR* format, ...) {}
435 virtual void out_message(const _TCHAR* format, ...) {}
437 _TCHAR message[1024];
440 virtual void sleep(uint32_t ms) {}
443 virtual void initialize_debug_log() {}
444 virtual void release_debug_log() {}
450 _TCHAR path[_MAX_PATH];
451 _TCHAR disk_name[64][128]; // Convert to UTF8
455 virtual bool create_blank_floppy_disk(const _TCHAR* file_path, uint8_t type) { return false;}
456 virtual void open_floppy_disk(int drv, const _TCHAR* file_path, int bank) {}
457 virtual void close_floppy_disk(int drv) {}
458 virtual bool is_floppy_disk_connected(int drv) { return false;}
459 virtual bool is_floppy_disk_inserted(int drv) { return false;}
460 virtual void is_floppy_disk_protected(int drv, bool value) {}
461 virtual bool is_floppy_disk_protected(int drv) { return false;}
462 virtual uint32_t is_floppy_disk_accessed() { return 0x00000000; }
463 virtual uint32_t floppy_disk_indicator_color() { return 0x00000000; }
466 virtual void open_cart(int drv, const _TCHAR* file_path) {}
467 virtual void close_cart(int drv) {}
468 virtual bool is_cart_inserted(int drv) { return false; }
471 virtual void open_quick_disk(int drv, const _TCHAR* file_path) {}
472 virtual void close_quick_disk(int drv) {}
473 virtual bool is_quick_disk_connected(int drv) { return false; }
474 virtual bool is_quick_disk_inserted(int drv) { return false; }
475 virtual uint32_t is_quick_disk_accessed() { return 0x00000000; }
476 virtual bool get_quick_disk_status(int drive, _TCHAR* media_name, size_t buflen, bool& play, int& wait_count, int& cur_bank)
482 virtual bool create_blank_hard_disk(const _TCHAR* file_path,
483 int sector_size, int sectors,
484 int surfaces, int cylinders) { return false; }
485 virtual void open_hard_disk(int drv, const _TCHAR* file_path) {}
486 virtual void close_hard_disk(int drv) {}
487 virtual bool is_hard_disk_inserted(int drv) { return false; }
488 virtual uint32_t is_hard_disk_accessed() { return 0x00000000; }
489 virtual bool get_hard_disk_status(int drive, _TCHAR* media_name, size_t buflen, bool& play, int& wait_count, int& cur_bank)
495 virtual void play_tape(int drv, const _TCHAR* file_path) {}
496 virtual void rec_tape(int drv, const _TCHAR* file_path) {}
497 virtual void close_tape(int drv) {}
498 virtual bool is_tape_inserted(int drv) { return false; }
499 virtual bool is_tape_playing(int drv) { return false; }
500 virtual bool is_tape_recording(int drv) { return false; }
501 virtual int get_tape_position(int drv) { return 0; }
502 virtual const _TCHAR* get_tape_message(int drv) { return _T(" "); }
503 virtual void push_play(int drv) {}
504 virtual void push_stop(int drv) {}
505 virtual void push_fast_forward(int drv) {}
506 virtual void push_fast_rewind(int drv) {}
507 virtual void push_apss_forward(int drv) {}
508 virtual void push_apss_rewind(int drv) {}
511 virtual void open_compact_disc(int drv, const _TCHAR* file_path) {}
512 virtual void close_compact_disc(int drv) {}
513 virtual bool is_compact_disc_inserted(int drv) { return false; }
514 virtual uint32_t is_compact_disc_accessed() { return 0x00000000; }
517 virtual void open_laser_disc(int drv, const _TCHAR* file_path) {}
518 virtual void close_laser_disc(int drv) {}
519 virtual bool is_laser_disc_inserted(int drv) { return false; }
520 virtual uint32_t is_laser_disc_accessed() { return 0x00000000; }
522 // binary file (memory image)
523 virtual void load_binary(int drv, const _TCHAR* file_path) {}
524 virtual void save_binary(int drv, const _TCHAR* file_path) {}
528 _TCHAR path[_MAX_PATH];
529 _TCHAR bubble_name[16][128]; // Convert to UTF8
533 virtual void open_bubble_casette(int drv, const _TCHAR* file_path, int bank) {}
534 virtual void close_bubble_casette(int drv) {}
535 virtual bool is_bubble_casette_inserted(int drv) { return false; }
536 virtual bool is_bubble_casette_protected(int drv) { return false; }
537 virtual void is_bubble_casette_protected(int drv, bool value) {}
540 virtual uint32_t get_led_status() { return 0x00000000; }
543 virtual void set_sound_device_volume(int ch, int decibel_l, int decibel_r) {}
546 virtual void update_config() {}
549 virtual void save_state(const _TCHAR* file_path) {}
550 virtual void load_state(const _TCHAR* file_path) {}
551 virtual const _TCHAR *state_file_path(int num) { return (const _TCHAR*)_T("."); }
553 // messaging proxies.
554 // These are mostly used for replying mounting virtual media.
556 virtual void __FASTCALL osdcall_string(EMU_MEDIA_TYPE::type_t media_type, int drive, EMU_MESSAGE_TYPE::type_t message_type, _TCHAR* message) {}
557 virtual void __FASTCALL osdcall_int(EMU_MEDIA_TYPE::type_t media_type, int drive, EMU_MESSAGE_TYPE::type_t message_type, int64_t data) { }