LLDB  mainline
File.h
Go to the documentation of this file.
1 //===-- File.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 liblldb_File_h_
10 #define liblldb_File_h_
11 
12 #include "lldb/Host/PosixApi.h"
13 #include "lldb/Utility/IOObject.h"
14 #include "lldb/Utility/Status.h"
15 #include "lldb/lldb-private.h"
16 
17 #include <mutex>
18 #include <stdarg.h>
19 #include <stdio.h>
20 #include <sys/types.h>
21 
22 namespace lldb_private {
23 
24 /// \class File File.h "lldb/Host/File.h"
25 /// A file class.
26 ///
27 /// A file class that divides abstracts the LLDB core from host file
28 /// functionality.
29 class File : public IOObject {
30 public:
31  static int kInvalidDescriptor;
32  static FILE *kInvalidStream;
33 
34  // NB this enum is used in the lldb platform gdb-remote packet
35  // vFile:open: and existing values cannot be modified.
36  enum OpenOptions {
37  eOpenOptionRead = (1u << 0), // Open file for reading
38  eOpenOptionWrite = (1u << 1), // Open file for writing
40  (1u << 2), // Don't truncate file when opening, append to end of file
41  eOpenOptionTruncate = (1u << 3), // Truncate file when opening
42  eOpenOptionNonBlocking = (1u << 4), // File reads
43  eOpenOptionCanCreate = (1u << 5), // Create file if doesn't already exist
45  (1u << 6), // Can create file only if it doesn't already exist
48  (1u << 8) // Close the file when executing a new process
49  };
50 
51  static mode_t ConvertOpenOptionsForPOSIXOpen(uint32_t open_options);
52 
53  File()
54  : IOObject(eFDTypeFile, false), m_descriptor(kInvalidDescriptor),
55  m_stream(kInvalidStream), m_options(0), m_own_stream(false),
59 
60  File(FILE *fh, bool transfer_ownership)
61  : IOObject(eFDTypeFile, false), m_descriptor(kInvalidDescriptor),
62  m_stream(fh), m_options(0), m_own_stream(transfer_ownership),
66 
67  File(int fd, bool transfer_ownership)
68  : IOObject(eFDTypeFile, transfer_ownership), m_descriptor(fd),
69  m_stream(kInvalidStream), m_options(0), m_own_stream(false),
72 
73  /// Destructor.
74  ///
75  /// The destructor is virtual in case this class is subclassed.
76  ~File() override;
77 
78  bool IsValid() const override {
79  return DescriptorIsValid() || StreamIsValid();
80  }
81 
82  /// Convert to pointer operator.
83  ///
84  /// This allows code to check a File object to see if it contains anything
85  /// valid using code such as:
86  ///
87  /// \code
88  /// File file(...);
89  /// if (file)
90  /// { ...
91  /// \endcode
92  ///
93  /// \return
94  /// A pointer to this object if either the directory or filename
95  /// is valid, nullptr otherwise.
96  operator bool() const { return DescriptorIsValid() || StreamIsValid(); }
97 
98  /// Logical NOT operator.
99  ///
100  /// This allows code to check a File object to see if it is invalid using
101  /// code such as:
102  ///
103  /// \code
104  /// File file(...);
105  /// if (!file)
106  /// { ...
107  /// \endcode
108  ///
109  /// \return
110  /// Returns \b true if the object has an empty directory and
111  /// filename, \b false otherwise.
112  bool operator!() const { return !DescriptorIsValid() && !StreamIsValid(); }
113 
114  /// Get the file spec for this file.
115  ///
116  /// \return
117  /// A reference to the file specification object.
118  Status GetFileSpec(FileSpec &file_spec) const;
119 
120  Status Close() override;
121 
122  void Clear();
123 
124  int GetDescriptor() const;
125 
127 
128  void SetDescriptor(int fd, bool transfer_ownership);
129 
130  FILE *GetStream();
131 
132  void SetStream(FILE *fh, bool transfer_ownership);
133 
134  /// Read bytes from a file from the current file position.
135  ///
136  /// NOTE: This function is NOT thread safe. Use the read function
137  /// that takes an "off_t &offset" to ensure correct operation in multi-
138  /// threaded environments.
139  ///
140  /// \param[in] buf
141  /// A buffer where to put the bytes that are read.
142  ///
143  /// \param[in,out] num_bytes
144  /// The number of bytes to read form the current file position
145  /// which gets modified with the number of bytes that were read.
146  ///
147  /// \return
148  /// An error object that indicates success or the reason for
149  /// failure.
150  Status Read(void *buf, size_t &num_bytes) override;
151 
152  /// Write bytes to a file at the current file position.
153  ///
154  /// NOTE: This function is NOT thread safe. Use the write function
155  /// that takes an "off_t &offset" to ensure correct operation in multi-
156  /// threaded environments.
157  ///
158  /// \param[in] buf
159  /// A buffer where to put the bytes that are read.
160  ///
161  /// \param[in,out] num_bytes
162  /// The number of bytes to write to the current file position
163  /// which gets modified with the number of bytes that were
164  /// written.
165  ///
166  /// \return
167  /// An error object that indicates success or the reason for
168  /// failure.
169  Status Write(const void *buf, size_t &num_bytes) override;
170 
171  /// Seek to an offset relative to the beginning of the file.
172  ///
173  /// NOTE: This function is NOT thread safe, other threads that
174  /// access this object might also change the current file position. For
175  /// thread safe reads and writes see the following functions: @see
176  /// File::Read (void *, size_t, off_t &) \see File::Write (const void *,
177  /// size_t, off_t &)
178  ///
179  /// \param[in] offset
180  /// The offset to seek to within the file relative to the
181  /// beginning of the file.
182  ///
183  /// \param[in] error_ptr
184  /// A pointer to a lldb_private::Status object that will be
185  /// filled in if non-nullptr.
186  ///
187  /// \return
188  /// The resulting seek offset, or -1 on error.
189  off_t SeekFromStart(off_t offset, Status *error_ptr = nullptr);
190 
191  /// Seek to an offset relative to the current file position.
192  ///
193  /// NOTE: This function is NOT thread safe, other threads that
194  /// access this object might also change the current file position. For
195  /// thread safe reads and writes see the following functions: @see
196  /// File::Read (void *, size_t, off_t &) \see File::Write (const void *,
197  /// size_t, off_t &)
198  ///
199  /// \param[in] offset
200  /// The offset to seek to within the file relative to the
201  /// current file position.
202  ///
203  /// \param[in] error_ptr
204  /// A pointer to a lldb_private::Status object that will be
205  /// filled in if non-nullptr.
206  ///
207  /// \return
208  /// The resulting seek offset, or -1 on error.
209  off_t SeekFromCurrent(off_t offset, Status *error_ptr = nullptr);
210 
211  /// Seek to an offset relative to the end of the file.
212  ///
213  /// NOTE: This function is NOT thread safe, other threads that
214  /// access this object might also change the current file position. For
215  /// thread safe reads and writes see the following functions: @see
216  /// File::Read (void *, size_t, off_t &) \see File::Write (const void *,
217  /// size_t, off_t &)
218  ///
219  /// \param[in,out] offset
220  /// The offset to seek to within the file relative to the
221  /// end of the file which gets filled in with the resulting
222  /// absolute file offset.
223  ///
224  /// \param[in] error_ptr
225  /// A pointer to a lldb_private::Status object that will be
226  /// filled in if non-nullptr.
227  ///
228  /// \return
229  /// The resulting seek offset, or -1 on error.
230  off_t SeekFromEnd(off_t offset, Status *error_ptr = nullptr);
231 
232  /// Read bytes from a file from the specified file offset.
233  ///
234  /// NOTE: This function is thread safe in that clients manager their
235  /// own file position markers and reads on other threads won't mess up the
236  /// current read.
237  ///
238  /// \param[in] dst
239  /// A buffer where to put the bytes that are read.
240  ///
241  /// \param[in,out] num_bytes
242  /// The number of bytes to read form the current file position
243  /// which gets modified with the number of bytes that were read.
244  ///
245  /// \param[in,out] offset
246  /// The offset within the file from which to read \a num_bytes
247  /// bytes. This offset gets incremented by the number of bytes
248  /// that were read.
249  ///
250  /// \return
251  /// An error object that indicates success or the reason for
252  /// failure.
253  Status Read(void *dst, size_t &num_bytes, off_t &offset);
254 
255  /// Read bytes from a file from the specified file offset.
256  ///
257  /// NOTE: This function is thread safe in that clients manager their
258  /// own file position markers and reads on other threads won't mess up the
259  /// current read.
260  ///
261  /// \param[in,out] num_bytes
262  /// The number of bytes to read form the current file position
263  /// which gets modified with the number of bytes that were read.
264  ///
265  /// \param[in,out] offset
266  /// The offset within the file from which to read \a num_bytes
267  /// bytes. This offset gets incremented by the number of bytes
268  /// that were read.
269  ///
270  /// \param[in] null_terminate
271  /// Ensure that the data that is read is terminated with a NULL
272  /// character so that the data can be used as a C string.
273  ///
274  /// \param[out] data_buffer_sp
275  /// A data buffer to create and fill in that will contain any
276  /// data that is read from the file. This buffer will be reset
277  /// if an error occurs.
278  ///
279  /// \return
280  /// An error object that indicates success or the reason for
281  /// failure.
282  Status Read(size_t &num_bytes, off_t &offset, bool null_terminate,
283  lldb::DataBufferSP &data_buffer_sp);
284 
285  /// Write bytes to a file at the specified file offset.
286  ///
287  /// NOTE: This function is thread safe in that clients manager their
288  /// own file position markers, though clients will need to implement their
289  /// own locking externally to avoid multiple people writing to the file at
290  /// the same time.
291  ///
292  /// \param[in] src
293  /// A buffer containing the bytes to write.
294  ///
295  /// \param[in,out] num_bytes
296  /// The number of bytes to write to the file at offset \a offset.
297  /// \a num_bytes gets modified with the number of bytes that
298  /// were read.
299  ///
300  /// \param[in,out] offset
301  /// The offset within the file at which to write \a num_bytes
302  /// bytes. This offset gets incremented by the number of bytes
303  /// that were written.
304  ///
305  /// \return
306  /// An error object that indicates success or the reason for
307  /// failure.
308  Status Write(const void *src, size_t &num_bytes, off_t &offset);
309 
310  /// Flush the current stream
311  ///
312  /// \return
313  /// An error object that indicates success or the reason for
314  /// failure.
315  Status Flush();
316 
317  /// Sync to disk.
318  ///
319  /// \return
320  /// An error object that indicates success or the reason for
321  /// failure.
322  Status Sync();
323 
324  /// Get the permissions for a this file.
325  ///
326  /// \return
327  /// Bits logical OR'ed together from the permission bits defined
328  /// in lldb_private::File::Permissions.
329  uint32_t GetPermissions(Status &error) const;
330 
331  /// Return true if this file is interactive.
332  ///
333  /// \return
334  /// True if this file is a terminal (tty or pty), false
335  /// otherwise.
336  bool GetIsInteractive();
337 
338  /// Return true if this file from a real terminal.
339  ///
340  /// Just knowing a file is a interactive isn't enough, we also need to know
341  /// if the terminal has a width and height so we can do cursor movement and
342  /// other terminal manipulations by sending escape sequences.
343  ///
344  /// \return
345  /// True if this file is a terminal (tty, not a pty) that has
346  /// a non-zero width and height, false otherwise.
347  bool GetIsRealTerminal();
348 
350 
351  /// Output printf formatted output to the stream.
352  ///
353  /// Print some formatted output to the stream.
354  ///
355  /// \param[in] format
356  /// A printf style format string.
357  ///
358  /// \param[in] ...
359  /// Variable arguments that are needed for the printf style
360  /// format string \a format.
361  size_t Printf(const char *format, ...) __attribute__((format(printf, 2, 3)));
362 
363  size_t PrintfVarArg(const char *format, va_list args);
364 
365  void SetOptions(uint32_t options) { m_options = options; }
366 
367  static bool DescriptorIsValid(int descriptor) { return descriptor >= 0; };
368 
369 protected:
371 
372  bool StreamIsValid() const { return m_stream != kInvalidStream; }
373 
375 
376  // Member variables
378  FILE *m_stream;
385 
386 private:
387  DISALLOW_COPY_AND_ASSIGN(File);
388 };
389 
390 } // namespace lldb_private
391 
392 #endif // liblldb_File_h_
Enumerations for broadcasting.
Definition: SBLaunchInfo.h:14
FILE * m_stream
Definition: File.h:378
std::mutex offset_access_mutex
Definition: File.h:384
Status Read(void *buf, size_t &num_bytes) override
Read bytes from a file from the current file position.
Definition: File.cpp:335
A file utility class.
Definition: FileSpec.h:55
Status Sync()
Sync to disk.
Definition: File.cpp:312
static bool DescriptorIsValid(int descriptor)
Definition: File.h:367
static mode_t ConvertOpenOptionsForPOSIXOpen(uint32_t open_options)
Definition: File.cpp:653
bool GetIsInteractive()
Return true if this file is interactive.
Definition: File.cpp:706
bool operator!() const
Logical NOT operator.
Definition: File.h:112
off_t SeekFromCurrent(off_t offset, Status *error_ptr=nullptr)
Seek to an offset relative to the current file position.
Definition: File.cpp:249
A file class.
Definition: File.h:29
void SetOptions(uint32_t options)
Definition: File.h:365
Status GetFileSpec(FileSpec &file_spec) const
Get the file spec for this file.
Definition: File.cpp:188
uint32_t m_options
Definition: File.h:379
~File() override
Destructor.
Definition: File.cpp:74
Status Close() override
Definition: File.cpp:158
bool DescriptorIsValid() const
Definition: File.h:370
LazyBool m_is_interactive
Definition: File.h:381
bool GetIsRealTerminal()
Return true if this file from a real terminal.
Definition: File.cpp:712
int m_descriptor
Definition: File.h:377
FILE * GetStream()
Definition: File.cpp:103
WaitableHandle GetWaitableHandle() override
Definition: File.cpp:94
size_t Printf(const char *format,...) __attribute__((format(printf
Output printf formatted output to the stream.
Definition: File.cpp:625
int GetDescriptor() const
Definition: File.cpp:76
off_t SeekFromStart(off_t offset, Status *error_ptr=nullptr)
Seek to an offset relative to the beginning of the file.
Definition: File.cpp:223
bool m_own_stream
Definition: File.h:380
uint32_t GetPermissions(Status &error) const
Get the permissions for a this file.
Definition: File.cpp:142
Status Write(const void *buf, size_t &num_bytes) override
Write bytes to a file at the current file position.
Definition: File.cpp:394
static int kInvalidDescriptor
Definition: File.h:31
bool GetIsTerminalWithColors()
Definition: File.cpp:718
File(int fd, bool transfer_ownership)
Definition: File.h:67
void CalculateInteractiveAndTerminal()
Definition: File.cpp:677
LazyBool m_is_real_terminal
Definition: File.h:382
LazyBool m_supports_colors
Definition: File.h:383
void SetDescriptor(int fd, bool transfer_ownership)
Definition: File.cpp:96
File(FILE *fh, bool transfer_ownership)
Definition: File.h:60
bool IsValid() const override
Definition: File.h:78
bool StreamIsValid() const
Definition: File.h:372
static FILE * kInvalidStream
Definition: File.h:32
size_t size_t PrintfVarArg(const char *format, va_list args)
Definition: File.cpp:634
Status Flush()
Flush the current stream.
Definition: File.cpp:301
off_t SeekFromEnd(off_t offset, Status *error_ptr=nullptr)
Seek to an offset relative to the end of the file.
Definition: File.cpp:275
An error handling class.
Definition: Status.h:44
void SetStream(FILE *fh, bool transfer_ownership)
Definition: File.cpp:135