Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2005.08.07;
Скачать: CL | DM;

Вниз

_Release и VCL   Найти похожие ветки 

 
SeLarin ©   (2004-10-25 08:33) [0]

Привет, Мастера! Начал изучать COM и возникла проблема.
Есть код:

procedure TForm1.Button1Click(Sender: TObject);
var
 iShLnk: IShellLink;
 iPersFile: IPersistFile;
 Path: array[0..MAX_PATH] of Char;
 pfd: TWin32FindData;
 hr: HRESULT;
begin
 CoInitialize(nil);
 iShLnk:=nil;
 iPersFile:=nil;
 hr:=CoCreateInstance(CLSID_ShellLink,nil,CLSCTX_INPROC_SERVER,IID_IShellLinkA,iShLnk);
 if SUCCEEDED(hr) then
 begin
   hr:=iShLnk.QueryInterface(IID_IPersistFile,iPersFile);
   if SUCCEEDED(hr) then
   begin
     iPersFile.Load("Path_To_Some_Lnk_File", STGM_READ); // загружаем данные из ярлыка
     iPersFile._Release;
   end;
   if iShLnk.GetPath(Path,MAX_PATH,pfd,SLGP_UNCPRIORITY)=NOERROR then // считывает путь
     Application.MessageBox(Path,"Hi!!!",0); // показывает путь из ярлыка
   iShLnk._Release;
 end;
 CoUninitialize;
end;

Формально код написан без ошибок (руки в этом плане вроде бы растут из того места, откуда надо). При запуске на исполнение все работает и сообщение с путем из ярлыка показывается (путь правильный), но при этом при завершении процедуры возникает "External exception C000001D". В модуле Windows значению C000001D соответствует только одна константа - STATUS_ILLEGAL_OPERATION, смысл которой мне установить не удалось. Опытным путем установил, что исключение связано с вызовами метода _Release. Если убрать оба вызова, то исключения не возникает, если любой один - возникает только "Access violation...", но ведь _Release убрать вообще нельзя! Причем исключения странные: отловить и обработать их с помощью try..except не удается.
В связи с этим возникают вопросы: 1) почему возникает исключение? 2) как его избежать?

Кроме того, если данный код использовать (без изменений) в консольной программе, то никаких исключений не происходит. Значит, возникновение исключений каким-то образом связано с VCL?


 
VMcL ©   (2004-10-25 10:35) [1]

>>SeLarin ©  (25.10.04 08:33)

В Object Pascal экземпляры интерфейсов являются объектами с управляемым временем жизни. Вызов Release компилятор вставляет автоматически в том месте, где переменная интерфейсного типа выходит из области видимости.


 
VMcL ©   (2004-10-25 10:38) [2]

P.S.
Для того, чтобы явно освободить экземпляр интерфейса (это не так уж часто нужно) следует просто присвоить переменной интерфейсного типа константу nil:
SomeIntf := nil;  // Здесь компилятор автоматически вставит вызов Release при необходимости.


 
SeLarin ©   (2004-10-25 14:06) [3]

Спасибо. Просто и ясно!



Страницы: 1 вся ветка

Текущий архив: 2005.08.07;
Скачать: CL | DM;

Наверх




Память: 0.45 MB
Время: 0.024 c
1-1121888954
Quattro
2005-07-20 23:49
2005.08.07
Установка CoolTrayIcon v 4.3.1


1-1121685502
Destroyer
2005-07-18 15:18
2005.08.07
Как правильно удалить кнопку из её обработчика?


14-1121316605
Kerk
2005-07-14 08:50
2005.08.07
Если Санта Клаус жив, то он уже мертв...


1-1121770761
td
2005-07-19 14:59
2005.08.07
как скопировать текст из нескольких текстовых файлов в один?


5-1090750729
MSTX
2004-07-25 14:18
2005.08.07
Рисование на TButton





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский