我有以下boost :: interprocess :: message_queue相关问题.
按照预期,我计划在> = 2个进程之间共享一个消息队列.显然,其中一个可能在消息队列中崩溃.因此,它将保留内部锁,使其他进程无法访问队列.怎么解决这个问题?似乎没有办法解锁使用的内部互斥锁.
假设我有课Base和Derived : public Base.我使用boost :: interprocess库构建了一个共享内存段.是否可以使用与此类似的代码:
Base* b = new Derived();
write(b); //one app writes
Base* b2 = read(b); //second app reads
//b equals b2 (bitwise, not the ptr location)
Run Code Online (Sandbox Code Playgroud)
我在这里看到的问题是,例如,派生的Base类所需的空间是未知的(因此要分配多少shmem?)
问:如何通过应用程序之间的指针传递对象?
首先,我将使用source概述域.
namespace bip=boost::interprocess;
typedef bip::allocator<int, bip::managed_mapped_file::segment_manager> allocator;
typedef bip::vector<int, allocator> vector;
bip::managed_mapped_file m_file(open_or_create, "./file", constant_value);
bip::allocator alloc(m_file.get_segment_manager());
bip::vector *vec = m_file.find_or_construct<vector>("vector")(alloc);
Run Code Online (Sandbox Code Playgroud)
我不关心底层文件的最终大小,但我无法预见这个值.是否有任何增强机制,它将处理调整基础文件的大小?或者我必须抓住bip :: bad_alloc并自己照顾这个?
我想从切换CreatMutex到boost::interprocess::named_mutex限制我的应用程序的单个实例.当应用程序运行并且结束时,两种方法都有效.但是,当应用程序崩溃并使用时,锁定不会被释放boost::interprocess::named_mutex.我可以通过使用两个name_mutex解决该问题,但我真的不明白这个问题.
为什么boost::interprocess::named_mutex在应用程序崩溃但未释放时锁定未释放CreatMutex?有什么不同?
boost::interprocess::named_mutex mutex(boost::interprocess::open_or_create, "my_mutex");
boost::interprocess::scoped_lock<boost::interprocess::named_mutex> lock(mutex, boost::interprocess::try_to_lock);
if(!lock) {
return 1; //exit
}
//application may crash here.
boost::interprocess::named_mutex::remove("my_mutex");
return 1; //exit
Run Code Online (Sandbox Code Playgroud) 我有一个类似指针的结构,代替指针.与指针的区别在于它具有(也是特殊的)分配器可以用来释放内存的额外信息.
这种类似指针的结构适用于所有基本用途.我可以分配和释放内存,dereferrence,increment ->等.
现在我想使用这个指针由类似STL的容器管理.早期,我意识到STL向量基本上不能处理非原始指针.
T*太硬编码了,标准基本上排除了任何不是指针的东西.
受Boost.Interprocess的启发' offset_ptr<T>我决定使用Boost.Container vector,它是非常可定制的,原则上可以管理任何东西,传递给它的分配器boost::container::vector可以处理任何类似指针的东西.
现在班上boost::container::vector<T, myallocator_with_special_pointer<T>>可以做任何事......除了resize()!!
查看其中的代码boost/container/vector.hpp似乎调整大小的过程(基本上是分配,然后是复制(或移动)和释放)涉及原始指针.
违规行是:
[line 2729:] T * const new_buf = container_detail::to_raw_pointer
(allocator_traits_type::allocate(this->m_holder.alloc(), new_cap, this->m_holder.m_start));
Run Code Online (Sandbox Code Playgroud)
后面是后面的
[line 3022:] this->m_holder.start(new_start); // new_start is the same as new_buf above.
// member ::start(pointer&) will need to convert a raw pointer to the pointer typedef.
Run Code Online (Sandbox Code Playgroud)
两条线都绝对杀死了使用任何不是的东西的可能性raw_pointer.即使我有一个原始指针的转换运算符,其他有关特殊指针的信息也将丢失.
这个小细节似乎非常愚蠢,禁止使用非原始指针.鉴于容器的所有努力都是通用的(例如,定义pointertypedef),为什么这部分代码T*仅用于调整大小?
换句话说,为什么Boost Container不使用这一行
[alternative] pointer const new_buf =
allocator_traits_type::allocate(this->m_holder.alloc(), new_cap, this->m_holder.m_start);
Run Code Online (Sandbox Code Playgroud)
是否有一种变通方法或使用Boost容器向量来处理非原始指针的替代方法? …
我尝试了几个小时,这个问题几乎让我发疯。
我想创建一个spsc_queue过度共享的内存,队列中的每个元素都是mq_item_t下面的一个结构体。
typedef struct _mq_item_t{
mq_item_type type;
union
{
struct{
log_level_t level;
char * text;
} log;
struct{
char * control;
size_t control_size;
char * payload;
size_t payload_size;
} error;
struct{
char * channel;
char * control;
size_t control_size;
char * payload;
size_t payload_size;
} data;
};
} mq_item_t;
Run Code Online (Sandbox Code Playgroud)
然后我有以下代码来创建spsc_queue.
typedef boost::interprocess::managed_windows_shared_memory native_managed_shared_memory;
typedef boost::interprocess::allocator<mq_item_t, native_managed_shared_memory::segment_manager> shmem_allocator;
typedef boost::lockfree::spsc_queue< mq_item_t, boost::lockfree::allocator<shmem_allocator>> lockfree_queue;
m_segment = new native_managed_shared_memory(create_only, mem_name, SHARED_MEMORY_BYTES, NULL, perm);
shmem_allocator alloc(m_segment->get_segment_manager());
m_segment->find_or_construct<lockfree_queue>("name of …Run Code Online (Sandbox Code Playgroud) 我正在使用IPC构建一个多生产者/单一消费者应用程序,使用Boost.Interprocess实现.
每个生产者通过在共享内存(managed_shared_memory::allocate)内部分配块来发送消息,并将对象编组到该块中.然后,它通过a发送一个小对象,message_queue它保存块的位置(偏移量)和大小.
消费者receives从队列中获取此指示符并解组该对象.消费者负责释放内存块.
基于此实现,我不相信内存中存在的对象或块需要同步,因为一旦消费者知道它们,生产者将不再触摸它们.因此,我认为只有内部message_queue和managed_shared_memory需要同步.
我的问题是:请记住每个进程都是单线程的,do allocate/ deallocate,和send/ receivecalls需要同步吗?
文档提供的Boost示例不使用消息队列的同步,但我认为这只是为了简化示例源.
我正在开发一个由2个进程组成的应用程序,这些进程必须共享一些数据结构.这些类组织在不同的库中,库用于不同的应用程序.
那么,有没有其他方法可以使用STL共享类或结构(在Windows中)?目标是不要在我们的库中创建过多的Boost依赖.
谢谢
我做IPC Linux的使用boost::interprocess::shared_memory_object按照基准(匿名互斥体示例).
有一个服务器进程,它创建shared_memory_object并写入它,同时保持interprocess_mutex包裹在scoped_lock; 和客户端进程打印其他人写的任何内容 - 在这种情况下,它是一个int.
我遇到了一个问题:如果服务器在持有互斥锁的情况下休眠,则客户端进程永远无法获取它并永远等待.
越野车服务器循环:
using namespace boost::interprocess;
int n = 0;
while (1) {
std::cerr << "acquiring mutex... ";
{
// "data" is a struct on the shared mem. and contains a mutex and an int
scoped_lock<interprocess_mutex> lock(data->mutex);
data->a = n++;
std::cerr << n << std::endl;
sleep(1);
} // if this bracket is placed before "sleep", everything works
}
Run Code Online (Sandbox Code Playgroud)
服务器输出: …
我有一些代码等待共享内存上的写操作.如果没有人写,它继续等待.
Test* Foo::Get()
{
boost::interprocess::scoped_lock<boost::interprocess::interprocess_mutex> lock ( mutex ) ; // mutex is boost::interprocess::interprocess_mutex
if ( this->check == 0 )
this->interprocessCondition.wait ( lock ) ; // interprocessCondition is boost::interprocess::interprocess_condition
...
}
Run Code Online (Sandbox Code Playgroud)
当我抽样时,我发现它消耗了大约90%的CPU.
有人可以帮我解决这个性能问题吗?请参阅附图.
