Странное поведение DeleteAllItems в СTreeControl
От: _devdi_  
Дата: 08.02.06 18:49
Оценка:
1. Есть три контрол на диалоге с кучей айтемов (около 60)
2. после выбора айтема вызывается диалговое окошко для редактирования данных
3. после нажатия ок вызывается т_Tree.DeleteAllItems() и дерево заполняется новыми элементами

4. Самое интересное. в 1 случае из 5 происходит падение с access violation в comctl32.dll

Подозрение падает именно на DeleteAllItems ибо при удалении три контрола и создании нового вместо удаления всех элементов бага не проявляется.
Поиск в групсах в гугле выдал несколько ссылок на похожую проблему однако на эти посты никто не ответил.

Может кто-нить встречался с чем — то похожим?

Буду признателен за любую помощь
Re: Странное поведение DeleteAllItems в СTreeControl
От: Аноним  
Дата: 08.02.06 19:58
Оценка:
Здравствуйте, _devdi_, Вы писали:

Ваш баг, где-нибудь память портите.
Re: Странное поведение DeleteAllItems в СTreeControl
От: VladFein США  
Дата: 08.02.06 20:02
Оценка:
Здравствуйте, _devdi_, Вы писали:

__>1. Есть три контрол на диалоге с кучей айтемов (около 60)

__>2. после выбора айтема вызывается диалговое окошко для редактирования данных
__>3. после нажатия ок вызывается т_Tree.DeleteAllItems() и дерево заполняется новыми элементами

__>4. Самое интересное. в 1 случае из 5 происходит падение с access violation в comctl32.dll


__>Подозрение падает именно на DeleteAllItems ибо при удалении три контрола и создании нового вместо удаления всех элементов бага не проявляется.

__>Поиск в групсах в гугле выдал несколько ссылок на похожую проблему однако на эти посты никто не ответил.

__>Может кто-нить встречался с чем — то похожим?


__>Буду признателен за любую помощь

В первую очередь я бы посоветовал проанализировать Ваш код (или покажите здесь).
Как Вы обрабатываете TVN_DELETEITEM? Как освобождаете память?
И почему "подозрение"? Что показывает debugger?
P.S. 60 — это еще не куча.
Re[2]: Странное поведение DeleteAllItems в СTreeControl
От: _devdi_  
Дата: 08.02.06 20:43
Оценка:
Здравствуйте, VladFein, Вы писали:

VF>Как Вы обрабатываете TVN_DELETEITEM? Как освобождаете память?

Никак не обрабатываю (дефалтовый обработчик).
Всмысле освобождаю? Немного недопонял вопроса
VF>И почему "подозрение"? Что показывает debugger?
скажите что именно нужно.
Re[3]: Странное поведение DeleteAllItems в СTreeControl
От: VladFein США  
Дата: 08.02.06 20:52
Оценка:
Здравствуйте, _devdi_, Вы писали:

VF>>И почему "подозрение"? Что показывает debugger?

__>скажите что именно нужно.
Call Stack после access violation
Если программа небольшая — поместите здесь. Посмотрим что там падает.
Re[4]: Странное поведение DeleteAllItems в СTreeControl
От: _devdi_  
Дата: 09.02.06 15:08
Оценка:
Здравствуйте, VladFein, Вы писали:

VF>Здравствуйте, _devdi_, Вы писали:


VF>>>И почему "подозрение"? Что показывает debugger?

__>>скажите что именно нужно.
VF>Call Stack после access violation
VF>Если программа небольшая — поместите здесь. Посмотрим что там падает.

Итак Call Stack после падения:

    comctl32.dll!CreateToolbar() + 0xa5aa
    comctl32.dll!CreateStatusWindow() + 0x1fa6
    comctl32.dll!CreateStatusWindow() + 0x2d68
    comctl32.dll!CreateStatusWindow() + 0x4063
    USER32.DLL!SetWindowPlacement() + 0x50
    USER32.DLL!ScreenToClient() + 0xd5
    USER32.DLL!CallWindowProcA() + 0x19
    mfc71d.dll!CWnd::DefWindowProcA(unsigned int nMsg=515, unsigned int wParam=1, long lParam=8650816) Line 1024 + 0x20 C++
    mfc71d.dll!CWnd::WindowProc(unsigned int message=515, unsigned int wParam=1, long lParam=8650816) Line 1746 + 0x1a C++
    mfc71d.dll!AfxCallWndProc(CWnd * pWnd=0x0012f7fc, HWND__ * hWnd=0x00270e14, unsigned int nMsg=515, unsigned int wParam=1, long lParam=8650816) Line 241 + 0x1a C++
    mfc71d.dll!AfxWndProc(HWND__ * hWnd=0x00270e14, unsigned int nMsg=515, unsigned int wParam=1, long lParam=8650816) Line 389 C++
    mfc71d.dll!AfxWndProcBase(HWND__ * hWnd=0x00270e14, unsigned int nMsg=515, unsigned int wParam=1, long lParam=8650816) Line 209 + 0x15 C++
    ...
Воспроизвести багу можно создав новое MFC приложение с дефалтовыми настройками и добавить новый диалог со след. обработчиками

void SRGraphEditDialog::DoDataExchange(CDataExchange* pDX)
{
    CDialog::DoDataExchange(pDX);
    //{{AFX_DATA_MAP(SRGraphEditDialog)
    DDX_Control(pDX, IDC_TREEBUG, m_GraphTree);
    //}}AFX_DATA_MAP
}
//SRG_IDC_TREE1
BEGIN_MESSAGE_MAP(SRGraphEditDialog, CDialog)
    //{{AFX_MSG_MAP(SRGraphEditDialog)
    ON_NOTIFY(NM_DBLCLK, IDC_TREEBUG, OnDblclkTree1)
    //}}AFX_MSG_MAP
END_MESSAGE_MAP()

//SRG_IDC_TREE1

BOOL SRGraphEditDialog::OnInitDialog() 
{
    CDialog::OnInitDialog();

    BuildTree();
    
    return TRUE;  // return TRUE unless you set the focus to a control
                  // EXCEPTION: OCX Property Pages should return FALSE
}

void SRGraphEditDialog::BuildTree()
{
    m_GraphTree.DeleteAllItems();

    HTREEITEM listItem=m_GraphTree.InsertItem((LPCTSTR)_T("Data list"));

    for(int i = 0; i < 100; i++)
    {        
         HTREEITEM dataItem=m_GraphTree.InsertItem((LPCTSTR)_T("Data Item"), listItem);
                  
         CString annotationText;
         annotationText.Format(_T("%s"), MakeRandomString());
         HTREEITEM annotationItem=m_GraphTree.InsertItem((LPCTSTR)annotationText.GetBuffer(),dataItem);
    }
}

void SRGraphEditDialog::OnDblclkTree1(NMHDR* pNMHDR, LRESULT* pResult) 
{    
    BuildTree();

    *pResult = 0;
}

CString SRGraphEditDialog::MakeRandomString()
{
    CString sVal(_T(""));
    srand( (unsigned)time( NULL ) );
    for(int nCount = rand(); nCount > 0; nCount--)
    {
        sVal.AppendChar((TCHAR)rand());
    }
    return sVal;
}


Да чуть не забыл если у дерева установить стиль TVS_SINGLEEXPAND то бага перестает проявляться
Re[5]: Странное поведение DeleteAllItems в СTreeControl
От: VladFein США  
Дата: 09.02.06 21:33
Оценка: 1 (1)
Здравствуйте, _devdi_, Вы писали:

__>Воспроизвести багу можно создав новое MFC приложение с дефалтовыми настройками и добавить новый диалог со след. обработчиками


__>
__>CString SRGraphEditDialog::MakeRandomString()
__>{
__>    CString sVal(_T(""));
__>    srand( (unsigned)time( NULL ) );
__>    for(int nCount = rand(); nCount > 0; nCount--)
__>    {
__>        sVal.AppendChar((TCHAR)rand());
__>    }
__>    return sVal;
__>}
__>

Здесь, похоже, две проблемы:
1. Строки могут получиться ОООЧЕНЬ длинными (не уверен, какой лимит на текст в CTreeCtrl)
2. В строках могут оказаться нулевые байты
И "баг" может быть связан с memory corruption, а не с самим контролом.
Попробуйте переписать MakeRandomString используя, например
sVal.Format(_T("String # %d"), rand());

и посмотрите будет ли падать. (У меня ничего не падало).
Re[6]: Странное поведение DeleteAllItems в СTreeControl
От: _devdi_  
Дата: 10.02.06 10:09
Оценка:
Здравствуйте, VladFein, Вы писали:

VF>и посмотрите будет ли падать. (У меня ничего не падало).


Падает. Только Call Stack немного изменился.. падает прямо на DeleteAllItems

    comctl32.dll!CreateToolbar() + 0x848f
    comctl32.dll!CreateToolbar() + 0x8499
    comctl32.dll!CreateToolbar() + 0x8499
    comctl32.dll!CreateToolbar() + 0x863f
    comctl32.dll!CreateStatusWindow() + 0x41b4
    USER32.DLL!SetWindowPlacement() + 0x50
    USER32.DLL!ScreenToClient() + 0xd5
    USER32.DLL!CallWindowProcA() + 0x19
    MFC71.dll!CWnd::DefWindowProcA(unsigned int nMsg=4353, unsigned int wParam=0, long lParam=-65536) Line 1030 + 0x13C++
    MFC71.dll!CWnd::WindowProc(unsigned int message=4353, unsigned int wParam=0, long lParam=-65536) Line 1746 + 0x13C++
    MFC71.dll!AfxCallWndProc(CWnd * pWnd=0x00000000, HWND__ * hWnd=0x00500cbe, unsigned int nMsg=4353, unsigned int wParam=0, long lParam=-65536) Line 244 C++
    MFC71.dll!AfxWndProc(HWND__ * hWnd=0x00500cbe, unsigned int nMsg=4353, unsigned int wParam=0, long lParam=-65536) Line 387 + 0x10 C++
    MFC71.dll!AfxWndProcBase(HWND__ * hWnd=0x00500cbe, unsigned int nMsg=4353, unsigned int wParam=0, long lParam=-65536) Line 209 + 0x15 C++
    USER32.DLL!SetWindowPlacement() + 0x50
    USER32.DLL!IsWindowVisible() + 0x61c
    USER32.DLL!SendMessageA() + 0x44
    UnstableBug.exe!CTreeCtrl::DeleteAllItems() Line 247 + 0x65 C++
    UnstableBug.exe!SRGraphEditDialog::BuildTree() Line 56 C++
    UnstableBug.exe!SRGraphEditDialog::OnDblclkTree1(tagNMHDR * pNMHDR=0x0012f5cc, long * pResult=0x0012f3d0) Line 74 C++
    MFC71.dll!_AfxDispatchCmdMsg(CCmdTarget * pTarget=0x0012f990, unsigned int nID=1000, int nCode=65533, void (void)* pfn=0x00401cc6, void * pExtra=0x0012f33c, unsigned int nSig=57, AFX_CMDHANDLERINFO * pHandlerInfo=0x00000000) Line 119 C++

Совсем ничего не падало? Какую версию ОС используете?
У меня Win2k Advanced Server SP4 c IE6.0
Re[7]: Странное поведение DeleteAllItems в СTreeControl
От: VladFein США  
Дата: 10.02.06 15:01
Оценка:
Здравствуйте, _devdi_, Вы писали:

__>Здравствуйте, VladFein, Вы писали:


VF>>и посмотрите будет ли падать. (У меня ничего не падало).


__>Падает. Только Call Stack немного изменился.. падает прямо на DeleteAllItems




__>Совсем ничего не падало? Какую версию ОС используете?

__>У меня Win2k Advanced Server SP4 c IE6.0
XP, SP 2, IE 6, comctl32.dll v. 5.82.2900.2180
Re: Странное поведение DeleteAllItems в СTreeControl
От: Carc Россия http://www.amlpages.com/home.php
Дата: 10.02.06 18:10
Оценка: 1 (1)
Здравствуйте, _devdi_, Вы писали:

__>1. Есть три контрол на диалоге с кучей айтемов (около 60)

__>2. после выбора айтема вызывается диалговое окошко для редактирования данных
__>3. после нажатия ок вызывается т_Tree.DeleteAllItems() и дерево заполняется новыми элементами

__>4. Самое интересное. в 1 случае из 5 происходит падение с access violation в comctl32.dll


__>Подозрение падает именно на DeleteAllItems ибо при удалении три контрола и создании нового вместо удаления всех элементов бага не проявляется.

__>Поиск в групсах в гугле выдал несколько ссылок на похожую проблему однако на эти посты никто не ответил.

__>Может кто-нить встречался с чем — то похожим?


__>Буду признателен за любую помощь

Я встречался.
Source: MFC 6.0, VC6 sp5, в основном гонялось на win98 рус, но глюка проявлялась и не только в вин98 (2k, NT ws 4.0 sp4). DeleteAllItems был важен, т.к. вроде мне надо было память освободить (lParam у HTREEITEM хранил указатель на объект в куче)

Методы борьбы: если вместо DeleteAllItems позвать DeleteItem для корня (у меня он был один), то все равно конечно же приходило на каждый узел TVN_DELETEITEM.

Странности: ессесна пробовал и через макросы SDK TreeView_DeleteAllItems работать — ничего не изменилось, глюка все равно была.
У меня в основном провлялось в Debug тем, что намертво вешалась все на вызове метода или макроса, стек вроде бы (вроде бы:::) не рос.
Aml Pages Home
Re: Странное поведение DeleteAllItems в СTreeControl
От: cpp_best  
Дата: 24.02.06 18:30
Оценка:
Исправлено форматирование текста. — SchweinDeBurg

У меня тоже проблемы с DeleteAllItems. При вызове DeleteAllItems при заполненном дереве (да и пустом тоже) последующие вставки элементов в дерево проявляются глюки. Элементы вроде как вставляются, но в дереве не отображаются, если кликать мышкой в том месте, где должны быть элементы, то они (невидимые) будут выделяться.

Вот код:

    hRootCategory = TreeCtrl.InsertItem(_T("root"), 0, 0, NULL, TVI_SORT); // сколько угодно раз
    ...
    TreeCtrl.DeleteAllItems();
    hRootCategory = TreeCtrl.InsertItem(_T("root"), 0, 0, NULL, TVI_SORT); // теперь глюки

Кстати, код товарища _devdi_ тоже не заработал у меня (Win2k Pro SP4, IE 6 SP1, VS 7.1).
Можно все это обойти конечно удалением поэлементно вот так (как в msdn):

    HTREEITEM hCurrent = TreeCtrl.GetNextItem(hRootCategory, TVGN_PREVIOUS);
    TVITEM item;
    TCHAR szText[1024];
    while (hCurrent != NULL)
    {
        item.hItem = hCurrent;
        item.mask = TVIF_TEXT | TVIF_HANDLE;
        item.pszText = szText;
        item.cchTextMax = 1024;

        hCurrent = TreeCtrl.GetNextItem(hCurrent, TVGN_PREVIOUS);

        if (TreeCtrl.GetItem(&item))
            TreeCtrl.DeleteItem(item.hItem);
    }
    // до сюда удаляет все кроме первого элемента
    // добавляются отныне элементы прекрасно
    hCurrent = TreeCtrl.GetNextItem(hCurrent, TVGN_PREVIOUS);
    item.hItem = hCurrent;
    item.mask = TVIF_TEXT | TVIF_HANDLE;
    item.pszText = szText;
    item.cchTextMax = 1024;
    TreeCtrl.DeleteItem(item.hItem); // удаляем последний элемент, и опять глючит

Уже три дня угробил, помогите! Пробовал переименовать тот первый элемент, но не получается даже получить его имя, а этот код не меняет имени:
TreeCtrl.SetItemText(hCurrent, "New value");

Но наверное можно победить DeleteAllItems()? MS ее просто использует одним вызовом и ничего более. Спасибо большое заранее.
Re[2]: Странное поведение DeleteAllItems в СTreeControl
От: _devdi_  
Дата: 01.03.06 14:29
Оценка:
Здравствуйте, cpp_best, Вы писали:


_>У меня тоже проблемы с DeleteAllItems. При вызове DeleteAllItems при заполненном дереве (да и пустом тоже) последующие вставки элементов в дерево проявляются глюки. Элементы вроде как вставляются, но в дереве не отображаются, если кликать мышкой в том месте, где должны быть элементы, то они (невидимые) будут выделяться.


Может сюда:
http://www.rsdn.ru/Forum/?mid=1152774
Если не твой случай пересоздавай окно.

_>Но наверное можно победить DeleteAllItems()? MS ее просто использует одним вызовом и ничего более. Спасибо большое заранее.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.