Главная страница
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.47 MB
Время: 0.061 c
3-1120009643
DimonS
2005-06-29 05:47
2005.08.07
Не просматривается таблица dBase.


3-1120209540
Dell3r
2005-07-01 13:19
2005.08.07
Помогите составить запрос


1-1121981919
Тестер1
2005-07-22 01:38
2005.08.07
С чем может быть связан Виолэйшен Акссэс в ScreenToClient ?


4-1118395724
!Trinix
2005-06-10 13:28
2005.08.07
Форма


1-1121715510
JohnJ
2005-07-18 23:38
2005.08.07
Поиск компонентов