• Non ci sono risultati.

[3.3.7] Miglioramenti e Correzion

ODPSRP-QUERY-METHOD WITHOUT-NOTIFICATION

[3.3.7.9] Frammentazione Pacchetti

L’ambiente di simulazione Qualnet 3.6 non supporta la frammentazione IP ma al contrario impone un limite alla dimensione massima del payload che può essere inviato tramite i protocolli di trasporto UDP e TCP.

Questa forte limitazione rappresenta un problema per la simulazione e lo studio del comportamento del sistema in caso di notifiche di dimensione non trascurabili in quanto in questo caso i meccanismi di bufferizzazione delle notifiche stesse portano frequentemente a superare il limite imposto.

Per ovviare a tale inconveniente sono state implementate due soluzioni per superare le limitazioni dell’ambiente di simulazione Qualnet: la prima si applica al meccanismo relativo il

QUERY BUFFER, mentre la seconda si applica al meccanismo relativo il NOTIFICATION BUFFER.

Come noto il QUERY BUFFER viene utilizzato durante il QUERY-BUFFER-INTERVAL per memorizzare tutte le notifiche eventualmente pubblicate fino all’istante di invio del pacchetto JOIN QUERY, mentre il NOTIFICATION BUFFER viene utilizzato durante il WAIT-FOR- REPLY-INTERVAL per memorizzare tutte le notifiche eventualmente pubblicate prima del termine del ciclo di ricostruzione della mesh di trasporto, ovvero dall’istante di invio di una JOIN QUERY fino all’istante in cui si ritengono ricevute tutte le relative JOIN REPLY.

Il QUERY-BUFFER viene utilizzato per memorizzare notifiche soltanto nel caso in cui la simulazione viene eseguita con il parametro QUERY-METHOD impostato sul valore WITH- NOTIFICATION, ovvero nel caso in cui il meccanismo nominato LIGHT-QUERY-METHOD e dettagliato nella sezione [3.3.7.8] è disabilitato.

La prima soluzione riguarda proprio la gestione del QUERY-BUFFER e consiste nell’evitare di memorizzarvi un numero di notifiche tale da poter creare successivamente pacchetti JOIN QUERY troppo grandi, che superano il limite imposto dal simulatore.

In dettaglio, ogni qualvolta viene memorizzata all’interno del buffer una notifica, viene effettuato un test per verificare se una nuova eventuale notifica sia tale da far superare il limite: in caso affermativo viene immediatamente creato e inviato il pacchetto JOIN QUERY e il buffer viene svuotato.

La seconda soluzione invece riguarda il NOTIFICATION BUFFER e consiste semplicemente nell’operare a livello applicativo una frammentazione del pacchetto NOTIFICATION allo scadere del WAIT-FOR-REPLY-INTERVAL: quando si rende necessario svuotare il NOTIFICATION BUFFER tramite l’invio di un pacchetto NOTIFICATION, si creano e si trasmettono più pacchetti NOTIFICATION, ogniuno contenente un numero di notifiche tali da non superare il limite imposto dal Qualnet alla dimensione dei singoli pacchetti IP.

Un problema che sorge a questo punto è costituito dall’intervallo con qui questi pacchetti devono essere inviati al sottostante livello di trasporto UDP: la soluzione più semplice consiste nell’inserire tra un pacchetto e il successivo un ritardo impostabile tramite il parametro

BUFFER-FLUSH-DELAY, di default impostato al valore di 20 millisecondi.

Per modificare tale parametro è sufficiente inserire all’interno del file di configurazione la seguente stringa:

[3.3.7.10] Filter Timeout e Reply Timeout

Quando un nodo intermedio riceve un JOIN REPLY a lui destinato, memorizza i filtri in esso contenuti (filtri di forward), si attiva come forwarder, quindi se necessario ritrasmette un proprio JOIN REPLY al proprio nodo predecessore lungo il path di trasporto (nodeUp).

Ognuno di questi filtri dovrebbe avere un tempo di vita limitato, oltre il quale dovrebbe essere scartato, in modo da evitare che un path di trasporto attivato da una sottoscrizione rimanga attivo in eterno.

La prima soluzione implementata è estremamente semplice e consiste nel memorizzare per ogni filtro di forward ricevuto tramite pacchetti JOIN REPLY l’istante di ricezione, che chiameremo FILTER_TIMESTAMP.

È presente un parametro all’interno del nostro protocollo di servizio che stabilisce il tempo di vita massimo di ogniuno di questi filtri di forward e che può essere impostato a piacere tramite la seguente stringa da inserire all’interno del file di configurazione della simulazione:

ODPSRP-FG-TIMEOUT value

In genere tale parametro è bene che sia impostato con valori pari a circa 2.5-3 volte l’intervallo di ricostruzione della mesh (ODPSRP-QUERY-INTERVAL).

Questa semplice implementazione tuttavia dimostra effetti collaterali piuttosto gravi se consideriamo che tutti i nodi intermedi divengono essi stessi dei subscriber attivi fintanto che i filtri ricevuti (filtri di forward) non vengono scartati per vecchiaia: in particolare ogni nodo intermedio ad ogni ciclo di ricostruzione e aggiornamento della mesh di trasporto, risponde con un proprio JOIN REPLY contenente tutti i filtri di forward non ancora scaduti; tutti i nodi che ricevono tale pacchetto inseriscono i filtri in esso contenuti tra i propri filtri di forward con TIMESTAMP pari all’istante di ricezione e qui vi rimarranno attivi per un tempo pari a FG_TIMEOUT; al successivo ciclo di refresh tali nodi ritrasmetteranno a loro volta un nuovo JOIN REPLY con i filtri ancora attivi e altri nodi memorizzeranno i filtri ricevuti con un valore di TIMESTAMP pari all’istante di ricezione, e cosi via.

In questo modo succede che un filtro sottoscritto da un nodo Subscriber rimane all’interno della rete un tempo indeterminato e assolutamente casuale, indipendente dal valore del parametro FG_TIMEOUT.

Per ovviare a tale problema sarebbe sufficiente impedire ai nodi intermedi di rispondere ai JOIN QUERY in maniera autonoma, ovvero di evitare che nodi intermedi si comportino da nodi Subscriber e costringerli a rispondere ai pacchetti JOIN QUERY solo e unicamente nel caso di ricezione di un relativo JOIN REPLY durante lo stesso ciclo di ricostruzione e aggiornamento mesh.

Ciò nonostante abbiamo già spiegato il motivo della scelta di permettere ai nodi intermedi di agire come dei veri e propri nodi Subscriber fintanto che possiedono filtri attivi, quindi è necessario ricorrere ad una soluzione diversa.

La seconda soluzione implementata consiste nell’inserire all’interno di ogni filtro che viene inviato tramite pacchetti JOIN REPLY il tempo di validitá ancora disponibile: ogni nodo Subscriber quindi invierà i filtri sottoscritti da applicazioni locali con un tempo di validità pari al massimo (ovvero pari al parametro FG_TIMEOUT), mentre tutti i filtri di forward che verranno inseriti all’interno dei pacchetti JOIN REPLY avranno un tempo di validità pari al valore precedentemente prelevato dal JOIN REPLY, diminuito del tempo trascorso.

In Figura 28 è possibile osservare in maniera più diretta e chiara il meccanismo descritto.

Forwarder Node Forwarder Node JOIN REPLY [X>5],life=8s JOIN REPLY [X>5],life=8s JOIN REPLY [X>5],life=8s [X=3],life=8s JOIN REPLY [X>5],life=8s [X=3],life=8s JOIN QUERY [X] JOIN QUERY [X] JOIN QUERY [X] JOIN REPLY [X>5],life=3s [X=3],life=8s JOIN REPLY [X>5],life=3s JOIN REPLY [X>5],life=3s [X=3],life=8s Subscriber Node [X=3] 16/04/2004 - 23/04/2004 5s JOIN QUERY [X] JOIN QUERY [X] JOIN QUERY [X] JOIN REPLY [X=3],life=8s JOIN REPLY [X=3],life=8s 16/04/2004 - 23/04/2004 5s 8s Filtro [X>5] scaduto FG_FILTER_TIMEOUT = 8s QUERY_INTERVAL = 5s time time time Figura 28

In questo modo i filtri sottoscritti da un nodo Subscriber all’interno di un pacchetto JOIN REPLY rimarranno attivi in rete esattamente per un tempo pari a FG_TIMEOUT, oltre il quale scadranno tutti contemporaneamente a meno di aggiornamenti fatti dallo stesso nodo Subscriber.

In realtà nell’implementazione del protocollo di servizio ODPSRP realizzata i tempi inseriti per ogni filtro all’interno dei pacchetti JOIN REPLY non contengono propriamente il tempo di vita ancora utile, bensì l’istante in cui tali filtri andranno a scadere: questo per una ragione di semplicità implementativa offerta dall’ambiente di sviluppo Qualnet in cui tutti gli orologi di sistema dei vari nodi sono perfettamente sincronizzati.

In un’implementazione reale dovremo al contrario inserire per ogni filtro il tempo di vita residuo; in questo modo si prescinde da una improbabile sincronizzazione degli orologi di sistema dei vari nodi anche se in realtà il tutto funziona correttamente solo se i pacchetti sperimentano tempi di attesa sulle code delle interfacce di comunicazione trascurabili.

[3.4] QualnetAnimator

Qualnet Animator rappresenta un modulo di Qualnet® 3.6 che si interfaccia direttamente al simulatore e permette l’utilizzo di un’interfaccia grafica particolarmente semplice e user-friendly per la creazione ed esecuzione di configurazioni di simulazione personalizzate.

In particolar modo tale strumento ci risulta molto comodo e pratico per visualizzare in modo semplice e diretto il comportamento del sistema e analizzarne e studiarne così eventuali difetti e malfunzionamenti.

Per un utilizzo proficuo di questa interfaccia è stato necessario inserire all’interno del codice del protocollo delle chiamate a particolari funzioni dell’interfaccia grafica stessa contenute all’interno del file di intestazione “gui.h” che permettono di disegnare direttamente sulla finestra dell’Animator animazioni in tempo reale che sintetizzano con effetti grafici diretti e facilmente comprensibili ciò che sta accadendo nel sistema.

In particolare:

• i nodi Publisher così come i nodi Subscriber sono rappresentati mediante apposite icone stilizzate (un satellite per il primo, un uomo con ricetrasmittente per il secondo)

• il processo di costruzione e aggiornamento della mesh di trasporto viene visualizzato tramite una “bolla di trasmissione” di colore nero centrata sul nodo Publisher

• I cammini di forward trovati tramite il flooding dei pacchetti JOIN QUERY vengono direttamente tracciati tramite linee di congiunzione nere

• I nodi Forwarder vengono visualizzati con un’apposita icona (un traliccio che rappresenta il ponte radio)

• Le trasmissioni e ritrasmissioni di pacchetti NOTIFICATION sono rappresentate tramite “bolle di trasmissione” di colore blu

• La ricezione di pacchetti di tipo NOTIFICATION viene visualizzata tramite una freccia orientata di colore verde

Notare come il sistema sia di facile comprensione soltanto nel caso venga eseguito con un solo nodo Publisher presente all’interno del sistema; in caso contrario infatti le linee di forward si sovrappongono così come i nodi Forwarder e non si ha più una corretta cognizione di ciò che sta realmente accandendo nel sistema.

Riportiamo di seguito alcuni screenshot prelevati direttamente prelevati dall’interfaccia grafica durante l’esecuzione di un sistema costituito da 20 nodi disposti su di un’area di 1km quadrato, con un nodo Publisher e tre nodi Subscriber.

In Figura 29 sono chiaramente visibili i tre nodi Subscriber e il nodo Publisher; la “bolla di trasmissione” centrata sul nodo Publisher indica l’inizio di un ciclo di costruzione della mesh di trasporto tramite l’invio in flooding del pacchetto JOIN QUERY.

Figura 30

Come possiamo vedere in Figura 30, durante tale ciclo i pacchetti JOIN QUERY vengono ritrasmessi da ogni nodo e contemporaneamente ogni nodo viene a conoscere il proprio predecessore lungo il cammino di forward, creando tutta una serie di link virtuali rappresentati dalle linee di congiunzione nere.

Figura 31

In Figura 31 vediamo uno screenshot prelevato immediatamente dopo il termine di un ciclo di costruzione e aggiornamento della mesh di trasporto; possiamo vedere la presenza di alcuni nodi che si sono attivati come Forwarder e che quindi hanno cambiato la propria icona: si tratta dei nodi 7,8,9,13,19.

Tali nodi ritrasmetteranno ogni notifica non duplicata che riceveranno dal nodo Publisher, ovvero dal nodo 1.

Figura 32

In Figura 32 osserviamo una “bolla di ritrasmissione” centrata sul nodo Forwarder 7: si tratta di una ritrasmissione di un pacchetto di notifica ricevuto dal nodo Publisher 1.

Tale ritrasmissione permetterà ai nodi Forwarder 8 e 13 di riceve e quindi di ritrasmettere tale notifica in modo da farla giungere fino a destinazione ai nodi Subscriber 15 e 20; tutti gli altri nodi non Forwarder, scarteranno ogni notifica ricevuta, sia essa duplicata o meno, in quanto non interessati ne direttamente ne indirettamente agli eventi in essa contenuti.

Documenti correlati