La questione è emersa per me nella programmazione embedded, ma penso che possa essere applicata a un certo numero di situazioni di rete generale, ad es. quando un partner di comunicazione fallisce.
Supponiamo di avere una logica di applicazione (un programma) in esecuzione su un computer e un gadget collegato a quel computer tramite ad es. un'interfaccia seriale come RS232. Il gadget ha un LED rosso / verde / blu e un pulsante che disabilita il LED. Il colore dei LED può essere guidato da comandi software sull'interfaccia seriale e lo stato (rosso / verde / blu / spento) viene riletto e provoca una reazione nella logica dell'applicazione. Il comportamento asincrono della logica dell'applicazione in relazione al colore del LED fino a un certo ritardo (a seconda del ciclo di esecuzione dell'applicazione) è tollerato.
Ciò che essenzialmente abbiamo è una risorsa (il LED) che non può essere riservata e gestita atomicamente dal software perché l'utente (organico) può in qualsiasi momento premere il pulsante per interferire / interrompere il tentativo del software di cambiare il colore del LED.
Spogliamo questo esempio dal suo equipaggiamento fisico oso dire che abbiamo due macchine a stati comunicanti A (logica applicativa) e G (gadget) dove G esegue cambiamenti di stato all'insaputa di A (e anche il contrario, ma questo è non significativo nel nostro esempio) e solo A può essere modificato ad un prezzo ragionevole. A ha bisogno di vedere la reazione e lo stato di G in un'informazione che può essere (leggermente) superata ma non incoerente rispetto alla finestra temporale breve quando questa informazione è stata generata sul lato di G.
Quello che sto cercando è un metodo conciso per gestire una situazione del genere nel software embedded (ad esempio non sono disponibili layer / framework come CORBA ecc.). Una tecnica di programmazione che è in grado di mappare il comportamento completo di entrambi i partecipanti su interfacce classiche di un linguaggio di programmazione classico (C in questo caso). Per complicare le cose (o meglio, per generalizzare), un semplice ciclo di comunicazione ad alta frequenza da A a G e ritorno (IOW: A sta rapidamente interrogando G) è fuori fuoco a causa di restrizioni tecniche (ritardo della comunicazione seriale, A non sempre attivo , eccetera.). Quello che attualmente vedo come una soluzione generale è:
- la logica dell'applicazione A come un thread di esecuzione
- un oggetto adattatore (proxy) PG (che presenta G all'interno del computer), insieme al driver seriale come un altro thread
- un oggetto di comunicazione tra i due (A e PG) che è scambiabile in modo sicuro per transazioni
I due contesti di esecuzione (thread) sul computer possono essere multi-core o solo interrupt o attività in un RTOS. L'oggetto com contiene i seguenti dati:
- stato sospetto (scritto da A): efficacemente un membro del gruppo di stati di potere in G (nel nostro caso: rosso, verde, blu, spento, rosso_o_verde, rosso_o_bluè, rosso_o_off ... ecc.)
- dati di comando (scritti da A): test_if_off, switch_to_red, switch_to_green, switch_to_blue
- stato operativo (scritto da PG): operation_pending, success, wrong_state, link_broken
- nuovo stato (scritto da PG): rosso, verde, blu, spento
L'idea dell'oggetto com è che A scriva qualsiasi (set di) stato in cui pensa che G sia, insieme a un comando. (Esempio: stato sospetto="red_or_green", comando: "switch_to_blue") Si noti che i comandi emessi da A non funzioneranno se l'utente ha spento il LED e A deve saperlo. PG raccoglierà un oggetto com e tenterà di inviare il comando a G, ricevere la sua risposta (o un timeout) e impostare lo stato dell'operazione e il nuovo stato di conseguenza. A riprenderà l'oject una volta che non è più in operation_pending e può reagire al risultato. Ovviamente l'oggetto com può essere separato (in due oggetti, uno per ciascuna direzione) ma penso che in quasi tutte le istanze sia conveniente avere il comando vicino al risultato.
Mi piacerebbe che venissero evidenziate grandi imperfezioni o che ascoltassi una visione completamente diversa su tale situazione.