1 //===-- Terminal.h ----------------------------------------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #ifndef LLDB_HOST_TERMINAL_H 10 #define LLDB_HOST_TERMINAL_H 11 #if defined(__cplusplus) 12 13 #include "lldb/lldb-private.h" 14 #include "llvm/Support/Error.h" 15 16 namespace lldb_private { 17 18 class TerminalState; 19 20 class Terminal { 21 public: 22 enum class Parity { 23 No, 24 Even, 25 Odd, 26 Space, 27 Mark, 28 }; 29 30 enum class ParityCheck { 31 // No parity checking 32 No, 33 // Replace erraneous bytes with NUL 34 ReplaceWithNUL, 35 // Ignore erraneous bytes 36 Ignore, 37 // Mark erraneous bytes by prepending them with \xFF\x00; real \xFF 38 // is escaped to \xFF\xFF 39 Mark, 40 }; 41 m_fd(fd)42 Terminal(int fd = -1) : m_fd(fd) {} 43 44 ~Terminal() = default; 45 46 bool IsATerminal() const; 47 GetFileDescriptor()48 int GetFileDescriptor() const { return m_fd; } 49 SetFileDescriptor(int fd)50 void SetFileDescriptor(int fd) { m_fd = fd; } 51 FileDescriptorIsValid()52 bool FileDescriptorIsValid() const { return m_fd != -1; } 53 Clear()54 void Clear() { m_fd = -1; } 55 56 llvm::Error SetEcho(bool enabled); 57 58 llvm::Error SetCanonical(bool enabled); 59 60 llvm::Error SetRaw(); 61 62 llvm::Error SetBaudRate(unsigned int baud_rate); 63 64 llvm::Error SetStopBits(unsigned int stop_bits); 65 66 llvm::Error SetParity(Parity parity); 67 68 llvm::Error SetParityCheck(ParityCheck parity_check); 69 70 llvm::Error SetHardwareFlowControl(bool enabled); 71 72 protected: 73 struct Data; 74 75 int m_fd; // This may or may not be a terminal file descriptor 76 77 llvm::Expected<Data> GetData(); 78 llvm::Error SetData(const Data &data); 79 80 friend class TerminalState; 81 }; 82 83 /// \class TerminalState Terminal.h "lldb/Host/Terminal.h" 84 /// A RAII-friendly terminal state saving/restoring class. 85 /// 86 /// This class can be used to remember the terminal state for a file 87 /// descriptor and later restore that state as it originally was. 88 class TerminalState { 89 public: 90 /// Construct a new instance and optionally save terminal state. 91 /// 92 /// \param[in] term 93 /// The Terminal instance holding the file descriptor to save the state 94 /// of. If the instance is not associated with a fd, no state will 95 /// be saved. 96 /// 97 /// \param[in] save_process_group 98 /// If \b true, save the process group settings, else do not 99 /// save the process group settings for a TTY. 100 TerminalState(Terminal term = -1, bool save_process_group = false); 101 102 /// Destroy the instance, restoring terminal state if saved. If restoring 103 /// state is undesirable, the instance needs to be reset before destruction. 104 ~TerminalState(); 105 106 /// Save the TTY state for \a fd. 107 /// 108 /// Save the current state of the TTY for the file descriptor "fd" and if 109 /// "save_process_group" is true, attempt to save the process group info for 110 /// the TTY. 111 /// 112 /// \param[in] term 113 /// The Terminal instance holding fd to save. 114 /// 115 /// \param[in] save_process_group 116 /// If \b true, save the process group settings, else do not 117 /// save the process group settings for a TTY. 118 /// 119 /// \return 120 /// Returns \b true if \a fd describes a TTY and if the state 121 /// was able to be saved, \b false otherwise. 122 bool Save(Terminal term, bool save_process_group); 123 124 /// Restore the TTY state to the cached state. 125 /// 126 /// Restore the state of the TTY using the cached values from a previous 127 /// call to TerminalState::Save(int,bool). 128 /// 129 /// \return 130 /// Returns \b true if the TTY state was successfully restored, 131 /// \b false otherwise. 132 bool Restore() const; 133 134 /// Test for valid cached TTY state information. 135 /// 136 /// \return 137 /// Returns \b true if this object has valid saved TTY state 138 /// settings that can be used to restore a previous state, 139 /// \b false otherwise. 140 bool IsValid() const; 141 142 void Clear(); 143 144 protected: 145 /// Test if tflags is valid. 146 /// 147 /// \return 148 /// Returns \b true if \a m_tflags is valid and can be restored, 149 /// \b false otherwise. 150 bool TFlagsIsValid() const; 151 152 /// Test if ttystate is valid. 153 /// 154 /// \return 155 /// Returns \b true if \a m_ttystate is valid and can be 156 /// restored, \b false otherwise. 157 bool TTYStateIsValid() const; 158 159 /// Test if the process group information is valid. 160 /// 161 /// \return 162 /// Returns \b true if \a m_process_group is valid and can be 163 /// restored, \b false otherwise. 164 bool ProcessGroupIsValid() const; 165 166 // Member variables 167 Terminal m_tty; ///< A terminal 168 int m_tflags = -1; ///< Cached tflags information. 169 std::unique_ptr<Terminal::Data> m_data; ///< Platform-specific implementation. 170 lldb::pid_t m_process_group = -1; ///< Cached process group information. 171 }; 172 173 } // namespace lldb_private 174 175 #endif // #if defined(__cplusplus) 176 #endif // LLDB_HOST_TERMINAL_H 177