首頁 >後端開發 >Golang >如何在 Linux 和 macOS 上建立模擬終端機 (TTY) 的程式?

如何在 Linux 和 macOS 上建立模擬終端機 (TTY) 的程式?

Susan Sarandon
Susan Sarandon原創
2024-12-01 06:41:17224瀏覽

How Can I Create a Program That Mimics a Terminal (TTY) on Linux and macOS?

創建一個偽裝成TTY 的程式

在許多情況下,程式會仔細檢查stdin 的性質,辨別它是否是終端( TTY)或使用特殊功能(如isatty)的管道。這種區別促使程式以不同的方式產生輸出。為了應對這項挑戰,我們將探索如何建立一個能夠偽裝成 TTY 的計畫。

適用於 Linux 和 macOS 的解決方案

下面的程式碼片段舉例說明適用於 Linux 和 macOS 的可行解決方案。它利用pty 接口,提供在偽終端中運行命令的功能,有效地欺騙程序將輸入解釋為來自TTY:

#include <signal.h>
#include <stdlib.h>
#include <sysexits.h>
#include <unistd.h>
#include <util.h>

pid_t child = 0;

void sighandler(int signum) {
  if (child > 0) {
    killpg(child, signum);
    exit(signum);
  }
}

int main(int argc, char *argv[]) {
  if (argc < 2) {
    return EX_USAGE;
  }

  int master;
  child = forkpty(&amp;master, NULL, NULL, NULL);
  // Forkpty setup: master (parent) and child (command execution)

  if (child == -1) {
    perror("failed to fork pty");
    return EX_OSERR;
  }

  if (child == 0) {
    execvp(argv[1], argv + 1);
    // Execute the specified command within the pty
  }

  signal(SIGHUP, sighandler);
  signal(SIGINT, sighandler);
  signal(SIGTERM, sighandler);
  // Trap signals and forward them to the child

  const int buf_size = 1024;
  char buf[buf_size];
  fd_set fds;
  ssize_t bytes_read;
  // I/O management variables

  while (1) {
    FD_ZERO(&amp;fds);
    FD_SET(master, &amp;fds);
    // Set up file descriptor set and monitor master (pty)

    if (select(master + 1, &amp;fds, NULL, NULL, NULL) > 0 &amp;&amp; FD_ISSET(master, &amp;fds)) {
      bytes_read = read(master, buf, buf_size);
      if (bytes_read <= 0) {
        return EXIT_SUCCESS;
      }

      if (write(STDOUT_FILENO, buf, bytes_read) != bytes_read) {
        perror("failed to write to stdout");
        return EX_OSERR;
      }
    }
  }
}

此代碼在父進程之間建立通信通道和一個在pty 中運行的子進程。父進程不斷地從 pty 讀取並將其內容轉發到 stdout,從而有效地模擬常規 TTY 的行為。

實作此方法可讓您的程式繞過需要來自 TTY 輸入的程式所施加的潛在約束。它使您的程式能夠操作和轉換輸入,同時仍保留終端的外觀。

以上是如何在 Linux 和 macOS 上建立模擬終端機 (TTY) 的程式?的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn