#include "StdAfx.h" #include "SMemoryInterface.h" #include "SMacroFile.h" CSMemoryInterface::CSMemoryInterface(int nType, ISMemoryInterface2Parent* pISMI2P, DWORD dwPeriod) : m_nMemoryType(nType), m_pISMI2P(pISMI2P), CSTimerThread(dwPeriod) { m_pSemaPhore = NULL; m_hAsignedMemory = NULL; m_pSharedMemory = NULL; m_dwMemorySize = 0; m_dwSignalDataSize = sizeof(CSSignalData); // clear signal data memset(&m_curSignalData, 0, sizeof(CSSignalData)); memset(&m_prevSignalData, 0, sizeof(CSSignalData)); // alloc send signal thread m_pWorkThread = new CSWorkThread(static_cast(this)); } CSMemoryInterface::~CSMemoryInterface(void) { // delete send signal thread if (m_pWorkThread) { delete m_pWorkThread; m_pWorkThread = NULL; } StopThread(); DeleteMemory(); } void CSMemoryInterface::DeleteMemory() { if(m_pSharedMemory) { UnmapViewOfFile(m_pSharedMemory); m_pSharedMemory = NULL; } if(m_hAsignedMemory) { CloseHandle(m_hAsignedMemory); m_hAsignedMemory = NULL; } if (m_pSemaPhore) { delete m_pSemaPhore; m_pSemaPhore = NULL; } m_dwMemorySize = 0; } BOOL CSMemoryInterface::CreateMemory(DWORD64 dwSize) { DeleteMemory(); m_dwMemorySize = -1; // DWORD max DWORD64 nMaxSize = dwSize + m_dwSignalDataSize; // check size if (nMaxSize>=m_dwMemorySize) { return FALSE; } // set memory size m_dwMemorySize = DWORD(nMaxSize); // set memory name CString strMemoryName = _T(""); switch(m_nMemoryType) { case SMemoryInterface::MemoryType_Control: strMemoryName = _T("MemoryType_Control"); break; case SMemoryInterface::MemoryType_Inspect: strMemoryName = _T("MemoryType_Inspect"); break; case SMemoryInterface::MemoryType_Review: strMemoryName = _T("MemoryType_Review"); break; default: return FALSE; break; } // Create File m_hAsignedMemory = (HANDLE) CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, m_dwMemorySize, strMemoryName); if(m_hAsignedMemory==NULL) { DeleteMemory(); return FALSE; } // Map File m_pSharedMemory = (BYTE *)MapViewOfFile(m_hAsignedMemory, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, 0); if(m_pSharedMemory==NULL) { DeleteMemory(); return FALSE; } // Alloc Semaphore if (m_pSemaPhore) { delete m_pSemaPhore; m_pSemaPhore = NULL; } m_pSemaPhore = new CSemaphore(1, 1, strMemoryName); if (m_pSemaPhore==NULL) { DeleteMemory(); return FALSE; } return TRUE; } BOOL CSMemoryInterface::LockMemory() { if (m_pSemaPhore==NULL) return FALSE; return m_pSemaPhore->Lock(); } BOOL CSMemoryInterface::UnlockMemory() { if (m_pSemaPhore==NULL) return FALSE; return m_pSemaPhore->Unlock(); } BOOL CSMemoryInterface::StartThread() { if (m_pISMI2P==NULL) return FALSE; return CreateTimerThread(this); } void CSMemoryInterface::StopThread() { CSTimerThread::StopThread(); } LPVOID CSMemoryInterface::GetMemoryAddress(DWORD dwAddress) { if (m_pSharedMemory==NULL) return NULL; if (dwAddress >= m_dwMemorySize) return NULL; return &(m_pSharedMemory[dwAddress]); } const LPVOID CSMemoryInterface::GetMemoryAddress(DWORD dwAddress) const { if (m_pSharedMemory==NULL) return NULL; if (dwAddress >= m_dwMemorySize) return NULL; return &(m_pSharedMemory[dwAddress]); } LPVOID CSMemoryInterface::GetMemoryData( DWORD dwAddress ) { return GetMemoryAddress(m_dwSignalDataSize+dwAddress); } const LPVOID CSMemoryInterface::GetMemoryData( DWORD dwAddress ) const { return GetMemoryAddress(m_dwSignalDataSize+dwAddress); } const LPVOID CSMemoryInterface::GetSignalData() const { return GetMemoryAddress(0); } const BOOL CSMemoryInterface::GetSignalData(int nSignalType, int nSignalIndex, BOOL& bValue) const { if (nSignalType<0 || nSignalType>=MAX_SIGNAL_TYPE_COUNT) return FALSE; if (nSignalIndex<0 || nSignalIndex>=MAX_SIGNAL_INDEX_COUNT) return FALSE; const CSSignalData* pData = static_cast(GetSignalData()); if (pData==NULL) return FALSE; DWORD64 dwCurValue = pData->m_dwSendSignal[nSignalType]; DWORD64 dwBitValue = 1 << nSignalIndex; bValue = ( ( dwCurValue & dwBitValue ) == dwBitValue ) ? TRUE : FALSE; return TRUE; } BOOL CSMemoryInterface::ClearSignalData() { CSSignalData *pData = static_cast(GetMemoryAddress(0)); if (pData==NULL) return FALSE; LockMemory(); memset(pData, 0, sizeof(CSSignalData)); memset(&m_curSignalData, 0, sizeof(CSSignalData)); memset(&m_prevSignalData, 0, sizeof(CSSignalData)); UnlockMemory(); return TRUE; } BOOL CSMemoryInterface::SendSignal(int nSignalType, int nSignalIndex, int nSignalValue) { if (nSignalType<0 || nSignalType>=MAX_SIGNAL_TYPE_COUNT) return FALSE; if (nSignalIndex<0 || nSignalIndex>=MAX_SIGNAL_INDEX_COUNT) return FALSE; CSSignalData* pData = static_cast(GetMemoryAddress(0)); if (pData==NULL) return FALSE; LockMemory(); DWORD64 nBitValue = 1 << nSignalIndex; if (nSignalValue) { pData->m_dwSendSignal[nSignalType] = pData->m_dwSendSignal[nSignalType] | nBitValue; } else { pData->m_dwSendSignal[nSignalType] = pData->m_dwSendSignal[nSignalType] & (~nBitValue); } UnlockMemory(); return TRUE; } void CSMemoryInterface::ISWT2P_ProcessSendSignalData(int nSignalType, int nSignalIndex, int nSignalValue, DWORD dwDelayTime, DWORD dwHoldTime) { // send ::Sleep(dwDelayTime); if (SendSignal(nSignalType, nSignalIndex, nSignalValue)==FALSE) { return; } // clear (1->0) (0->1) ::Sleep(dwHoldTime); if (SendSignal(nSignalType, nSignalIndex, !nSignalValue)==FALSE) { return; } } BOOL CSMemoryInterface::SendSignal( int nSignalType, int nSignalIndex, int nValue, DWORD dwDelayTime, DWORD dwHoldTime ) { if (m_pWorkThread==NULL) return FALSE; return m_pWorkThread->AddThreadData(nSignalType, nSignalIndex, nValue, dwDelayTime, dwHoldTime); } void CSMemoryInterface::TimerThreadProcess(PVOID pParameter) { if (m_pISMI2P==NULL) return; const CSSignalData* pData = static_cast(GetSignalData()); if (pData==NULL) return; // save cur signal m_curSignalData = *pData; // check prev signal for (int nSignalType=0; nSignalTypeISMI2P_SendSignalValue(m_nMemoryType, nSignalType, nSignalIdx, bCurValue); } dwBitValue = dwBitValue << 1; } } } // save current signal m_prevSignalData = m_curSignalData; }