aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChris Lattner <sabre@nondot.org>2008-04-01 00:53:25 +0000
committerChris Lattner <sabre@nondot.org>2008-04-01 00:53:25 +0000
commit540630f637c14d27eadc1c79e93fbc2360715206 (patch)
tree9553325b0caa60995768cc7d6e8068a288ccb0ec
parent328c84aa992138cda53d197f4d180ec5b40a5aa2 (diff)
cleanup the MappedFile API and comments. This removes and updates
tons of out of date comments (really nothing throws here!) and fixes some other fairly glaring issues: "size" used to return the size of the file *and* change it, depending on how you called it. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@49009 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--include/llvm/System/MappedFile.h135
-rw-r--r--lib/System/Unix/MappedFile.inc133
-rw-r--r--lib/System/Win32/MappedFile.inc104
3 files changed, 159 insertions, 213 deletions
diff --git a/include/llvm/System/MappedFile.h b/include/llvm/System/MappedFile.h
index af13cbb5af..6f902d28a1 100644
--- a/include/llvm/System/MappedFile.h
+++ b/include/llvm/System/MappedFile.h
@@ -28,145 +28,90 @@ namespace sys {
/// for mapping a file into memory for both read and write access. This class
/// does not provide facilities for finding the file or operating on paths to
/// files. The sys::Path class is used for that.
- /// @since 1.4
- /// @brief An abstraction for memory mapped files.
class MappedFile {
- /// @name Types
- /// @{
+ sys::PathWithStatus Path; ///< Path to the file.
+ unsigned Options; ///< Options used to create the mapping
+ void *BasePtr; ///< Pointer to the base memory address
+ mutable MappedFileInfo *MapInfo; ///< Platform specific info for the mapping
+
+ MappedFile& operator=(const MappedFile &that); // DO NOT IMPLEMENT
+ MappedFile(const MappedFile &that); // DO NOT IMPLEMENT
public:
enum MappingOptions {
- READ_ACCESS = 0x0001, ///< Map the file for reading
- WRITE_ACCESS = 0x0002, ///< Map the file for write access
- EXEC_ACCESS = 0x0004, ///< Map the file for execution access
+ READ_ACCESS = 0x0001, ///< Map the file for reading
+ WRITE_ACCESS = 0x0002, ///< Map the file for write access
+ EXEC_ACCESS = 0x0004, ///< Map the file for execution access
SHARED_MAPPING = 0x0008 ///< Map the file shared with other processes
};
- /// @}
- /// @name Constructors
- /// @{
- public:
- /// Construct a MappedFile to the \p path in the operating system's file
- /// system with the mapping \p options provided.
- /// @throws std::string if an error occurs
- MappedFile() : path_(), options_(READ_ACCESS), base_(0), info_(0) {}
+
+ MappedFile() : Options(READ_ACCESS), BasePtr(0), MapInfo(0) {}
/// Destruct a MappedFile and release all memory associated with it.
- /// @throws std::string if an error occurs
- ~MappedFile() { if (info_) terminate(); }
+ ~MappedFile() { close(); }
+
+ public: // Accessors
- /// @}
- /// @name Accessors
- /// @{
- public:
/// This function determines if the file is currently mapped or not.
- /// @returns true iff the file is mapped into memory, false otherwise
- /// @brief Determine if a MappedFile is currently mapped
- /// @throws nothing
- bool isMapped() const { return base_ != 0; }
+ bool isMapped() const { return BasePtr != 0; }
/// This function returns a void* pointer to the base address of the file
/// mapping. This is the memory address of the first byte in the file.
/// Note that although a non-const pointer is returned, the memory might
/// not actually be writable, depending on the MappingOptions used when
/// the MappedFile was opened.
- /// @returns The base pointer to the memory mapped file.
- /// @brief Obtain the base pointer to the memory mapped file.
- /// @throws nothing
- void* base() const { return base_; }
+ void* base() const { return BasePtr; }
/// This function returns a char* pointer to the base address of the file
/// mapping. This is the memory address of the first byte in the file.
/// Note that although a non-const pointer is returned, the memory might
/// not actually be writable, depending on the MappingOptions used when
/// the MappedFile was opened.
- /// @returns The base pointer to the memory mapped file as a char pointer.
- /// @brief Obtain the base pointer to the memory mapped file.
- /// @throws nothing
- char* charBase() const { return reinterpret_cast<char*>(base_); }
+ char* charBase() const { return reinterpret_cast<char*>(BasePtr); }
/// This function returns a reference to the sys::Path object kept by the
/// MappedFile object. This contains the path to the file that is or
/// will be mapped.
- /// @returns sys::Path containing the path name.
- /// @brief Returns the mapped file's path as a sys::Path
- /// @throws nothing
- const sys::Path& path() const { return path_; }
+ const sys::Path& path() const { return Path; }
/// This function returns the number of bytes in the file.
- /// @throws std::string if an error occurs
size_t size() const;
- /// @}
- /// @name Mutators
- /// @{
- public:
- /// Open a file to be mapped and get its size but don't map it yet.
- /// @returns true if an error occurred
- bool open(
- const sys::Path& p, ///< Path to file to be mapped
- int options = READ_ACCESS, ///< Access mode for the mapping
- std::string* ErrMsg = 0 ///< Optional error string pointer
- ) {
- path_ = p;
- options_ = options;
+ public: // Mutators
+
+ /// Open a file to be mapped and get its size but don't map it yet. Return
+ /// true on error.
+ bool open(const sys::Path &P, int options = READ_ACCESS,
+ std::string *ErrMsg = 0) {
+ Path = P;
+ Options = options;
return initialize(ErrMsg);
}
- /// The mapped file is removed from memory. If the file was mapped for
+ /// unmap - Remove the mapped file from memory. If the file was mapped for
/// write access, the memory contents will be automatically synchronized
/// with the file's disk contents.
- /// @brief Remove the file mapping from memory.
void unmap();
- /// The mapped file is put into memory.
- /// @returns The base memory address of the mapped file or 0 if an error
- /// occurred.
- /// @brief Map the file into memory.
- void* map(
- std::string* ErrMsg = 0///< Optional error string pointer
- );
+ /// map - Reserve space for the file, map it into memory, and return a
+ /// pointer to it. This returns the base memory address of the mapped file
+ /// or 0 if an error occurred.
+ void *map(std::string* ErrMsg = 0);
- /// This method causes the size of the file, and consequently the size
- /// of the mapping to be set. This is logically the same as unmap(),
+ /// resize - This method causes the size of the file, and consequently the
+ /// size of the mapping to be set. This is logically the same as unmap(),
/// adjust size of the file, map(). Consequently, when calling this
/// function, the caller should not rely on previous results of the
/// map(), base(), or baseChar() members as they may point to invalid
/// areas of memory after this call.
- /// @throws std::string if an error occurs
- /// @brief Set the size of the file and memory mapping.
- bool size(size_t new_size, std::string* ErrMsg = 0);
+ bool resize(size_t new_size, std::string *ErrMsg = 0);
- void close() { if (info_) terminate(); }
+ void close() { if (MapInfo) terminate(); }
- /// @}
- /// @name Implementation
- /// @{
- private:
- /// @brief Initialize platform-specific portion
- bool initialize(std::string* ErrMsg);
-
- /// @brief Terminate platform-specific portion
- void terminate();
-
- /// @}
- /// @name Data
- /// @{
- private:
- sys::PathWithStatus path_; ///< Path to the file.
- int options_; ///< Options used to create the mapping
- void* base_; ///< Pointer to the base memory address
- mutable MappedFileInfo* info_; ///< Platform specific info for the mapping
-
- /// @}
- /// @name Disabled
- /// @{
private:
- ///< Disallow assignment
- MappedFile& operator=(const MappedFile &that);
- ///< Disallow copying
- MappedFile(const MappedFile& that);
- /// @}
+ bool initialize(std::string *ErrMsg);
+ void terminate();
};
-}
-}
+} // end namespace sys
+} // end namespace llvm
#endif
diff --git a/lib/System/Unix/MappedFile.inc b/lib/System/Unix/MappedFile.inc
index 546a226ef3..dcfd1892f8 100644
--- a/lib/System/Unix/MappedFile.inc
+++ b/lib/System/Unix/MappedFile.inc
@@ -31,105 +31,109 @@
#include <sys/stat.h>
#endif
-namespace llvm {
+using namespace llvm;
using namespace sys;
-struct sys::MappedFileInfo {
- int FD;
- off_t Size;
-};
+namespace llvm {
+ namespace sys {
+ struct MappedFileInfo {
+ int FD;
+ off_t Size;
+ };
+ }
+}
bool MappedFile::initialize(std::string* ErrMsg) {
int mode = 0;
- if (options_ & READ_ACCESS)
- if (options_ & WRITE_ACCESS)
+ if (Options & READ_ACCESS)
+ if (Options & WRITE_ACCESS)
mode = O_RDWR;
else
mode = O_RDONLY;
- else if (options_ & WRITE_ACCESS)
+ else if (Options & WRITE_ACCESS)
mode = O_WRONLY;
- int FD = ::open(path_.c_str(), mode);
+ int FD = ::open(Path.c_str(), mode);
if (FD < 0) {
- MakeErrMsg(ErrMsg, "can't open file '" + path_.toString() + "'");
+ MakeErrMsg(ErrMsg, "can't open file '" + Path.toString() + "'");
return true;
}
- const FileStatus *Status = path_.getFileStatus(false, ErrMsg);
+ const FileStatus *Status = Path.getFileStatus(false, ErrMsg);
if (!Status) {
::close(FD);
return true;
}
- info_ = new MappedFileInfo;
- info_->FD = FD;
- info_->Size = Status->getSize();
+ MapInfo = new MappedFileInfo();
+ MapInfo->FD = FD;
+ MapInfo->Size = Status->getSize();
return false;
}
void MappedFile::terminate() {
- assert(info_ && "MappedFile not initialized");
- ::close(info_->FD);
- delete info_;
- info_ = 0;
+ assert(MapInfo && "MappedFile not initialized");
+ ::close(MapInfo->FD);
+ delete MapInfo;
+ MapInfo = 0;
}
void MappedFile::unmap() {
- assert(info_ && "MappedFile not initialized");
- if (isMapped()) {
- if (options_ & WRITE_ACCESS)
- ::msync(base_, info_->Size, MS_SYNC);
- ::munmap(base_, info_->Size);
- base_ = 0; // Mark this as non-mapped.
- }
+ assert(MapInfo && "MappedFile not initialized");
+ if (!isMapped()) return;
+
+ if (Options & WRITE_ACCESS)
+ ::msync(BasePtr, MapInfo->Size, MS_SYNC);
+ ::munmap(BasePtr, MapInfo->Size);
+ BasePtr = 0; // Mark this as non-mapped.
}
void* MappedFile::map(std::string* ErrMsg) {
- assert(info_ && "MappedFile not initialized");
- if (!isMapped()) {
- int prot = PROT_NONE;
- int flags = 0;
+ assert(MapInfo && "MappedFile not initialized");
+ if (isMapped()) return BasePtr;
+
+ int prot = PROT_NONE;
+ int flags = 0;
#ifdef MAP_FILE
- flags |= MAP_FILE;
+ flags |= MAP_FILE;
#endif
- if (options_ == 0) {
- prot = PROT_READ;
- flags = MAP_PRIVATE;
- } else {
- if (options_ & READ_ACCESS)
- prot |= PROT_READ;
- if (options_ & WRITE_ACCESS)
- prot |= PROT_WRITE;
- if (options_ & EXEC_ACCESS)
- prot |= PROT_EXEC;
- if (options_ & SHARED_MAPPING)
- flags |= MAP_SHARED;
- else
- flags |= MAP_PRIVATE;
- }
- size_t map_size = ((info_->Size / Process::GetPageSize())+1) *
- Process::GetPageSize();
-
- base_ = ::mmap(0, map_size, prot, flags, info_->FD, 0);
- if (base_ == MAP_FAILED) {
- MakeErrMsg(ErrMsg, "Can't map file:" + path_.toString());
- return 0;
- }
+ if (Options == 0) {
+ prot = PROT_READ;
+ flags = MAP_PRIVATE;
+ } else {
+ if (Options & READ_ACCESS)
+ prot |= PROT_READ;
+ if (Options & WRITE_ACCESS)
+ prot |= PROT_WRITE;
+ if (Options & EXEC_ACCESS)
+ prot |= PROT_EXEC;
+ if (Options & SHARED_MAPPING)
+ flags |= MAP_SHARED;
+ else
+ flags |= MAP_PRIVATE;
}
- return base_;
+ size_t map_size = ((MapInfo->Size / Process::GetPageSize())+1) *
+ Process::GetPageSize();
+
+ BasePtr = ::mmap(0, map_size, prot, flags, MapInfo->FD, 0);
+ if (BasePtr == MAP_FAILED) {
+ MakeErrMsg(ErrMsg, "Can't map file:" + Path.toString());
+ return 0;
+ }
+ return BasePtr;
}
size_t MappedFile::size() const {
- assert(info_ && "MappedFile not initialized");
- return info_->Size;
+ assert(MapInfo && "MappedFile not initialized");
+ return MapInfo->Size;
}
-bool MappedFile::size(size_t new_size, std::string* ErrMsg) {
- assert(info_ && "MappedFile not initialized");
+bool MappedFile::resize(size_t new_size, std::string* ErrMsg) {
+ assert(MapInfo && "MappedFile not initialized");
// Take the mapping out of memory
- this->unmap();
+ unmap();
// Adjust the current size to a page boundary
- size_t cur_size = ((info_->Size / Process::GetPageSize())+1) *
+ size_t cur_size = ((MapInfo->Size / Process::GetPageSize())+1) *
Process::GetPageSize();
// Adjust the new_size to a page boundary
@@ -140,15 +144,12 @@ bool MappedFile::size(size_t new_size, std::string* ErrMsg) {
if (new_size > cur_size) {
// Ensure we can allocate at least the idodes necessary to handle the
// file size requested.
- if ((off_t)-1 == ::lseek(info_->FD, new_size, SEEK_SET))
+ if ((off_t)-1 == ::lseek(MapInfo->FD, new_size, SEEK_SET))
return MakeErrMsg(ErrMsg, "Can't lseek: ");
- if (-1 == ::write(info_->FD, "\0", 1))
+ if (-1 == ::write(MapInfo->FD, "\0", 1))
return MakeErrMsg(ErrMsg, "Can't write: ");
}
// Put the mapping back into memory.
- return this->map(ErrMsg);
+ return map(ErrMsg);
}
-
-}
-
diff --git a/lib/System/Win32/MappedFile.inc b/lib/System/Win32/MappedFile.inc
index 28dbb9856d..de8eec3673 100644
--- a/lib/System/Win32/MappedFile.inc
+++ b/lib/System/Win32/MappedFile.inc
@@ -28,32 +28,32 @@ struct sys::MappedFileInfo {
};
bool MappedFile::initialize(std::string* ErrMsg) {
- assert(!info_);
- info_ = new MappedFileInfo;
- info_->hFile = INVALID_HANDLE_VALUE;
- info_->hMapping = NULL;
-
- DWORD mode = options_ & WRITE_ACCESS ? GENERIC_WRITE : GENERIC_READ;
- DWORD disposition = options_ & WRITE_ACCESS ? OPEN_ALWAYS : OPEN_EXISTING;
- DWORD share = options_ & WRITE_ACCESS ? FILE_SHARE_WRITE : FILE_SHARE_READ;
- share = options_ & SHARED_MAPPING ? share : 0;
- info_->hFile = CreateFile(path_.c_str(), mode, share, NULL, disposition,
+ assert(!MapInfo);
+ MapInfo = new MappedFileInfo;
+ MapInfo->hFile = INVALID_HANDLE_VALUE;
+ MapInfo->hMapping = NULL;
+
+ DWORD mode = Options & WRITE_ACCESS ? GENERIC_WRITE : GENERIC_READ;
+ DWORD disposition = Options & WRITE_ACCESS ? OPEN_ALWAYS : OPEN_EXISTING;
+ DWORD share = Options & WRITE_ACCESS ? FILE_SHARE_WRITE : FILE_SHARE_READ;
+ share = Options & SHARED_MAPPING ? share : 0;
+ MapInfo->hFile = CreateFile(Path.c_str(), mode, share, NULL, disposition,
FILE_ATTRIBUTE_NORMAL, NULL);
- if (info_->hFile == INVALID_HANDLE_VALUE) {
- delete info_;
- info_ = NULL;
+ if (MapInfo->hFile == INVALID_HANDLE_VALUE) {
+ delete MapInfo;
+ MapInfo = NULL;
return MakeErrMsg(ErrMsg,
- std::string("Can't open file: ") + path_.toString());
+ std::string("Can't open file: ") + Path.toString());
}
LARGE_INTEGER size;
- if (!GetFileSizeEx(info_->hFile, &size) ||
- (info_->size = size_t(size.QuadPart), info_->size != size.QuadPart)) {
- CloseHandle(info_->hFile);
- delete info_;
- info_ = NULL;
+ if (!GetFileSizeEx(MapInfo->hFile, &size) ||
+ (MapInfo->size = size_t(size.QuadPart), MapInfo->size != size.QuadPart)) {
+ CloseHandle(MapInfo->hFile);
+ delete MapInfo;
+ MapInfo = NULL;
return MakeErrMsg(ErrMsg,
- std::string("Can't get size of file: ") + path_.toString());
+ std::string("Can't get size of file: ") + Path.toString());
}
return false;
@@ -61,56 +61,56 @@ bool MappedFile::initialize(std::string* ErrMsg) {
void MappedFile::terminate() {
unmap();
- if (info_->hFile != INVALID_HANDLE_VALUE)
- CloseHandle(info_->hFile);
- delete info_;
- info_ = NULL;
+ if (MapInfo->hFile != INVALID_HANDLE_VALUE)
+ CloseHandle(MapInfo->hFile);
+ delete MapInfo;
+ MapInfo = NULL;
}
void MappedFile::unmap() {
- assert(info_ && "MappedFile not initialized");
+ assert(MapInfo && "MappedFile not initialized");
if (isMapped()) {
- UnmapViewOfFile(base_);
- base_ = NULL;
+ UnmapViewOfFile(BasePtr);
+ BasePtr = NULL;
}
- if (info_->hMapping != INVALID_HANDLE_VALUE) {
- CloseHandle(info_->hMapping);
- info_->hMapping = NULL;
+ if (MapInfo->hMapping != INVALID_HANDLE_VALUE) {
+ CloseHandle(MapInfo->hMapping);
+ MapInfo->hMapping = NULL;
}
}
void* MappedFile::map(std::string* ErrMsg) {
if (!isMapped()) {
DWORD prot = PAGE_READONLY;
- if (options_ & EXEC_ACCESS)
+ if (Options & EXEC_ACCESS)
prot = SEC_IMAGE;
- else if (options_ & WRITE_ACCESS)
+ else if (Options & WRITE_ACCESS)
prot = PAGE_READWRITE;
- info_->hMapping = CreateFileMapping(info_->hFile, NULL, prot, 0, 0, NULL);
- if (info_->hMapping == NULL) {
- MakeErrMsg(ErrMsg, std::string("Can't map file: ") + path_.toString());
+ MapInfo->hMapping = CreateFileMapping(MapInfo->hFile, NULL, prot, 0, 0, NULL);
+ if (MapInfo->hMapping == NULL) {
+ MakeErrMsg(ErrMsg, std::string("Can't map file: ") + Path.toString());
return 0;
}
- prot = (options_ & WRITE_ACCESS) ? FILE_MAP_WRITE : FILE_MAP_READ;
- base_ = MapViewOfFileEx(info_->hMapping, prot, 0, 0, 0, NULL);
- if (base_ == NULL) {
- CloseHandle(info_->hMapping);
- info_->hMapping = NULL;
- MakeErrMsg(ErrMsg, std::string("Can't map file: ") + path_.toString());
+ prot = (Options & WRITE_ACCESS) ? FILE_MAP_WRITE : FILE_MAP_READ;
+ BasePtr = MapViewOfFileEx(MapInfo->hMapping, prot, 0, 0, 0, NULL);
+ if (BasePtr == NULL) {
+ CloseHandle(MapInfo->hMapping);
+ MapInfo->hMapping = NULL;
+ MakeErrMsg(ErrMsg, std::string("Can't map file: ") + Path.toString());
return 0;
}
}
- return base_;
+ return BasePtr;
}
size_t MappedFile::size() const {
- assert(info_ && "MappedFile not initialized");
- return info_->size;
+ assert(MapInfo && "MappedFile not initialized");
+ return MapInfo->size;
}
-bool MappedFile::size(size_t new_size, std::string* ErrMsg) {
- assert(info_ && "MappedFile not initialized");
+bool MappedFile::resize(size_t new_size, std::string* ErrMsg) {
+ assert(MapInfo && "MappedFile not initialized");
// Take the mapping out of memory.
unmap();
@@ -120,16 +120,16 @@ bool MappedFile::size(size_t new_size, std::string* ErrMsg) {
new_size = (new_size + pagesizem1) & ~pagesizem1;
// If the file needs to be extended, do so.
- if (new_size > info_->size) {
+ if (new_size > MapInfo->size) {
LARGE_INTEGER eof;
eof.QuadPart = new_size;
- if (!SetFilePointerEx(info_->hFile, eof, NULL, FILE_BEGIN))
+ if (!SetFilePointerEx(MapInfo->hFile, eof, NULL, FILE_BEGIN))
return MakeErrMsg(ErrMsg,
- std::string("Can't set end of file: ") + path_.toString());
- if (!SetEndOfFile(info_->hFile))
+ std::string("Can't set end of file: ") + Path.toString());
+ if (!SetEndOfFile(MapInfo->hFile))
return MakeErrMsg(ErrMsg,
- std::string("Can't set end of file: ") + path_.toString());
- info_->size = new_size;
+ std::string("Can't set end of file: ") + Path.toString());
+ MapInfo->size = new_size;
}
// Remap the file.