mirror of
https://github.com/mutouyun/cpp-ipc.git
synced 2025-12-06 16:56:45 +08:00
support for specified shm modes
This commit is contained in:
parent
adbc187ffe
commit
10e6cca8b0
@ -9,7 +9,12 @@ namespace shm {
|
||||
|
||||
using id_t = void*;
|
||||
|
||||
IPC_EXPORT id_t acquire(char const * name, std::size_t size);
|
||||
enum : unsigned {
|
||||
create = 0x01,
|
||||
open = 0x02
|
||||
};
|
||||
|
||||
IPC_EXPORT id_t acquire(char const * name, std::size_t size, unsigned mode = create | open);
|
||||
IPC_EXPORT void * to_mem (id_t id);
|
||||
IPC_EXPORT void release(id_t id, void * mem, std::size_t size);
|
||||
IPC_EXPORT void remove (char const * name);
|
||||
@ -17,7 +22,7 @@ IPC_EXPORT void remove (char const * name);
|
||||
class IPC_EXPORT handle {
|
||||
public:
|
||||
handle();
|
||||
handle(char const * name, std::size_t size);
|
||||
handle(char const * name, std::size_t size, unsigned mode = create | open);
|
||||
handle(handle&& rhs);
|
||||
|
||||
~handle();
|
||||
@ -29,7 +34,7 @@ public:
|
||||
std::size_t size () const;
|
||||
char const * name () const;
|
||||
|
||||
bool acquire(char const * name, std::size_t size);
|
||||
bool acquire(char const * name, std::size_t size, unsigned mode = create | open);
|
||||
void release();
|
||||
|
||||
void* get() const;
|
||||
|
||||
@ -40,7 +40,7 @@ inline auto& str_of(void* mem, std::size_t size) {
|
||||
namespace ipc {
|
||||
namespace shm {
|
||||
|
||||
id_t acquire(char const * name, std::size_t size) {
|
||||
id_t acquire(char const * name, std::size_t size, unsigned mode) {
|
||||
if (name == nullptr || name[0] == '\0' || size == 0) {
|
||||
return nullptr;
|
||||
}
|
||||
@ -49,8 +49,22 @@ id_t acquire(char const * name, std::size_t size) {
|
||||
ipc::error("name is too long!: [%d]%s\n", static_cast<int>(op_name.size()), op_name.c_str());
|
||||
return nullptr;
|
||||
}
|
||||
int fd = ::shm_open(op_name.c_str(), O_CREAT | O_RDWR,
|
||||
S_IRUSR | S_IWUSR |
|
||||
// Open the object for read-write access.
|
||||
int flag = O_RDWR;
|
||||
switch (mode) {
|
||||
case open:
|
||||
break;
|
||||
// The check for the existence of the object,
|
||||
// and its creation if it does not exist, are performed atomically.
|
||||
case create:
|
||||
flag |= O_CREAT | O_EXCL;
|
||||
break;
|
||||
// Create the shared memory object if it does not exist.
|
||||
default:
|
||||
flag |= O_CREAT;
|
||||
break;
|
||||
}
|
||||
int fd = ::shm_open(op_name.c_str(), flag, S_IRUSR | S_IWUSR |
|
||||
S_IRGRP | S_IWGRP |
|
||||
S_IROTH | S_IWOTH);
|
||||
if (fd == -1) {
|
||||
|
||||
@ -13,16 +13,29 @@
|
||||
namespace ipc {
|
||||
namespace shm {
|
||||
|
||||
id_t acquire(char const * name, std::size_t size) {
|
||||
id_t acquire(char const * name, std::size_t size, unsigned mode) {
|
||||
if (name == nullptr || name[0] == '\0' || size == 0) {
|
||||
return nullptr;
|
||||
}
|
||||
HANDLE h = ::CreateFileMapping(INVALID_HANDLE_VALUE, NULL,
|
||||
PAGE_READWRITE | SEC_COMMIT,
|
||||
0, static_cast<DWORD>(size),
|
||||
ipc::detail::to_tchar(std::string{"__IPC_SHM__"} + name).c_str());
|
||||
HANDLE h;
|
||||
auto fmt_name = ipc::detail::to_tchar(std::string{"__IPC_SHM__"} + name);
|
||||
// Opens a named file mapping object.
|
||||
if (mode == open) {
|
||||
h = ::OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, fmt_name.c_str());
|
||||
}
|
||||
// Creates or opens a named file mapping object for a specified file.
|
||||
else {
|
||||
h = ::CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE | SEC_COMMIT,
|
||||
0, static_cast<DWORD>(size), fmt_name.c_str());
|
||||
// If the object exists before the function call, the function returns a handle to the existing object
|
||||
// (with its current size, not the specified size), and GetLastError returns ERROR_ALREADY_EXISTS.
|
||||
if ((mode == create) && (::GetLastError() == ERROR_ALREADY_EXISTS)) {
|
||||
::CloseHandle(h);
|
||||
h = NULL;
|
||||
}
|
||||
}
|
||||
if (h == NULL) {
|
||||
ipc::error("fail CreateFileMapping[%d]: %s\n", static_cast<int>(::GetLastError()), name);
|
||||
ipc::error("fail CreateFileMapping/OpenFileMapping[%d]: %s\n", static_cast<int>(::GetLastError()), name);
|
||||
return nullptr;
|
||||
}
|
||||
return static_cast<id_t>(h);
|
||||
|
||||
@ -21,9 +21,9 @@ handle::handle()
|
||||
: p_(p_->make()) {
|
||||
}
|
||||
|
||||
handle::handle(char const * name, std::size_t size)
|
||||
handle::handle(char const * name, std::size_t size, unsigned mode)
|
||||
: handle() {
|
||||
acquire(name, size);
|
||||
acquire(name, size, mode);
|
||||
}
|
||||
|
||||
handle::handle(handle&& rhs)
|
||||
@ -57,10 +57,10 @@ char const * handle::name() const {
|
||||
return impl(p_)->n_.c_str();
|
||||
}
|
||||
|
||||
bool handle::acquire(char const * name, std::size_t size) {
|
||||
bool handle::acquire(char const * name, std::size_t size, unsigned mode) {
|
||||
release();
|
||||
impl(p_)->id_ = shm::acquire((impl(p_)->n_ = name).c_str(),
|
||||
impl(p_)->s_ = size);
|
||||
impl(p_)->s_ = size, mode);
|
||||
impl(p_)->m_ = shm::to_mem (impl(p_)->id_);
|
||||
return valid();
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user