Ошибка выполнения «Отладка» на VS2008? - PullRequest
0 голосов
/ 07 мая 2010

Я пишу программу C ++ MFC на VS2008 и получаю эту «ошибку подтверждения отладки» при первом запуске программы иногда .Когда я пытаюсь отладить его, он приводит меня к этому файлу winhand.cpp, который не является частью программы, которую я написал, поэтому я не уверен, как отладить это.winhand.cpp

 CObject* pTemp = LookupTemporary(h);
 if (pTemp != NULL)
 {
  // temporary objects must have correct handle values
  HANDLE* ph = (HANDLE*)((BYTE*)pTemp + m_nOffset);  // after CObject
  ASSERT(ph[0] == h || ph[0] == NULL);
  if (m_nHandles == 2)
   ASSERT(ph[1] == h);
 }

Так почему же происходит эта ошибка?Почему это происходит только иногда (в 50% случаев)?Как мне отладить это?

Я предоставлю код, если необходимо.

СПАСИБО!

Ответы [ 6 ]

3 голосов
/ 07 мая 2010

Код, который утверждает, является частью класса CHandleMap MFC.MFC работает с окнами как CWnd объектами, но Windows работает с ними как с HWND ручками.карта дескриптора позволяет MFC «преобразовать» HWND в указатель на объект MFC, представляющий этот объект.

Кажется, что утверждение делает проверку того, что когда поиск дескриптора находит объект MFC, что объект MFC также думает, что оборачивает один и тот же дескриптор.

Если они отличаются, то вы получите утверждение.

Таким образом, может показаться, что что-то портит карту дескриптора илиОбъект MFC для этого дескриптора, или вы делаете что-то неправильно, что приводит к несовпадению этих двух структур данных.

Некоторые вещи, которые вы можете сделать, чтобы попытаться отладить проблему, это определить:

  • какой объект MFC находится в поиске (это то, на что указывает pObject)
  • то, что объект MFC считает обертывающим (это дескриптор ph[0] и / или ph[1] - IЯ не уверен, почему их может быть 2)
  • для чего нужен дескриптор (это h)

Похожи ли дескрипторы на значения дескриптора или они выглядят какодеяниевозраст?pObject указывает на что-то похожее на объект MFC или мусор?Кажется ли что-то из этого взаимосвязанным?

Ответы на эти вопросы могут указывать на то, что вам нужно делать дальше (может быть, установить точку останова для записи отладки для элемента, который выглядит так, как будто он удален).

1 голос
/ 08 июля 2014

Я получил это же утверждение несколько дней назад, и после некоторого поиска в Google, Я нашел решение для моего случая здесь: http://forums.codeguru.com/showthread.php?216770-What-would-cause-this-assertion

В моем случае измените на неправильное использование

CDC* dc = GetDC();
CSize spaceSize = dc->GetTextExtent(" ");
dc->DeleteDC();

до

CDC* dc = GetDC();
CSize spaceSize = dc->GetTextExtent(" ");
ReleaseDC(dc);

исправит это.

0 голосов
/ 07 января 2017

Я знаю, что это очень старый пост, но надеюсь, что кто-то может получить небольшую помощь от моего ответа.

Я также недавно столкнулся с подобной проблемой из-за своей простой ошибки, затем я наткнулся на этот пост и получил подсказку из поста "pac".

Я обнаружил, что если я использую DeleteDC () для освобождения DC, возвращенного из GetWindowDC () или GetDC (), я получу вышеуказанное утверждение в кадре MFC, как только экземпляр объекта CPaintDC выйдет из области видимости.

CDC * pDC = GetWindowDC();
...
ReleaseDC(pDC);

Вы должны использовать DeleteDC () только в сочетании с API CreateDC ().

CDC * pDC = new CDC();
pDC->CreateDC();
....
pDC->DeleteDC();
0 голосов
/ 07 мая 2010

Это выглядит подозрительно, как ошибка, с которой я столкнулся сегодня утром.Это происходит в OnIdle ()?

0 голосов
/ 07 мая 2010

Когда отладчик выходит из строя, направьте стек вызовов к первому биту вашего кода (если есть - надеюсь, есть!). В идеале это так же просто, как что-то в вашем коде, неправильно вызывать библиотечную функцию, и библиотека отлавливает ошибку с помощью assert и предупреждает вас об этом. (Я не думаю, что кто-то сможет сказать, что не так из кода library , нам нужно увидеть ваш код.)

В противном случае вас ждет сложная отладка: вы делаете что-то не так с библиотекой, которая утверждает (выглядит как MFC), поэтому вернитесь и просмотрите весь свой код MFC и убедитесь, что все правильно и в соответствии с документация.

0 голосов
/ 07 мая 2010

Ищите код по этим строкам (по памяти из книги Страуструпа):

c1 = (t2+t3).c_str();

(по духу, могут быть и другие команды и выражения, конечно). Временные объекты уничтожаются после того, как их заключающее полное выражение было оценено, или, по крайней мере, стандарт позволяет им это делать. Это означает, что то, что вы хотели бы выделить для c1, может или не может оставаться в памяти, где оно может быть назначено для c1. Компилятор может предупредить вас об этой проблеме, и проблема может возникать или не возникать в зависимости от того, что именно вы назначаете, и других обстоятельств (я не пишу компилятор), что также объясняет, почему вы получаете это сообщение об ошибке только иногда.

Итак, я бы просканировал мой код на наличие похожих выражений и вычистил их.

...