YSTest  PreAlpha_b500_20140530
The YSLib Test Project
 全部  命名空间 文件 函数 变量 类型定义 枚举 枚举值 友元 宏定义  
MemoryMapping.cpp
浏览该文件的文档.
1 /*
2  © 2012-2014 FrankHB.
3 
4  This file is part of the YSLib project, and may only be used,
5  modified, and distributed under the terms of the YSLib project
6  license, LICENSE.TXT. By continuing to use, modify, or distribute
7  this file you indicate that you have read the license and
8  understand and accept it fully.
9 */
10 
28 #include "YCLib/YModules.h"
29 #include YFM_YCLib_MemoryMapping
30 #include YFM_YCLib_FileSystem // for platform::uopen, platform::GetFileSizeOf;
31 #include <fcntl.h>
32 #include <stdexcept> // for std::runtime_error;
33 #if YCL_DS
34 # include <unistd.h>
35 #elif YCL_Win32
36 # include <Windows.h>
37 # include <sys/stat.h>
38 
39 namespace
40 {
41 
42 #define MAP_FAILED (reinterpret_cast<void*>(-1))
43 
44 void*
45 map_file(size_t len, int fd)
46 {
47  void* p_mapped{};
48 
49  if(len != 0)
50  {
51  const auto h(::HANDLE(::_get_osfhandle(fd)));
52 
53  if(h != INVALID_HANDLE_VALUE)
54  if(::HANDLE fm = ::CreateFileMapping(h, nullptr, PAGE_READONLY, 0,
55  len, nullptr))
56  {
57  p_mapped = ::MapViewOfFile(fm, FILE_MAP_READ, 0, 0, len);
58  ::CloseHandle(fm);
59  }
60  }
61  return p_mapped ? p_mapped : MAP_FAILED;
62 }
63 
64 } // unnamed namespace;
65 
66 #elif YCL_Android
67 # include <sys/mman.h>
68 # include <sys/stat.h>
69 #else
70 # error "Unsupported platform found."
71 #endif
72 
73 namespace platform
74 {
75 
76 MappedFile::MappedFile(const char* path)
77  : fd(uopen(path, O_RDONLY, S_IRUSR | S_IWUSR)), size([](int fd){
78  if(fd == -1)
79  throw FileOperationFailure("Failed mapping file.");
80  return GetFileSizeOf(fd);
81  }(fd))
82 {
83 #if YCL_DS
84  addr = new ystdex::byte[size];
85 
86  ::read(fd, addr, size);
87 #else
88 # if YCL_Win32
89  const auto p(map_file(size, fd));
90 # else
91  const auto p(::mmap(0, size, PROT_READ, MAP_PRIVATE, fd, 0));
92 # endif
93 
94  if(p == MAP_FAILED)
95  throw std::runtime_error("Mapping failed.");
96  // TODO: Create specific exception type.
97  addr = static_cast<ystdex::byte*>(p);
98 #endif
99 }
101 {
102 #if YCL_DS
103  delete addr;
104 #elif YCL_Win32
105  ::UnmapViewOfFile(addr);
106 #else
107  ::munmap(addr, size);
108 #endif
109  ::close(fd);
110 }
111 
112 } // namespace platform;
113 
MappedFile(const char *)
unsigned char byte
字节类型。
Definition: ydef.h:555
std::uint64_t size
Definition: MemoryMapping.h:46
ystdex::byte * addr
Definition: MemoryMapping.h:47
表示文件操作失败的异常。
YF_API std::uint64_t GetFileSizeOf(int)
取文件的大小。
YF_API int uopen(const char *filename, int oflag) ynothrow
以 UTF-8 文件名无缓冲打开文件。