2013-02-15 3 views
8

boost::lockfree::queue<<T, fixed_sized<false>, ..> 을 공유 메모리에 두는 데 문제가 있습니다. 내가 대기열에 65535 개 이상의 메시지를 삽입 할 수 있기 때문에 내가 필요하고, fixed_sized 큐는 다음 코드가 제대로 작동 65535
로 제한된다 (그러나 capacity<...> 옵션은 fixed_sized<true>을 의미) :공유 메모리의 boost :: lockfree :: queue 문제 (부스트 1.53, gcc 4.7.2/clang 3.0-6ubuntu3)

typedef boost::interprocess::allocator< 
    MessageT, 
    boost::interprocess::managed_shared_memory::segment_manager> 
     ShmemAllocator; 
typedef boost::lockfree::queue< 
    MessageT, 
    boost::lockfree::capacity<65535>, 
    boost::lockfree::allocator<ShmemAllocator> > 
     Queue; 
m_segment = new boost::interprocess::managed_shared_memory(
    boost::interprocess::create_only, segmentName, size); 
Queue* m_queue = m_segment->construct<Queue>(
    queueName)(
    m_segment->get_segment_manager()); 
... 
m_queue->bounded_push(message); 

boost::lockfree::queue<MessageT> q; 
.... 
q.bounded_push(message); 

을하지만 그것을 결합 할 때 : (하지만 공유 메모리를 사용하지 않습니다)도 제대로 코드를 작품 다음

typedef boost::interprocess::allocator< 
    MessageT, 
    boost::interprocess::managed_shared_memory::segment_manager> 
     ShmemAllocator; 
typedef boost::lockfree::queue< 
    MessageT, 
    boost::lockfree::allocator<ShmemAllocator> > 
     Queue; 
m_segment = new boost::interprocess::managed_shared_memory(
    boost::interprocess::create_only, segmentName, size); 
Queue* m_queue = m_segment->construct<Queue>(
    queueName)(
    m_segment->get_segment_manager()); 
... 
m_queue->bounded_push(message); 
,

다음과 같은 로그와 함께 컴파일에 실패 :

In file included from src/model/Queue.h:16: 

In file included from /home/uppi/lib/include/boost/lockfree/queue.hpp:24: 

/home/uppi/lib/include/boost/lockfree/detail/freelist.hpp:171:28: error: no viable conversion from 'pointer' (aka 'offset_ptr<boost::lockfree::queue<PacketMessage, 
     boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, 
     boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, boost::parameter::void_>::node, long, unsigned long, 0UL>') to 
     'boost::lockfree::queue<PacketMessage, boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, 
     boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, 
     boost::parameter::void_>::node *' 
        return Alloc::allocate(1); 
          ~~~~~~~~~~~~~~~~~ 

/home/uppi/lib/include/boost/lockfree/detail/freelist.hpp:157:20: note: in instantiation of function template specialization 'boost::lockfree::detail::freelist_stack<boost::lockfree::queue<PacketMessage, 
     boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, 
     boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, boost::parameter::void_>::node, 
     boost::interprocess::allocator<boost::lockfree::queue<PacketMessage, boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, 
     boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, 
     boost::parameter::void_>::node, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned 
     long, 0>, 0>, iset_index> > >::allocate_impl<true>' requested here 
      return allocate_impl<Bounded>(); 


/home/uppi/lib/include/boost/lockfree/detail/freelist.hpp:89:20: note: in instantiation of function template specialization 'boost::lockfree::detail::freelist_stack<boost::lockfree::queue<PacketMessage, 
     boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, 
     boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, boost::parameter::void_>::node, 
     boost::interprocess::allocator<boost::lockfree::queue<PacketMessage, boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, 
     boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, 
     boost::parameter::void_>::node, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned 
     long, 0>, 0>, iset_index> > >::allocate<true, true>' requested here 
     T * node = allocate<ThreadSafe, Bounded>(); 


/home/uppi/lib/include/boost/lockfree/queue.hpp:281:34: note: in instantiation of function template specialization 'boost::lockfree::detail::freelist_stack<boost::lockfree::queue<PacketMessage, 
     boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, 
     boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, boost::parameter::void_>::node, 
     boost::interprocess::allocator<boost::lockfree::queue<PacketMessage, boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, 
     boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, 
     boost::parameter::void_>::node, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned 
     long, 0>, 0>, iset_index> > >::construct<true, true, PacketMessage, boost::lockfree::queue<PacketMessage, boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, 
     boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, 
     boost::parameter::void_, boost::parameter::void_>::node *>' requested here 
     node * n = pool.template construct<true, Bounded>(t, pool.null_handle()); 


/home/uppi/lib/include/boost/lockfree/queue.hpp:270:16: note: in instantiation of function template specialization 'boost::lockfree::queue<PacketMessage, 
     boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, 
     boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, boost::parameter::void_, boost::parameter::void_>::do_push<true>' requested here 
     return do_push<true>(t); 


src/model/Queue.inl:4:18: note: in instantiation of member function 'boost::lockfree::queue<PacketMessage, boost::lockfree::allocator<boost::interprocess::allocator<PacketMessage, 
     boost::interprocess::segment_manager<char, boost::interprocess::rbtree_best_fit<boost::interprocess::mutex_family, boost::interprocess::offset_ptr<void, long, unsigned long, 0>, 0>, iset_index> > >, 
     boost::parameter::void_, boost::parameter::void_>::bounded_push' requested here 
     return m_queue->bounded_push(message);       

/home/uppi/lib/include/boost/interprocess/offset_ptr.hpp:450:4: note: candidate function 
    operator unspecified_bool_type() const 

내가 공유 메모리에 boost::lockfree::queue 또는 boost::lockfree::stack를 사용하여

+0

lockfree의 저자 인 Tim Blechmann에게 이것에 대해 물어 보셨습니까? 그는 대개 꽤 도움이됩니다. – eile

+0

감사합니다. 나는 그에게 전자 메일을 보냈습니다. – uppi

답변

14

를 누락 무엇을 말해 호환성을 위해, 65535 개 요소로 제한하십시오. 단 하나 생산자, 단 하나 소비자 사용 케이스가있는 경우에, boost::lockfree::spsc_queue를 사용하고 싶을 수도있다. 그러나 이것은 동적 크기가 아닙니다.

이유는 32 비트 호환성입니다. 64 비트 플랫폼의 경우 boost.lockfree 코드를 사용하여 16 비트 인덱스 대신 32 비트를 사용할 수 있습니다. 일을 올바르게 구현하기 위해서는 다소 사소한 변화가 필요할 것입니다.

+0

설명해 주셔서 감사합니다. – uppi

+0

@timblechmann 그러나 플랫폼 x86_64가 이미 10 년 동안 존재한다면, 왜 boost :: lockfree :: queue의 64 비트 구현을 구현하지 않았습니까? – Alex

+0

@Alex는 손을 더럽 히고 데이터 구조를 구성하는 정책을 추가하는 패치를 제공합니다. – timblechmann