From c842fa175cdda0331567ea6f06e7084ceb51d260 Mon Sep 17 00:00:00 2001 From: George Hazan Date: Tue, 13 Jan 2015 21:33:15 +0000 Subject: well, everything works but events git-svn-id: http://svn.miranda-ng.org/main/trunk@11850 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- plugins/Dbx_mdb/src/commonheaders.h | 12 ++++-- plugins/Dbx_mdb/src/dbcontacts.cpp | 20 ++++++---- plugins/Dbx_mdb/src/dbintf.cpp | 38 +++++++++--------- plugins/Dbx_mdb/src/dbintf.h | 3 +- plugins/Dbx_mdb/src/dbmodulechain.cpp | 11 ++++-- plugins/Dbx_mdb/src/dbsettings.cpp | 74 ++++++++++++++++++----------------- 6 files changed, 88 insertions(+), 70 deletions(-) (limited to 'plugins/Dbx_mdb') diff --git a/plugins/Dbx_mdb/src/commonheaders.h b/plugins/Dbx_mdb/src/commonheaders.h index ecc4347629..7b0c0bc0ad 100644 --- a/plugins/Dbx_mdb/src/commonheaders.h +++ b/plugins/Dbx_mdb/src/commonheaders.h @@ -59,10 +59,13 @@ extern LIST g_Dbs; class txn_lock { MDB_txn *txn; + MDB_env *env; public: - __forceinline txn_lock(MDB_env *pEnv) - { mdb_txn_begin(pEnv, NULL, 0, &txn); + __forceinline txn_lock(MDB_env *pEnv) : + env(pEnv) + { + mdb_txn_begin(pEnv, NULL, 0, &txn); } __forceinline ~txn_lock() @@ -73,10 +76,11 @@ public: __forceinline operator MDB_txn*() const { return txn; } - __forceinline void commit() + __forceinline bool commit() { - mdb_txn_commit(txn); + bool bRes = (mdb_txn_commit(txn) != MDB_MAP_FULL); txn = NULL; + return bRes; } __forceinline void abort() diff --git a/plugins/Dbx_mdb/src/dbcontacts.cpp b/plugins/Dbx_mdb/src/dbcontacts.cpp index b02c4cb596..0a6e6859f1 100644 --- a/plugins/Dbx_mdb/src/dbcontacts.cpp +++ b/plugins/Dbx_mdb/src/dbcontacts.cpp @@ -89,10 +89,12 @@ STDMETHODIMP_(LONG) CDbxMdb::DeleteContact(MCONTACT contactID) MDB_val key = { sizeof(DWORD), &contactID }; - txn_lock trnlck(m_pMdbEnv); - mdb_open(trnlck, "contacts", MDB_INTEGERKEY, &m_dbContacts); - mdb_del(trnlck, m_dbContacts, &key, NULL); - trnlck.commit(); + for (;; Remap()) { + txn_lock trnlck(m_pMdbEnv); + mdb_del(trnlck, m_dbContacts, &key, NULL); + if (trnlck.commit()) + break; + } return 0; } @@ -110,10 +112,12 @@ STDMETHODIMP_(MCONTACT) CDbxMdb::AddContact() MDB_val key = { sizeof(DWORD), &dwContactId }; MDB_val data = { sizeof(DBContact), &dbc }; - txn_lock trnlck(m_pMdbEnv); - mdb_open(trnlck, "contacts", MDB_INTEGERKEY, &m_dbContacts); - mdb_put(trnlck, m_dbContacts, &key, &data, 0); - trnlck.commit(); + for (;; Remap()) { + txn_lock trnlck(m_pMdbEnv); + mdb_put(trnlck, m_dbContacts, &key, &data, 0); + if (trnlck.commit()) + break; + } DBCachedContact *cc = m_cache->AddContactToCache(dwContactId); cc->dwDriverData = 0; diff --git a/plugins/Dbx_mdb/src/dbintf.cpp b/plugins/Dbx_mdb/src/dbintf.cpp index 52e5083e75..b889ea8f5b 100644 --- a/plugins/Dbx_mdb/src/dbintf.cpp +++ b/plugins/Dbx_mdb/src/dbintf.cpp @@ -51,7 +51,6 @@ CDbxMdb::CDbxMdb(const TCHAR *tszFileName, int iMode) : InitDbInstance(this); mdb_env_create(&m_pMdbEnv); - mdb_env_set_mapsize(m_pMdbEnv, 65536); mdb_env_set_maxdbs(m_pMdbEnv, 10); m_codePage = CallService(MS_LANGPACK_GETCODEPAGE, 0, 0); @@ -86,13 +85,7 @@ CDbxMdb::~CDbxMdb() int CDbxMdb::Load(bool bSkipInit) { - int mode = MDB_NOSYNC | MDB_NOSUBDIR; - if (m_bReadOnly) - mode += MDB_RDONLY; - else - mode += MDB_WRITEMAP; - - if (mdb_env_open(m_pMdbEnv, _T2A(m_tszProfileName), mode, 0664) != 0) + if (!Remap()) return EGROKPRF_CANTREAD; if (!bSkipInit) { @@ -129,16 +122,8 @@ int CDbxMdb::Load(bool bSkipInit) int CDbxMdb::Create(void) { - int mode = MDB_NOSYNC | MDB_NOSUBDIR; - if (m_bReadOnly) - mode += MDB_RDONLY; - else - mode += MDB_WRITEMAP; - - if (mdb_env_open(m_pMdbEnv, _T2A(m_tszProfileName), mode, 0664) != 0) - return EGROKPRF_CANTREAD; - - return 0; + m_dwFileSize = 0; + return (Remap()) ? 0 : EGROKPRF_CANTREAD; } int CDbxMdb::Check(void) @@ -147,6 +132,10 @@ int CDbxMdb::Check(void) if (hFile == INVALID_HANDLE_VALUE) return EGROKPRF_CANTREAD; + LARGE_INTEGER iFileSize; + GetFileSizeEx(hFile, &iFileSize); + m_dwFileSize = (iFileSize.LowPart & 0xFFFFF000); + DWORD dummy = 0; char buf[32]; if (!ReadFile(hFile, buf, sizeof(buf), &dummy, NULL)) { @@ -170,6 +159,19 @@ STDMETHODIMP_(void) CDbxMdb::SetCacheSafetyMode(BOOL bIsSet) m_safetyMode = bIsSet != 0; } +bool CDbxMdb::Remap() +{ + m_dwFileSize += 0x100000; + mdb_env_set_mapsize(m_pMdbEnv, m_dwFileSize); + + int mode = MDB_NOSYNC | MDB_NOSUBDIR; + if (m_bReadOnly) + mode += MDB_RDONLY; + else + mode += MDB_WRITEMAP; + return mdb_env_open(m_pMdbEnv, _T2A(m_tszProfileName), mode, 0664) == MDB_SUCCESS; +} + ///////////////////////////////////////////////////////////////////////////////////////// static DWORD DatabaseCorrupted = 0; diff --git a/plugins/Dbx_mdb/src/dbintf.h b/plugins/Dbx_mdb/src/dbintf.h index 78507969df..e83f559634 100644 --- a/plugins/Dbx_mdb/src/dbintf.h +++ b/plugins/Dbx_mdb/src/dbintf.h @@ -197,7 +197,7 @@ protected: void FillContacts(void); - void Map(); + bool Remap(); public: // Check functions int WorkInitialChecks(int); @@ -218,6 +218,7 @@ public: protected: MDB_env *m_pMdbEnv; + DWORD m_dwFileSize; HANDLE hSettingChangeEvent, hContactDeletedEvent, hContactAddedEvent, hEventMarkedRead; diff --git a/plugins/Dbx_mdb/src/dbmodulechain.cpp b/plugins/Dbx_mdb/src/dbmodulechain.cpp index 4643a2d295..a54d7ab2f9 100644 --- a/plugins/Dbx_mdb/src/dbmodulechain.cpp +++ b/plugins/Dbx_mdb/src/dbmodulechain.cpp @@ -103,10 +103,13 @@ DWORD CDbxMdb::GetModuleNameOfs(const char *szName) MDB_val key = { sizeof(int), &newIdx }, data = { sizeof(DBModuleName) + nameLen, pmod }; - txn_lock trnlck(m_pMdbEnv); - mdb_open(trnlck, "modules", MDB_INTEGERKEY, &m_dbModules); - mdb_put(trnlck, m_dbModules, &key, &data, 0); - trnlck.commit(); + for (;; Remap()) { + txn_lock trnlck(m_pMdbEnv); + mdb_open(trnlck, "modules", MDB_INTEGERKEY, &m_dbModules); + mdb_put(trnlck, m_dbModules, &key, &data, 0); + if (trnlck.commit()) + break; + } // add to cache char *mod = (char*)HeapAlloc(m_hModHeap, 0, nameLen + 1); diff --git a/plugins/Dbx_mdb/src/dbsettings.cpp b/plugins/Dbx_mdb/src/dbsettings.cpp index c4eaaad098..c345c42174 100644 --- a/plugins/Dbx_mdb/src/dbsettings.cpp +++ b/plugins/Dbx_mdb/src/dbsettings.cpp @@ -473,9 +473,6 @@ STDMETHODIMP_(BOOL) CDbxMdb::WriteContactSetting(MCONTACT contactID, DBCONTACTWR } else m_cache->GetCachedValuePtr(contactID, szCachedSettingName, -1); - txn_lock trnlck(m_pMdbEnv); - //mdb_open(trnlck, "settings", 0, &m_dbSettings); - DBSettingKey keySearch; keySearch.dwContactID = contactID; keySearch.dwOfsModule = GetModuleNameOfs(dbcws->szModule); @@ -497,31 +494,35 @@ STDMETHODIMP_(BOOL) CDbxMdb::WriteContactSetting(MCONTACT contactID, DBCONTACTWR data.mv_size = 3 + dbcwWork.value.cpbVal; break; } - if (mdb_put(trnlck, m_dbSettings, &key, &data, MDB_RESERVE) != 0) - return 1; - - BYTE *pBlob = (BYTE*)data.mv_data; - *pBlob++ = dbcwWork.value.type; - switch (dbcwWork.value.type) { - case DBVT_BYTE: *pBlob = dbcwWork.value.bVal; break; - case DBVT_WORD: *(WORD*)pBlob = dbcwWork.value.wVal; break; - case DBVT_DWORD: *(DWORD*)pBlob = dbcwWork.value.dVal; break; + for (;; Remap()) { + txn_lock trnlck(m_pMdbEnv); + if (mdb_put(trnlck, m_dbSettings, &key, &data, MDB_RESERVE) != 0) + return 1; - case DBVT_ASCIIZ: - case DBVT_UTF8: - data.mv_size = *(WORD*)pBlob = dbcwWork.value.cchVal; - pBlob += 2; - memcpy(pBlob, dbcwWork.value.pszVal, dbcwWork.value.cchVal); - break; + BYTE *pBlob = (BYTE*)data.mv_data; + *pBlob++ = dbcwWork.value.type; + switch (dbcwWork.value.type) { + case DBVT_BYTE: *pBlob = dbcwWork.value.bVal; break; + case DBVT_WORD: *(WORD*)pBlob = dbcwWork.value.wVal; break; + case DBVT_DWORD: *(DWORD*)pBlob = dbcwWork.value.dVal; break; + + case DBVT_ASCIIZ: + case DBVT_UTF8: + data.mv_size = *(WORD*)pBlob = dbcwWork.value.cchVal; + pBlob += 2; + memcpy(pBlob, dbcwWork.value.pszVal, dbcwWork.value.cchVal); + break; + + case DBVT_BLOB: + case DBVT_ENCRYPTED: + data.mv_size = *(WORD*)pBlob = dbcwWork.value.cpbVal; + pBlob += 2; + memcpy(pBlob, dbcwWork.value.pbVal, dbcwWork.value.cpbVal); + } - case DBVT_BLOB: - case DBVT_ENCRYPTED: - data.mv_size = *(WORD*)pBlob = dbcwWork.value.cpbVal; - pBlob += 2; - memcpy(pBlob, dbcwWork.value.pbVal, dbcwWork.value.cpbVal); + if (trnlck.commit()) + break; } - - trnlck.commit(); lck.unlock(); // notify @@ -555,19 +556,21 @@ STDMETHODIMP_(BOOL) CDbxMdb::DeleteContactSetting(MCONTACT contactID, LPCSTR szM mir_cslock lck(m_csDbAccess); char *szCachedSettingName = m_cache->GetCachedSetting(szModule, szSetting, moduleNameLen, settingNameLen); if (szCachedSettingName[-1] == 0) { // it's not a resident variable - txn_lock trnlck(m_pMdbEnv); - //mdb_open(trnlck, "settings", 0, &m_dbSettings); - DBSettingKey keySearch; keySearch.dwContactID = contactID; keySearch.dwOfsModule = GetModuleNameOfs(szModule); strncpy_s(keySearch.szSettingName, szSetting, _TRUNCATE); MDB_val key = { 2 * sizeof(DWORD) + settingNameLen, &keySearch }, data; - if (mdb_del(trnlck, m_dbSettings, &key, &data)) - return 1; - trnlck.commit(); + for (;; Remap()) { + txn_lock trnlck(m_pMdbEnv); + if (mdb_del(trnlck, m_dbSettings, &key, &data)) + return 1; + + if (trnlck.commit()) + break; + } } m_cache->GetCachedValuePtr(saveContact, szCachedSettingName, -1); @@ -593,7 +596,7 @@ STDMETHODIMP_(BOOL) CDbxMdb::EnumContactSettings(MCONTACT contactID, DBCONTACTEN DBSettingKey keySearch; keySearch.dwContactID = contactID; keySearch.dwOfsModule = GetModuleNameOfs(dbces->szModule); - keySearch.szSettingName[0] = 0; + memset(keySearch.szSettingName, 0, SIZEOF(keySearch.szSettingName)); LIST arSettings(50); @@ -601,9 +604,9 @@ STDMETHODIMP_(BOOL) CDbxMdb::EnumContactSettings(MCONTACT contactID, DBCONTACTEN MDB_cursor *cursor; mdb_cursor_open(trnlck, m_dbSettings, &cursor); - MDB_val key = { 2 * sizeof(DWORD), &keySearch }, data; - mdb_cursor_get(cursor, &key, &data, MDB_SET_KEY); - while (mdb_cursor_get(cursor, &key, &data, MDB_NEXT) == 0) { + MDB_val key = { sizeof(keySearch), &keySearch }, data; + mdb_cursor_get(cursor, &key, &data, MDB_SET_RANGE); + do { DBSettingKey *pKey = (DBSettingKey*)key.mv_data; if (pKey->dwContactID != contactID || pKey->dwOfsModule != keySearch.dwOfsModule) break; @@ -612,6 +615,7 @@ STDMETHODIMP_(BOOL) CDbxMdb::EnumContactSettings(MCONTACT contactID, DBCONTACTEN strncpy_s(szSetting, pKey->szSettingName, key.mv_size - sizeof(DWORD)*2); arSettings.insert(mir_strdup(szSetting)); } + while (mdb_cursor_get(cursor, &key, &data, MDB_NEXT) == 0); mdb_cursor_close(cursor); for (int i = 0; i < arSettings.getCount(); i++) { -- cgit v1.2.3