Нарушение прав доступа при передаче строки BSTR в конструктор _bstr_t или CComBSTR

У меня есть строка BSTR, которая передается с COM-сервера. Когда я помещаю эту строку в конструктор _bstr_t (или CComBSTR), происходит нарушение доступа. Я проверил это исключение и обнаружил, что это исключение возникает только тогда, когда BSTR пуст (или ноль).

Я пытался явно обнулять BSTR в конструкторе _bstr_t, и это прекрасно работает:

BSTR bstr = NULL;
_bstr_t t(bstr, false);

cout << t.length() << endl;

Но с BSTR, который передается с COM-сервера, это не работает — исключение нарушения доступа возникает, когда строка пуста или равна нулю (или может быть повреждена?)

Я обнаружил, что этот обходной путь работает нормально:

if (SysStringLen(bstrFromCOMserver) > 0) {
_bstr_t t(bstrFromCOMserver, false);
cout << t.length() << endl;
}

Но я хочу знать, почему это не работает напрямую с обертками _bstr_t или CComBSTR:

_bstr_t t(bstrFromCOMserver, false);
if (t.length() > 0) {...}

Обновить:

Как COM-сервер передает строку BSTR:

void CALLBACK CProxy_ISTIQuoteEvents::OnSTIQuoteSnap(const structSTIQuoteSnap& structQuoteSnap) const {
if (SysStringLen(structQuoteSnap.bstrUpdateTime) > 0) {
_bstr_t updateTime(structQuoteSnap.bstrUpdateTime, false);
}
}
}

0

Решение

OnSTIQuoteSnap Методы принадлежат приемнику событий и вызываются сервером, как мы пояснили в комментариях. Таким образом, сервер (как вызывающий) сохраняет владение structQuoteSnap структура и все ее поля. updateTime является локальной переменной смарт-указателя, которая должна делать копию строки (structQuoteSnap.bstrUpdateTime), но это не так (как false передается его конструктору), так что он скорее забирает память BSTR. Эта память освобождается, как только updateTime выходит за рамки. Сервер ничего не знает об этом и может продолжать использовать bstrUpdateTime и может в конце концов попытаться освободить одну и ту же память дважды.

1

Другие решения

Других решений пока нет …

По вопросам рекламы ammmcru@yandex.ru
Adblock
detector