[libc-commits] [libc] feat(filemode): implement class and helper functions to handle file modes for an opened file (PR #220906)
David Dada via libc-commits
libc-commits at lists.llvm.org
Thu Sep 3 06:09:12 PDT 2026
https://github.com/obadafidii updated https://github.com/llvm/llvm-project/pull/220906
>From e3dc3a646ef6c422e75810881826e211aebb7a3b Mon Sep 17 00:00:00 2001
From: tdadadavid <davidtofunmidada at gmail.com>
Date: Thu, 3 Sep 2026 13:21:11 +0100
Subject: [PATCH 1/2] feat(filemode): implement class and helper functions to
handle file modes for an opened file
Signed-off-by: tdadadavid <davidtofunmidada at gmail.com>
---
libc/src/__support/File/file_mode.h | 125 ++++++++++++++++++++++++++++
1 file changed, 125 insertions(+)
create mode 100644 libc/src/__support/File/file_mode.h
diff --git a/libc/src/__support/File/file_mode.h b/libc/src/__support/File/file_mode.h
new file mode 100644
index 0000000000000..6b837ea46f652
--- /dev/null
+++ b/libc/src/__support/File/file_mode.h
@@ -0,0 +1,125 @@
+
+#ifndef LLVM_LIBC_SRC___SUPPORT_FILE_FILE_MODE_H
+#define LLVM_LIBC_SRC___SUPPORT_FILE_FILE_MODE_H
+#include <cstdint>
+
+namespace LIBC_NAMESPACE_DECL {
+
+// FileMode class handles everything regarding the mode of the file, be it's opening mode or content type.
+class FileMode {
+public:
+ // FileMode constructor accepts the mode string as an argument.
+ // It performs validation against several rules and records the `file_mode` property to
+ // the specific mode.
+ explicit FileMode(const char *mode) : file_mode_(0) {
+ // First character in |mode| should be 'a', 'r' or 'w'.
+ if (*mode != 'a' && *mode != 'r' && *mode != 'w')
+ return;
+
+ // There should be exactly one main mode ('a', 'r' or 'w') character.
+ // If there are more than one main mode characters listed, then
+ // we will consider |mode| as incorrect and return 0;
+ int main_mode_count = 0;
+
+ for (; *mode != '\0'; ++mode) {
+ switch (*mode) {
+ case 'r':
+ file_mode_ |= static_cast<Mode>(OpenMode::READ);
+ ++main_mode_count;
+ break;
+ case 'w':
+ file_mode_ |= static_cast<Mode>(OpenMode::WRITE);
+ ++main_mode_count;
+ break;
+ case '+':
+ file_mode_ |= static_cast<Mode>(OpenMode::PLUS);
+ break;
+ case 'b':
+ file_mode_ |= static_cast<Mode>(ContentType::BINARY);
+ break;
+ case 'a':
+ file_mode_ |= static_cast<Mode>(OpenMode::APPEND);
+ ++main_mode_count;
+ break;
+ case 'x':
+ file_mode_ |= static_cast<Mode>(CreateType::EXCLUSIVE);
+ break;
+ default:
+ file_mode_ = 0;
+ }
+ }
+
+ if (main_mode_count != 1)
+ file_mode_ = 0;
+ }
+
+ // helper function to show if file allows writing
+ bool write_allowed() const {
+ return (file_mode_ & static_cast<Mode>(OpenMode::WRITE)) != 0;
+ }
+
+ // helper function to show if file allows reading
+ bool read_allowed() const {
+ return (file_mode_ & static_cast<Mode>(OpenMode::READ)) != 0;
+ }
+
+ // helper function to show if file allows appending
+ bool append_allowed() const {
+ return (file_mode_ & static_cast<Mode>(OpenMode::APPEND)) != 0;
+ }
+
+ // helper function to denote if the file is in binary format.
+ bool is_binary_format() const {
+ return (file_mode_ & static_cast<Mode>(ContentType::BINARY)) != 0;
+ }
+
+ // '+' means update is allowed
+ // TODO: ask michael if I need to give it a better name like "update_allowed" or just continue with the
+ // old convention.
+ bool is_plus() const {
+ return (file_mode_ & static_cast<Mode>(OpenMode::PLUS)) != 0;
+ }
+
+ // checks if a file was created for writing
+ bool is_exclusive_create() const {
+ return (file_mode_ & static_cast<Mode>(CreateType::EXCLUSIVE)) != 0;
+ }
+
+private:
+ // Mode is a generic or abstract mode bit for all kinds of modes
+ // (open-mode, 'content-mode', 'create-modes')
+ using Mode = uint32_t;
+
+ // Denotes the mode of the file.
+ //
+ // The three different types of flags below are to be used with '|' operator.
+ // Their values correspond to mutually exclusive bits in a 32-bit unsigned
+ // integer value. A flag set can include both READ and WRITE if the file
+ // is opened in update mode (ie. if the file was opened with a '+' the mode
+ // string.)
+ enum class OpenMode: Mode {
+ READ = 0x1,
+ WRITE = 0x2,
+ APPEND = 0x4,
+ PLUS = 0x8,
+ };
+
+ // Denotes a file opened in binary mode (which is specified by including
+ // the 'b' character in teh mode string.)
+ enum class ContentType: Mode {
+ BINARY = 0x10,
+ };
+
+ // Denotes a file to be created for writing.
+ enum class CreateType: Mode {
+ EXCLUSIVE = 0x100,
+ };
+
+ // This property tracks the mode for the particular file instance (i.e currently opened file)
+ int file_mode_;
+};
+
+
+}
+
+#endif // LLVM_LIBC_SRC___SUPPORT_FILE_FILE_MODE_H
>From b0470fe313766fcb4fac92b63d41d39314a90f75 Mon Sep 17 00:00:00 2001
From: tdadadavid <davidtofunmidada at gmail.com>
Date: Thu, 3 Sep 2026 14:08:49 +0100
Subject: [PATCH 2/2] feat(lint): lint file mode class to conform to standards
Signed-off-by: tdadadavid <davidtofunmidada at gmail.com>
---
libc/src/__support/File/file_mode.h | 23 ++++++++++++-----------
1 file changed, 12 insertions(+), 11 deletions(-)
diff --git a/libc/src/__support/File/file_mode.h b/libc/src/__support/File/file_mode.h
index 6b837ea46f652..707a448c5955d 100644
--- a/libc/src/__support/File/file_mode.h
+++ b/libc/src/__support/File/file_mode.h
@@ -5,12 +5,13 @@
namespace LIBC_NAMESPACE_DECL {
-// FileMode class handles everything regarding the mode of the file, be it's opening mode or content type.
+// FileMode class handles everything regarding the mode of the file, be it's
+// opening mode or content type.
class FileMode {
public:
// FileMode constructor accepts the mode string as an argument.
- // It performs validation against several rules and records the `file_mode` property to
- // the specific mode.
+ // It performs validation against several rules and records the `file_mode`
+ // property to the specific mode.
explicit FileMode(const char *mode) : file_mode_(0) {
// First character in |mode| should be 'a', 'r' or 'w'.
if (*mode != 'a' && *mode != 'r' && *mode != 'w')
@@ -74,8 +75,8 @@ class FileMode {
}
// '+' means update is allowed
- // TODO: ask michael if I need to give it a better name like "update_allowed" or just continue with the
- // old convention.
+ // TODO: ask michael if I need to give it a better name like "update_allowed"
+ // or just continue with the old convention.
bool is_plus() const {
return (file_mode_ & static_cast<Mode>(OpenMode::PLUS)) != 0;
}
@@ -97,7 +98,7 @@ class FileMode {
// integer value. A flag set can include both READ and WRITE if the file
// is opened in update mode (ie. if the file was opened with a '+' the mode
// string.)
- enum class OpenMode: Mode {
+ enum class OpenMode : Mode {
READ = 0x1,
WRITE = 0x2,
APPEND = 0x4,
@@ -106,20 +107,20 @@ class FileMode {
// Denotes a file opened in binary mode (which is specified by including
// the 'b' character in teh mode string.)
- enum class ContentType: Mode {
+ enum class ContentType : Mode {
BINARY = 0x10,
};
// Denotes a file to be created for writing.
- enum class CreateType: Mode {
+ enum class CreateType : Mode {
EXCLUSIVE = 0x100,
};
- // This property tracks the mode for the particular file instance (i.e currently opened file)
+ // This property tracks the mode for the particular file instance (i.e
+ // currently opened file)
int file_mode_;
};
-
-}
+} // namespace LIBC_NAMESPACE_DECL
#endif // LLVM_LIBC_SRC___SUPPORT_FILE_FILE_MODE_H
More information about the libc-commits
mailing list