60 using namespace EVENTSLIB;
66 static const std::string defaultSharedMemoryBufferKey(
"MNE_EVENTS_SHAREDMEMORY_BUFFER");
67 static const std::string defaultGroupName(
"external");
69 int EVENTSINTERNAL::EventSharedMemManager::m_iLastUpdateIndex(0);
75 constexpr
static int bufferLength(5);
76 static long long defatult_timerBufferWatch(200);
87 : m_EventSample(sample)
88 , m_CreatorId(creator)
98 return m_CreationTime;
105 return m_EventSample;
119 return m_TypeOfUpdate;
133 return EVENTSINTERNAL::EventUpdateTypeString[m_TypeOfUpdate];
139 : m_pEventManager(parent)
140 , m_SharedMemory(QString::fromStdString(defaultSharedMemoryBufferKey))
142 , m_sGroupName(defaultGroupName)
143 , m_bGroupCreated(false)
145 , m_SharedMemorySize(sizeof(int) + bufferLength * sizeof(
EventUpdate))
146 , m_fTimerCheckBuffer(defatult_timerBufferWatch)
147 , m_BufferWatcherThreadRunning(false)
148 , m_WritingToSharedMemory(false)
151 , m_SharedBuffer(nullptr)
153 , m_Mode(EVENTSLIB::SharedMemoryMode::READ)
160 EVENTSINTERNAL::EventSharedMemManager::~EventSharedMemManager()
162 detachFromSharedMemory();
163 delete[] m_LocalBuffer;
175 detachFromSharedMemory();
178 if(m_Mode == EVENTSLIB::SharedMemoryMode::READ)
180 attachToSharedSegment(QSharedMemory::AccessMode::ReadOnly);
181 launchSharedMemoryWatcherThread();
183 }
else if(m_Mode == EVENTSLIB::SharedMemoryMode::WRITE)
185 attachToOrCreateSharedSegment( QSharedMemory::AccessMode::ReadWrite);
186 }
else if(m_Mode == EVENTSLIB::SharedMemoryMode::READWRITE)
188 attachToOrCreateSharedSegment( QSharedMemory::AccessMode::ReadWrite);
189 launchSharedMemoryWatcherThread();
196 void EVENTSINTERNAL::EventSharedMemManager::attachToOrCreateSharedSegment(QSharedMemory::AccessMode mode)
198 attachToSharedSegment(mode);
201 m_IsInit = createSharedSegment(m_SharedMemorySize, mode);
207 void EVENTSINTERNAL::EventSharedMemManager::attachToSharedSegment(QSharedMemory::AccessMode mode)
209 m_IsInit = m_SharedMemory.attach(mode);
212 m_SharedBuffer =
static_cast<EventUpdate*
>(m_SharedMemory.data());
218 bool EVENTSINTERNAL::EventSharedMemManager::createSharedSegment(
int bufferSize, QSharedMemory::AccessMode mode)
220 bool output = m_SharedMemory.create(bufferSize, mode);
223 m_SharedBuffer =
static_cast<EventUpdate*
>(m_SharedMemory.data());
224 initializeSharedMemory();
231 void EVENTSINTERNAL::EventSharedMemManager::launchSharedMemoryWatcherThread()
233 m_BufferWatcherThread = std::thread(&EventSharedMemManager::bufferWatcher,
this);
238 void EVENTSINTERNAL::EventSharedMemManager::detachFromSharedMemory()
240 stopSharedMemoryWatcherThread();
241 if(!m_BufferWatcherThreadRunning && !m_WritingToSharedMemory)
243 if(m_SharedMemory.isAttached())
245 m_SharedMemory.detach();
252 void EVENTSINTERNAL::EventSharedMemManager::stopSharedMemoryWatcherThread()
254 if(m_BufferWatcherThreadRunning)
257 m_BufferWatcherThread.join();
265 detachFromSharedMemory();
281 (m_Mode == EVENTSLIB::SharedMemoryMode::WRITE ||
282 m_Mode == EVENTSLIB::SharedMemoryMode::READWRITE ) )
284 EventUpdate newUpdate(sample, m_Id, EventUpdateType::NEW_EVENT);
285 copyNewUpdateToSharedMemory(newUpdate);
294 (m_Mode == EVENTSLIB::SharedMemoryMode::WRITE ||
295 m_Mode == EVENTSLIB::SharedMemoryMode::READWRITE ) )
297 EventUpdate newUpdate(sample, m_Id, EventUpdateType::DELETE_EVENT);
298 copyNewUpdateToSharedMemory(newUpdate);
304 void EVENTSINTERNAL::EventSharedMemManager::initializeSharedMemory()
308 void* localBuffer =
static_cast<void*
>(m_LocalBuffer);
309 char* sharedBuffer =
static_cast<char*
>(m_SharedMemory.data()) +
sizeof(
int);
310 int indexIterator(0);
311 m_WritingToSharedMemory =
true;
312 if(m_SharedMemory.isAttached())
314 m_SharedMemory.lock();
315 memcpy(m_SharedMemory.data(), &indexIterator,
sizeof(
int));
316 memcpy(sharedBuffer, localBuffer, bufferLength *
sizeof(
EventUpdate));
317 m_SharedMemory.unlock();
319 m_WritingToSharedMemory =
false;
324 void EVENTSINTERNAL::EventSharedMemManager::copyNewUpdateToSharedMemory(EventUpdate& newUpdate)
328 char* sharedBuffer =
static_cast<char*
>(m_SharedMemory.data()) +
sizeof(
int);
329 int indexIterator(0);
330 m_WritingToSharedMemory =
true;
331 if(m_SharedMemory.isAttached())
333 m_SharedMemory.lock();
334 memcpy(&indexIterator, m_SharedMemory.data(),
sizeof(
int));
335 memcpy(m_SharedMemory.data(), &(++indexIterator),
sizeof(
int));
336 int index = (indexIterator-1) % bufferLength;
337 memcpy(sharedBuffer + (index *
sizeof(EventUpdate)),
static_cast<void*
>(&newUpdate),
sizeof(EventUpdate));
338 m_SharedMemory.unlock();
340 m_WritingToSharedMemory =
false;
345 void EVENTSINTERNAL::EventSharedMemManager::copySharedMemoryToLocalBuffer()
347 void* localBuffer =
static_cast<void*
>(m_LocalBuffer);
348 char* sharedBuffer =
static_cast<char*
>(m_SharedMemory.data()) +
sizeof(
int);
349 if(m_SharedMemory.isAttached())
351 m_SharedMemory.lock();
352 memcpy(localBuffer, sharedBuffer, bufferLength *
sizeof(EventUpdate));
353 m_SharedMemory.unlock();
361 void EVENTSINTERNAL::EventSharedMemManager::bufferWatcher()
363 m_BufferWatcherThreadRunning =
true;
368 copySharedMemoryToLocalBuffer();
369 auto timeCheck = getTimeNow();
370 processLocalBuffer();
371 m_lastCheckTime = timeCheck;
372 std::this_thread::sleep_for(std::chrono::milliseconds(m_fTimerCheckBuffer));
374 m_BufferWatcherThreadRunning =
false;
379 void EVENTSINTERNAL::EventSharedMemManager::processLocalBuffer()
381 for(
int i = 0; i < bufferLength; ++i)
384 if(m_LocalBuffer[i].getCreationTime() > m_lastCheckTime &&
385 m_LocalBuffer[i].getCreatorId() != m_Id )
387 createGroupIfNeeded();
388 processEvent(m_LocalBuffer[i]);
400 case EventUpdateType::NEW_EVENT :
405 case EventUpdateType::DELETE_EVENT :
407 processDeleteEvent(ne);
417 void EVENTSINTERNAL::EventSharedMemManager::processNewEvent(
const EventUpdate& ne)
420 m_pEventManager->generateNewEventId(), ne.
getSample(), m_GroupId);
421 m_pEventManager->insertEvent(newEvent);
426 void EVENTSINTERNAL::EventSharedMemManager::processDeleteEvent(
const EventUpdate& ne)
428 auto eventsInSample = m_pEventManager->getEventsInSample(ne.getSample());
429 for(
auto& e: *eventsInSample)
431 if(e.groupId == m_GroupId)
433 m_pEventManager->eraseEvent(e.id);
443 const auto tNow = std::chrono::system_clock::now();
444 return std::chrono::duration_cast<std::chrono::milliseconds>(
445 tNow.time_since_epoch()).count();
450 void EVENTSINTERNAL::EventSharedMemManager::createGroupIfNeeded()
456 m_bGroupCreated =
true;
462 void EVENTSINTERNAL::EventSharedMemManager::printLocalBuffer()
464 for(
int i = 0; i < bufferLength; ++i)
466 qDebug() <<
"[" << i <<
"] -" << m_LocalBuffer[i].eventTypeToText().c_str()
467 <<
"-" << m_LocalBuffer[i].getSample()
468 <<
"-" << m_LocalBuffer[i].getCreatorId()
469 <<
"-" << m_LocalBuffer[i].getCreationTime() <<
"\n";