From 15267ea2d489606fb4b99d011bc3ea7c2a644a9f Mon Sep 17 00:00:00 2001 From: George Hazan Date: Sun, 17 Mar 2013 14:22:17 +0000 Subject: fix for popup-related memory leaks git-svn-id: http://svn.miranda-ng.org/main/trunk@4077 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- plugins/YAPP/src/options.cpp | 71 ++++++++++++++++++++++--------------------- plugins/YAPP/src/services.cpp | 54 +++++++++++++++++++++----------- plugins/YAPP/src/services.h | 3 +- 3 files changed, 73 insertions(+), 55 deletions(-) (limited to 'plugins/YAPP/src') diff --git a/plugins/YAPP/src/options.cpp b/plugins/YAPP/src/options.cpp index e8f06ceea2..182504ac21 100644 --- a/plugins/YAPP/src/options.cpp +++ b/plugins/YAPP/src/options.cpp @@ -346,26 +346,24 @@ static INT_PTR CALLBACK DlgProcOpts1(HWND hwndDlg, UINT msg, WPARAM wParam, LPAR return 0; } -POPUPCLASS *newclasses = 0; +LIST arNewClasses(3); + static INT_PTR CALLBACK DlgProcOptsClasses(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam) { switch ( msg ) { case WM_INITDIALOG: TranslateDialogDefault( hwndDlg ); - if (num_classes) { - newclasses = (POPUPCLASS *)mir_alloc(num_classes * sizeof(POPUPCLASS)); - memcpy(newclasses, classes, num_classes * sizeof(POPUPCLASS)); - - POPUPCLASS *pc; + arNewClasses = arClasses; + { int index; - for (int i = 0; i < num_classes; i++) { - pc = &newclasses[i]; - if (pc->flags & PCF_UNICODE) { + for (int i = 0; i < arNewClasses.getCount(); i++) { + POPUPCLASS *pc = arNewClasses[i]; + if (pc->flags & PCF_UNICODE) index = SendDlgItemMessageW(hwndDlg, IDC_LST_CLASSES, LB_ADDSTRING, 0, (LPARAM)pc->pwszDescription); - } else { + else index = SendDlgItemMessageA(hwndDlg, IDC_LST_CLASSES, LB_ADDSTRING, 0, (LPARAM)pc->pszDescription); - } + SendDlgItemMessage(hwndDlg, IDC_LST_CLASSES, LB_SETITEMDATA, index, i); } } @@ -380,24 +378,26 @@ static INT_PTR CALLBACK DlgProcOptsClasses(HWND hwndDlg, UINT msg, WPARAM wParam EnableWindow(GetDlgItem(hwndDlg, IDC_CHK_TIMEOUT), index != -1); if (index != -1) { int i = SendDlgItemMessage(hwndDlg, IDC_LST_CLASSES, LB_GETITEMDATA, index, 0); - SendDlgItemMessage(hwndDlg, IDC_COL_TEXT, CPM_SETCOLOUR, 0, (LPARAM)newclasses[i].colorText); - SendDlgItemMessage(hwndDlg, IDC_COL_BG, CPM_SETCOLOUR, 0, (LPARAM)newclasses[i].colorBack); - CheckDlgButton(hwndDlg, IDC_CHK_TIMEOUT, newclasses[i].iSeconds != -1); - SetDlgItemInt(hwndDlg, IDC_ED_TIMEOUT, newclasses[i].iSeconds, TRUE); + SendDlgItemMessage(hwndDlg, IDC_COL_TEXT, CPM_SETCOLOUR, 0, (LPARAM)arNewClasses[i]->colorText); + SendDlgItemMessage(hwndDlg, IDC_COL_BG, CPM_SETCOLOUR, 0, (LPARAM)arNewClasses[i]->colorBack); + CheckDlgButton(hwndDlg, IDC_CHK_TIMEOUT, arNewClasses[i]->iSeconds != -1); + SetDlgItemInt(hwndDlg, IDC_ED_TIMEOUT, arNewClasses[i]->iSeconds, TRUE); } EnableWindow(GetDlgItem(hwndDlg, IDC_ED_TIMEOUT), index != -1 && IsDlgButtonChecked(hwndDlg, IDC_CHK_TIMEOUT)); return TRUE; - } else if ( HIWORD( wParam ) == EN_CHANGE && ( HWND )lParam == GetFocus()) { + } + if ( HIWORD( wParam ) == EN_CHANGE && ( HWND )lParam == GetFocus()) { int index = SendDlgItemMessage(hwndDlg, IDC_LST_CLASSES, LB_GETCURSEL, 0, 0); if (index != -1) { int i = SendDlgItemMessage(hwndDlg, IDC_LST_CLASSES, LB_GETITEMDATA, index, 0); BOOL tr; int t = GetDlgItemInt(hwndDlg, IDC_ED_TIMEOUT, &tr, FALSE); - newclasses[i].iSeconds = t; + arNewClasses[i]->iSeconds = t; SendMessage(GetParent(hwndDlg), PSM_CHANGED, 0, 0); } - } else { + } + else { int index = SendDlgItemMessage(hwndDlg, IDC_LST_CLASSES, LB_GETCURSEL, 0, 0); if (index != -1) { int i = SendDlgItemMessage(hwndDlg, IDC_LST_CLASSES, LB_GETITEMDATA, index, 0); @@ -406,33 +406,33 @@ static INT_PTR CALLBACK DlgProcOptsClasses(HWND hwndDlg, UINT msg, WPARAM wParam { BOOL isChecked = IsDlgButtonChecked(hwndDlg, IDC_CHK_TIMEOUT); EnableWindow(GetDlgItem(hwndDlg, IDC_ED_TIMEOUT), isChecked); - if (isChecked) newclasses[i].iSeconds = 0; - else newclasses[i].iSeconds = -1; - SetDlgItemInt(hwndDlg, IDC_ED_TIMEOUT, newclasses[i].iSeconds, TRUE); + if (isChecked) arNewClasses[i]->iSeconds = 0; + else arNewClasses[i]->iSeconds = -1; + SetDlgItemInt(hwndDlg, IDC_ED_TIMEOUT, arNewClasses[i]->iSeconds, TRUE); } SendMessage( GetParent( hwndDlg ), PSM_CHANGED, 0, 0 ); break; case IDC_COL_TEXT: - newclasses[i].colorText = SendDlgItemMessage(hwndDlg, IDC_COL_TEXT, CPM_GETCOLOUR, 0, 0); + arNewClasses[i]->colorText = SendDlgItemMessage(hwndDlg, IDC_COL_TEXT, CPM_GETCOLOUR, 0, 0); SendMessage( GetParent( hwndDlg ), PSM_CHANGED, 0, 0 ); break; case IDC_COL_BG: - newclasses[i].colorBack = SendDlgItemMessage(hwndDlg, IDC_COL_BG, CPM_GETCOLOUR, 0, 0); + arNewClasses[i]->colorBack = SendDlgItemMessage(hwndDlg, IDC_COL_BG, CPM_GETCOLOUR, 0, 0); SendMessage( GetParent( hwndDlg ), PSM_CHANGED, 0, 0 ); break; case IDC_BTN_PREVIEW: - if (newclasses[i].flags & PCF_UNICODE) { - POPUPCLASS pc = newclasses[i]; + if (arNewClasses[i]->flags & PCF_UNICODE) { + POPUPCLASS pc = *arNewClasses[i]; pc.PluginWindowProc = 0; POPUPDATACLASS d = {sizeof(d), pc.pszName}; d.pwszTitle = L"Preview"; d.pwszText = L"The quick brown fox jumps over the lazy dog."; CallService(MS_POPUP_ADDPOPUPCLASS, (WPARAM)&pc, (LPARAM)&d); } else { - POPUPCLASS pc = newclasses[i]; + POPUPCLASS pc = *arNewClasses[i]; pc.PluginWindowProc = 0; POPUPDATACLASS d = {sizeof(d), pc.pszName}; d.pszTitle = "Preview"; @@ -447,22 +447,23 @@ static INT_PTR CALLBACK DlgProcOptsClasses(HWND hwndDlg, UINT msg, WPARAM wParam case WM_NOTIFY: if (((LPNMHDR)lParam)->code == (unsigned)PSN_APPLY ) { - memcpy(classes, newclasses, num_classes * sizeof(POPUPCLASS)); + arClasses = arNewClasses; char setting[256]; - for (int i = 0; i < num_classes; i++) { - mir_snprintf(setting, 256, "%s/Timeout", classes[i].pszName); - DBWriteContactSettingWord(0, MODULE, setting, classes[i].iSeconds); - mir_snprintf(setting, 256, "%s/TextCol", classes[i].pszName); - db_set_dw(0, MODULE, setting, (DWORD)classes[i].colorText); - mir_snprintf(setting, 256, "%s/BgCol", classes[i].pszName); - db_set_dw(0, MODULE, setting, (DWORD)classes[i].colorBack); + for (int i = 0; i < arClasses.getCount(); i++) { + POPUPCLASS *pc = arClasses[i]; + mir_snprintf(setting, 256, "%s/Timeout", pc->pszName); + DBWriteContactSettingWord(0, MODULE, setting, pc->iSeconds); + mir_snprintf(setting, 256, "%s/TextCol", pc->pszName); + db_set_dw(0, MODULE, setting, (DWORD)pc->colorText); + mir_snprintf(setting, 256, "%s/BgCol", pc->pszName); + db_set_dw(0, MODULE, setting, (DWORD)pc->colorBack); } return TRUE; } break; case WM_DESTROY: - mir_free(newclasses); + arNewClasses.destroy(); break; } return 0; diff --git a/plugins/YAPP/src/services.cpp b/plugins/YAPP/src/services.cpp index 2a22a6d99e..4848788544 100644 --- a/plugins/YAPP/src/services.cpp +++ b/plugins/YAPP/src/services.cpp @@ -299,15 +299,12 @@ INT_PTR PopUp_ShowHistory(WPARAM wParam, LPARAM lParam) return 0; } -int num_classes = 0; -POPUPCLASS *classes = 0; +LIST arClasses(3); static INT_PTR RegisterPopupClass(WPARAM wParam, LPARAM lParam) { - classes = (POPUPCLASS *)mir_realloc(classes, sizeof(POPUPCLASS) * (num_classes + 1)); - memcpy(classes + num_classes, (PVOID)lParam, sizeof(POPUPCLASS)); - POPUPCLASS *pc = classes + num_classes; - num_classes++; + POPUPCLASS *pc = (POPUPCLASS*)mir_alloc( sizeof(POPUPCLASS)); + memcpy(pc, (PVOID)lParam, sizeof(POPUPCLASS)); pc->pszName = mir_strdup(pc->pszName); if (pc->flags & PCF_UNICODE) @@ -324,7 +321,31 @@ static INT_PTR RegisterPopupClass(WPARAM wParam, LPARAM lParam) mir_snprintf(setting, 256, "%s/BgCol", pc->pszName); pc->colorBack = (COLORREF)db_get_dw(0, MODULE, setting, (DWORD)pc->colorBack); - return 0; + arClasses.insert(pc); + return (INT_PTR)pc; +} + +static void FreePopupClass(POPUPCLASS *pc) +{ + mir_free(pc->pszName); + mir_free(pc->pszDescription); + mir_free(pc); +} + +static INT_PTR UnregisterPopupClass(WPARAM wParam, LPARAM lParam) +{ + POPUPCLASS *pc = (POPUPCLASS*)lParam; + if (pc == NULL) + return 1; + + for (int i=0; i < arClasses.getCount(); i++) + if (arClasses[i] == pc) { + arClasses.remove(i); + FreePopupClass(pc); + return 0; + } + + return 1; } static INT_PTR CreateClassPopup(WPARAM wParam, LPARAM lParam) @@ -336,9 +357,9 @@ static INT_PTR CreateClassPopup(WPARAM wParam, LPARAM lParam) if (wParam) pc = (POPUPCLASS *)wParam; else { - for (int i = 0; i < num_classes; i++) { - if (strcmp(classes[i].pszName, pdc->pszClassName) == 0) { - pc = &classes[i]; + for (int i = 0; i < arClasses.getCount(); i++) { + if ( strcmp(arClasses[i]->pszName, pdc->pszClassName) == 0) { + pc = arClasses[i]; break; } } @@ -367,6 +388,8 @@ static INT_PTR CreateClassPopup(WPARAM wParam, LPARAM lParam) void InitServices() { CreateServiceFunction(MS_POPUP_REGISTERCLASS, RegisterPopupClass); + CreateServiceFunction(MS_POPUP_UNREGISTERCLASS, UnregisterPopupClass); + CreateServiceFunction(MS_POPUP_ADDPOPUPCLASS, CreateClassPopup); CreateServiceFunction(MS_POPUP_ADDPOPUP, CreatePopup); CreateServiceFunction(MS_POPUP_ADDPOPUPW, CreatePopupW); @@ -383,9 +406,6 @@ void InitServices() CreateServiceFunction(MS_POPUP_SHOWHISTORY, PopUp_ShowHistory); CreateServiceFunction("PopUp/ToggleEnabled", TogglePopups); - CreateServiceFunction("YAPP/RegisterClass", RegisterPopupClass); - CreateServiceFunction("YAPP/ClassInstance", CreateClassPopup); - //////////////////////////////////////////////////////////////////////////// // Menus @@ -408,9 +428,7 @@ void InitServices() void DeinitServices() { - for (int i = 0; i < num_classes; i++) { - mir_free(classes[i].pszName); - mir_free(classes[i].pszDescription); - } - mir_free(classes); num_classes = 0; + for (int i = 0; i < arClasses.getCount(); i++) + FreePopupClass(arClasses[i]); + arClasses.destroy(); } diff --git a/plugins/YAPP/src/services.h b/plugins/YAPP/src/services.h index 8243b0ba8b..91e9500b02 100644 --- a/plugins/YAPP/src/services.h +++ b/plugins/YAPP/src/services.h @@ -4,7 +4,6 @@ void InitServices(); void DeinitServices(); -extern int num_classes; -extern POPUPCLASS *classes; +extern LIST arClasses; #endif -- cgit v1.2.3