--- nono/host/comdriver_stdio.cpp 2026/04/29 17:05:18 1.1.1.2 +++ nono/host/comdriver_stdio.cpp 2026/04/29 17:05:47 1.1.1.3 @@ -13,25 +13,38 @@ // コンストラクタ COMDriverStdio::COMDriverStdio(HostDevice *hostdev_) - : inherited(hostdev_, "Stdio") + : inherited(hostdev_, "stdio") { - // 現在の端末属性を取得 - tcgetattr(STDIN_FILENO, &oldtc); } // デストラクタ COMDriverStdio::~COMDriverStdio() { + hostdev->DelOuter(STDIN_FILENO); + // 端末属性を元に戻す - tcsetattr(STDIN_FILENO, TCSANOW, &oldtc); + if (tc_changed) { + tcsetattr(STDIN_FILENO, TCSANOW, &oldtc); + } + + stdio_occupied = false; } // ドライバ初期化 bool -COMDriverStdio::InitDriver() +COMDriverStdio::InitDriver(bool startup) { struct termios tc; + if (stdio_occupied) { + errmsg = "'stdio' is already in use by another hostcom-driver"; + putmsg(1, "%s", errmsg.c_str()); + return false; + } + + // 現在の端末属性を取得 + tcgetattr(STDIN_FILENO, &oldtc); + // 端末の設定を変更 tc = oldtc; @@ -46,15 +59,19 @@ COMDriverStdio::InitDriver() tc.c_cc[VMIN] = 1; if (tcsetattr(STDIN_FILENO, TCSANOW, &tc) < 0) { - putmsg(0, "tcsetattr: %s", strerror(errno)); + errmsg = string_format("tcsetattr: %s", strerror(errno)); + putmsg(1, "%s", errmsg.c_str()); return false; } + tc_changed = true; if (hostdev->AddOuter(STDIN_FILENO) < 0) { - putmsg(0, "AddOuter: %s", strerror(errno)); + errmsg = string_format("AddOuter: %s", strerror(errno)); + putmsg(1, "%s", errmsg.c_str()); return false; } + stdio_occupied = true; return true; } @@ -94,3 +111,6 @@ COMDriverStdio::Read() } return buf[0]; } + +// stdio を使えるのは同時に1人だけに限定する。 +/*static*/ bool COMDriverStdio::stdio_occupied = false;