--- nono/wx/wxapp.cpp 2026/04/29 17:04:28 1.1.1.1 +++ nono/wx/wxapp.cpp 2026/04/29 17:04:53 1.1.1.7 @@ -1,155 +1,122 @@ // // nono -// Copyright (C) 2018 isaki@NetBSD.org +// Copyright (C) 2020 nono project +// Licensed under nono-license.txt // -#include "vm.h" -#include "wxheader.h" #include "wxmainframe.h" #include "wxmainview.h" #include "wxtextpanel.h" +#include "wxversion.h" #include "mainapp.h" -#include +#include "mpu680x0.h" +#include "mpu88xx0.h" +#include "scheduler.h" +#include // イベントタイプの定義 -DEFINE_EVENT_TYPE(WXW_EVT_CREATE); -DEFINE_EVENT_TYPE(WXW_EVT_MONITOR_UPDATE); - -// コマンドラインオプションとか -bool console_log; - -// コマンドラインオプション -static const wxCmdLineEntryDesc cmddesc[] = -{ - { wxCMD_LINE_OPTION, "b", "b", "breakpoint", wxCMD_LINE_VAL_STRING }, - { wxCMD_LINE_OPTION, "c", "c", "vm directory", wxCMD_LINE_VAL_STRING }, - { wxCMD_LINE_SWITCH, "d", "d", "debugger prompt on startup", }, - { wxCMD_LINE_SWITCH, "C", "C", "console log" }, - { wxCMD_LINE_SWITCH, "f", "f", "fast mode" }, - { wxCMD_LINE_OPTION, "L", "L", "loglevel (-L help displays names)", - wxCMD_LINE_VAL_STRING }, - { wxCMD_LINE_OPTION, "M", "M", "monitors to display at startup", - wxCMD_LINE_VAL_STRING }, - { wxCMD_LINE_OPTION, "s", "s", "screen scale", wxCMD_LINE_VAL_STRING }, - { wxCMD_LINE_OPTION, "", "fontsize", "font size {12, 16, 24} (default:12)", - wxCMD_LINE_VAL_STRING }, - { wxCMD_LINE_SWITCH, "v", "v", "version" }, - - { wxCMD_LINE_NONE }, -}; +wxDEFINE_EVENT(WXW_EVT_CREATE, wxCommandEvent); +wxDEFINE_EVENT(WXW_EVT_HALT_NOTIFY, wxCommandEvent); class WXApp : public wxApp { + using inherited = wxApp; public: bool OnInit(); + int OnRun() override; private: - bool Parse(); bool ParseMonitors(const wxString& str); int SearchMonitorName(const char *name); + + wxLocale locale; }; +// IMPLEMENT_APP() は闇マクロすぎて clang のちからには耐えられない +#if defined(__clang__) +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Weverything" +#endif IMPLEMENT_APP(WXApp) +#if defined(__clang__) +#pragma clang diagnostic pop +#endif bool WXApp::OnInit() { - debug_breakaddr = 0xffffffff; - WXMainView::screen_scale = 1.0; - WXTextPanel::global_fontsize = FONT_6x12; - vmdir = "."; - - if (!Parse()) { - return false; - } - - // -C オプションならコンソールにもログを出力 - if (!main_init(console_log)) { - return false; - } - - // メインウィンドウ - gMainFrame = new WXMainFrame(NULL); - gMainFrame->Show(true); - SetTopWindow(gMainFrame); return true; } -bool -WXApp::Parse() +int +WXApp::OnRun() { - u_long ulval; + int rv; - wxCmdLineParser cmd(argc, argv); - cmd.SetDesc(cmddesc); - if (cmd.Parse() != 0) { - return false; + rv = gMainApp.Init1(false, argc, argv); + if (rv != MainApp::PASS) { + return rv; + } + + // 環境変数 $NONO_BUILD_HOME が定義されていればカタログ検索パスに + // $NONO_BUILD_HOME/po を追加する (システムパスより前に挿入される)。 + // カタログ開発時にワークツリーにあるカタログを見るため。 + locale.Init(wxLANGUAGE_DEFAULT); + const char *build_home = getenv("NONO_BUILD_HOME"); + if (build_home) { + wxString path(build_home); + path += "/po"; + wxLocale::AddCatalogLookupPathPrefix(path); + } + locale.AddCatalog("nono"); + + // --fontsize テキスト系コントロールのフォントサイズ + // 紛らわしいが ::global_fontsize は 12, 16 とかいう値。 + // WXTextPanel::global_fontsize (FontId) は enum 値。 + FontId fontid; + switch (gMainApp.fontsize) { + case 12: + fontid = FontId::_6x12; + break; + case 16: + fontid = FontId::_8x16; + break; + default: + warnx("invalid fontsize: %d", gMainApp.fontsize); + return EXIT_FAILURE; } + WXTextPanel::global_fontid = fontid; - wxString arg; - - // -v - if (cmd.Found("v")) { - fprintf(stderr, "nono version %d.%d.%d\n", - NONO_MAJOR_VER, NONO_MINOR_VER, NONO_PATCH_VER); - return false; - } - - // -b ブレイクポイント - if (cmd.Found("b", &arg)) { - arg.ToULong(&ulval, 16); - debug_breakaddr = ulval; - } - - // -c 設定ファイル - if (cmd.Found("c", &arg)) { - vmdir = std::string((const char *)arg.mb_str()); - } - - // -L ログレベル - if (cmd.Found("L", &arg)) { - strlcpy(logopt, (const char *)arg.mb_str(), sizeof(logopt)); - } + // グローバルオブジェクト (どこでやるのがいいか) + gHostInfo.reset(new HostInfoMonitor()); // -M 起動時に表示するモニタ - if (cmd.Found("M", &arg)) { - if (!ParseMonitors(arg)) { - return false; + if (!gMainApp.monitor_opt.empty()) { + if (!ParseMonitors(gMainApp.monitor_opt)) { + return EXIT_FAILURE; } } - // screen scale - if (cmd.Found("s", &arg)) { - if (!arg.ToDouble(&WXMainView::screen_scale)) { - return false; - } + // -s screen scale + WXMainView::screen_scale = gMainApp.screen_scale; + + // 引数処理が終わったので、スレッド作成を伴う初期化。 + if (!gMainApp.Init2()) { + return EXIT_FAILURE; } - // テキスト系コントロールのフォントサイズ - if (cmd.Found("fontsize", &arg)) { - fontsize_t fontsize; - arg.ToULong(&ulval, 10); - switch (ulval) { - case 12: - fontsize = FONT_6x12; - break; - case 16: - fontsize = FONT_8x16; - break; - case 24: - fontsize = FONT_12x24; - break; - default: - return false; - } - WXTextPanel::global_fontsize = fontsize; + // VM にコールバックを登録 + gScheduler->SetPowerOffCallback(wxmainframe_poweroff_callback); + if (gMPU680x0) { + gMPU680x0->SetHaltCallback(wxmainframe_halt_callback, this); } - console_log = cmd.Found("C"); - debug_on_start = cmd.Found("d"); - fast_mode = cmd.Found("f"); + // メインウィンドウ + gMainFrame = new WXMainFrame(NULL); + gMainFrame->Show(true); + SetTopWindow(gMainFrame); - return true; + return inherited::OnRun(); } // -M オプションの解析。書式は @@ -159,27 +126,28 @@ WXApp::Parse() bool WXApp::ParseMonitors(const wxString& str) { - const char *sep = ","; - char *word; - char *last; - char buf[str.Length() + 1]; + int s; + int end; - if (str == wxT("help")) { + if (str == "help") { for (int i = 0; i < WinID_MAX; i++) { - fprintf(stderr, " %s\n", WXMainFrame::monitor_names[i]); + auto& info = WXMainFrame::monitor_info[i]; + if (gMainApp.HasVMFeature(info.feature)) { + fprintf(stderr, " %s\n", info.name); + } } return false; } - // 由緒正しい C でパースしてしまう - strcpy(buf, (const char *)str.mb_str()); - for (word = strtok_r(buf, sep, &last); - word; - word = strtok_r(NULL, sep, &last)) - { + for (s = 0, end = 0; s < str.Length(); s = end + 1) { + end = str.find(',', s); + if (end == wxString::npos) { + end = str.size(); + } + wxString word = str.SubString(s, end - 1); int i = SearchMonitorName(word); if (i < 0) { - warnx("Unknown window name \"%s\"", word); + warnx("Unknown window name \"%s\"", (const char *)word.mb_str()); return false; } WXMainFrame::monitor_start[i] = true; @@ -191,7 +159,10 @@ int WXApp::SearchMonitorName(const char *name) { for (int i = 0; i < WinID_MAX; i++) { - if (strcmp(name, WXMainFrame::monitor_names[i]) == 0) { + auto& info = WXMainFrame::monitor_info[i]; + if (gMainApp.HasVMFeature(info.feature) && + strcmp(name, info.name) == 0) + { return i; } }