dynamic_cast di un oggetto COM a un'interfaccia COM non urtare il conteggio di riferimento, lo fa?
-
13-09-2019 - |
Domanda
Se ho una classe C ++, X, che attua il IY interfacce COM e IZ, e ho un puntatore y all'interfaccia IY di un oggetto di tipo X, e fare questo:
IZ *z = dynamic_cast<IZ *> ( y );
Questo non urtare conteggio dei riferimenti dell'oggetto, lo fa? Io non devo fare una Release () per tenere conto di esso, giusto?
Se è importante, sto usando ATL / COM.
Sto indovinando la risposta è "No, non urtare il conteggio di riferimento, e non non si ha a Release ()", ma voglio essere sicuro.
Grazie in anticipo.
Soluzione
conteggi di riferimento per gli oggetti COM vengono incrementati quando chiama qualcuno IUnknown :: AddRef (). QueryInterface (), in base alle leggi di COM in quanto dà un nuovo puntatore di interfaccia, internamente chiama AddRef ().
Nel codice inviato, non stai chiamando AddRef (), e non si sta chiamando una funzione che potrebbe porre AddRef (), quindi perché si potrebbe pensare che il conteggio dei riferimenti sarebbe stato incrementato?
Nonostante quello ATL / MFC fa al proprio cervello, non c'è nessuna magia coinvolti. In caso di dubbio, sempre è possibile visualizzare lo smontaggio in VS e passo attraverso di essa e dimostrare a te stesso che AddRef () non viene chiamato.
Edit: E voglio ribadire quanto detto Dewfy, non fare questo . Utilizzare QueryInterface (). O CComQIPtr <> (se proprio deve).
Ulteriore modifica: se si utilizza CComPtr <> e CComQIPtr <>, allora non c'è bisogno di chiamare Release () e gran parte del carico di capire il corretto ref-conteggio è alleviato. Si dovrebbe davvero prendere in considerazione il loro utilizzo.
Altri suggerimenti
dynamic_cast non deve essere utilizzato su molteplici motivi:
- Non si sa se di destinazione supporta RTTI
- Non è sicuro se OLE non crea proxy per voi
- ...
Invece utilizzare QueryInterface - sarebbe fatto quello che vuoi
.Anche se sei sicuro di domanda di cui sopra - di fusione non cambia refcounter
In C ++ Builder, dynamic_cast
su un puntatore a interfaccia COM realmente fa QueryInterface
. e il puntatore restituito, se il QI ha successo, viene AddRef
'd.
Le classi che implementano oggetti COM hanno diversi layout vtable al più generale classi C ++, quindi un C ++ - stile dynamic_cast
non può funzionare; così Presumo che questo è il motivo per C ++ Builder fa la cosa più ragionevole di fare QueryInterface.
(L'idea originale di COM era di generalizzare modello a oggetti C ++ per essere indipendente dal linguaggio e ad uno standard binario; hanno ribattezzato dynamic_cast a QueryInterface)
.Credo che la risposta in alto si riferisce a MSVC, se dynamic_cast provoca un comportamento indefinito.