Comunicazione tra oggetti

COM è progettato per consentire ai client di comunicare in modo trasparente con oggetti, indipendentemente dalla posizione in cui tali oggetti sono in esecuzione, nello stesso processo, nello stesso computer o in un computer diverso. Fornisce un singolo modello di programmazione per tutti i tipi di oggetti e sia per i client oggetto che per i server oggetti.

Dal punto di vista di un client, tutti gli oggetti sono accessibili tramite puntatori di interfaccia. Un puntatore deve essere in-process. In effetti, qualsiasi chiamata a una funzione di interfaccia raggiunge sempre una parte del codice in-process prima. Se l'oggetto è in-process, la chiamata lo raggiunge direttamente, senza alcun codice di infrastruttura di sistema. Se l'oggetto è out-of-process, la chiamata raggiunge prima ciò che viene chiamato un oggetto "proxy" fornito da COM o dall'oggetto (se l'implementatore desidera). I pacchetti proxy chiamano parametri (inclusi i puntatori di interfaccia) e generano la chiamata di procedura remota appropriata (o altro meccanismo di comunicazione nel caso di proxy generati personalizzati) all'altro processo o all'altro computer in cui si trova l'implementazione dell'oggetto. Questo processo di creazione di pacchetti di puntatori per la trasmissione attraverso i limiti del processo è denominato marshalling.

Dal punto di vista di un server, tutte le chiamate alle funzioni di interfaccia di un oggetto vengono effettuate tramite un puntatore a tale interfaccia. Anche in questo caso, un puntatore ha contesto solo in un singolo processo e il chiamante deve sempre essere una parte del codice in-process. Se l'oggetto è in-process, il chiamante è il client stesso. In caso contrario, il chiamante è un oggetto "stub" fornito da COM o dall'oggetto stesso. Lo stub riceve la chiamata di procedura remota (o un altro meccanismo di comunicazione nel caso di proxy generati personalizzati) dal "proxy" nel processo client, annulla ilmarsaling dei parametri e chiama l'interfaccia appropriata nell'oggetto server. Dal punto di vista dei client e dei server, comunicano sempre direttamente con un altro codice in-process.

COM fornisce un'implementazione del marshalling, definita marshalling standard. Questa implementazione funziona molto bene per la maggior parte degli oggetti e riduce notevolmente i requisiti di programmazione, rendendo il processo di marshalling efficacemente trasparente.

La netta separazione dell'interfaccia dall'implementazione della trasparenza del processo COM può, tuttavia, essere in alcune situazioni. La progettazione di un'interfaccia incentrata sulla sua funzione dal punto di vista del client può talvolta portare a decisioni di progettazione in conflitto con l'implementazione efficiente di tale interfaccia in una rete. In casi come questo, ciò che è necessario non è pura trasparenza del processo, ma "trasparenza del processo, a meno che non sia necessario prestare attenzione". COM offre questa funzionalità consentendo a un implementatore di oggetti di supportare il marshalling personalizzato (detto anche marshalling IMarshal). Il marshalling standard è, infatti, un'istanza del marshalling personalizzato; è l'implementazione predefinita usata quando un oggetto non richiede il marshalling personalizzato.

È possibile implementare il marshalling personalizzato per consentire a un oggetto di eseguire azioni diverse quando usate da una rete rispetto all'accesso locale ed è completamente trasparente per il client. Questa architettura consente di progettare interfacce client/oggetto senza considerare i problemi di prestazioni di rete e successivamente risolvere i problemi di prestazioni di rete senza interrompere la progettazione stabilita.

COM non specifica il modo in cui i componenti sono strutturati; specifica il modo in cui interagiscono. COM lascia la preoccupazione sulla struttura interna di un componente per i linguaggi di programmazione e gli ambienti di sviluppo. Viceversa, gli ambienti di programmazione non hanno standard impostati per l'uso di oggetti all'esterno dell'applicazione immediata. Microsoft Visual C++, ad esempio, funziona molto bene per la modifica di oggetti all'interno di un'applicazione, ma non supporta l'uso di oggetti all'esterno dell'applicazione. In genere, tutti gli altri linguaggi di programmazione sono gli stessi a questo proposito. Pertanto, per garantire l'interoperabilità a livello di rete, COM, tramite interfacce indipendenti dal linguaggio, sceglie dove i linguaggi di programmazione non vengono interrotti.

Il doppio riferimento indiretto della struttura vtbl significa che i puntatori nella tabella dei puntatori a funzione non devono puntare direttamente all'implementazione reale nell'oggetto reale. Questo è il cuore della trasparenza del processo.

Per i server in-process, in cui l'oggetto viene caricato direttamente nel processo client, i puntatori di funzione nella tabella puntano direttamente all'implementazione effettiva. In questo caso, una chiamata di funzione dal client a un metodo di interfaccia trasferisce direttamente il controllo di esecuzione al metodo . Tuttavia, questo non può funzionare per i processi locali, ma non per gli oggetti remoti, perché i puntatori alla memoria non possono essere condivisi tra processi. Tuttavia, il client deve essere in grado di chiamare metodi di interfaccia come se stesse chiamando l'implementazione effettiva. Di conseguenza, il client trasferisce in modo uniforme il controllo a un metodo in un oggetto effettuando la chiamata.

Un client chiama sempre metodi di interfaccia in un oggetto in-process. Se l'oggetto effettivo è locale o remoto, la chiamata viene effettuata a un oggetto proxy, che esegue quindi una chiamata di routine remota all'oggetto effettivo.

Quindi, quale metodo viene effettivamente eseguito? La risposta è che ogni volta che è presente una chiamata a un'interfaccia out-of-process, ogni metodo di interfaccia viene implementato da un oggetto proxy. L'oggetto proxy è sempre un oggetto in-process che agisce per conto dell'oggetto chiamato. Questo oggetto proxy sa che l'oggetto effettivo è in esecuzione in un server locale o remoto.

L'oggetto proxy crea un pacchetto dei parametri della funzione in alcuni pacchetti di dati e genera una chiamata RPC all'oggetto locale o remoto. Tale pacchetto viene prelevato da un oggetto stub nel processo del server nel computer locale o remoto, che decomprime i parametri e effettua la chiamata all'implementazione reale del metodo. Quando la funzione viene restituita, lo stub inserisce tutti i parametri out e il valore restituito e lo invia al proxy, che li decomprime e li restituisce al client originale.

Così, client e server parlano sempre tra loro come se tutto fosse in-process. Tutte le chiamate dal client e tutte le chiamate al server sono, a un certo punto, in-process. Tuttavia, poiché la struttura vtbl consente ad alcuni agenti, come COM, di intercettare tutte le chiamate di funzione e tutte le funzioni restituite dalle funzioni, tale agente può reindirizzare tali chiamate a una chiamata RPC in base alle esigenze. Anche se le chiamate in-process sono più veloci rispetto alle chiamate out-of-process, le differenze di processo sono completamente trasparenti per il client e il server.

Per ulteriori informazioni, vedi gli argomenti seguenti:

Client e server COM

Marshalling dell'interfaccia