Newsgroups : Borland : borland.public.delphi.nativeapi.win32 : 2008 Apr : COM: creation, ownership and destruction of (wide) strings in TPropVariant args

www.cryer.info
Managed Newsgroup Archive

COM: creation, ownership and destruction of (wide) strings in TPropVariant args

Subject:COM: creation, ownership and destruction of (wide) strings in TPropVariant args
Posted by:"Andrew Fiddian-Green" (..@dd)
Date:Thu, 10 Apr 2008 09:10:04 +0200

Hi,

I am writing a COM property handler shell extension for Windows. I am
rather confused about the creation, ownership scope and destruction of
(wide) strings that are referenced and passed between callee (my
handler) and caller (Windows Explorer) in TPropVariant structures.

My code is shown below.

TMyPropertyStore = class(TComObject, IPropertyStore, IInitializeWithStream)
   private
     fProperty: TPROPVARIANT;
   public
     function IInitializeWithStream_Initialize(const pIStream: IStream;
grfMode: DWORD): HRESULT; stdcall;
     function IPropertyStore_GetValue(var aPropKey: TPropertyKey; out
aPropVar: TPropVariant): HRESULT; stdcall;
end;

TMyparser
   procedure LoadFromStream(pIStream: IStream);
   property SomeThing: widestring;
end;

function IInitializeWithStream_Initialize(..)
begin
   parser := TMyParser.Create;
   try
     parser.LoadFromStream(piStream);
     fProperty.vt := VT_BSTR;
     fProperty.bstrVal := SysAllocString(PWideChar(parser.Something));
   finally
     parser.Free;
   end;
end;

function IPropertyStore_GetValue(..)
begin
   aPropVar := fProperty;
end;

In IInitializeWithStream_Initialize I am using SysAllocString() because
a straight PWideChar() cast seems to fail when the parser goes out of
scope. Perhaps because PWideChar() does not create a reference count
lock on the respective widestring?

In IPropertyStore_GetValue I use an assignment of my local TPropVariant
to the respective "out" argument. I am assuming that this does not
increment or decrement any reference counts on any strings?

I am assuming that the caller of IPropertyStore_GetValue (actually
Windows Explorer) makes its own local copy of the aPropVar.bstrVal and
does not increment or decrement any reference counts on my string, or
attempt to destroy the string?

I am assuming that I do not need to destroy the string created by
SysAllocString() explicitly in my destructor, since I guess it goes away
automatically when my object goes out of scope?

Finally, according to the Windows SDK, I should be using the following
rather than VT_BSTR but for some odd reason that does not seem to work
at all..
   fProperty.vt := VT_LPWSTR;
   fProperty.pwszVal := SysAllocString(PWideChar(parser.Something));

Also I wonder if I need to do anything explicit against the risk (is
there one?) that my object may be called simultaneously on several
threads...

Any advice would be much welcome.

Regards
AndrewFG

Glossary

Replies:

www.cryer.info
Managed Newsgroup Archive