Realizzare test di I/O affidabili su un sistema di storage è una tecnica che spesso sconfina nell’arte. Sia arte nel sapere definire metodologie affidabili e ripetitive, ma purtroppo ancora più spesso arte di chi realizza i test nel configurare ad hoc il test per far dire allo strumento di misurazione quello che il produttore vuole che si dica; falsare i test di I/O infatti è quanto di più facile sia possibile fare, e spesso basta omettere nella pubblicazione dei risultati dei parametri fondamentali come la latenza o il block size per renderli completamente differenti. Basta usare un block size di 512 byte per far schizzare l’I/O alle stelle, pur sapendo che nessun software “reale” utilizza quelle dimensioni, oppure indicare i valori ottenuti senza dire che nel frattempo la latenza è diventata di 10 secondi…
A livello industriale esistono strumenti per realizzare dei test, come TPC-C o SPECsfs. Sono strumenti molto potenti, e permettono oltretutto di uniformare le metodologie di test indipendentemente dallo storage su cui vengono eseguiti. Sarebbero perfetti, se non fosse che costano parecchi soldi, e se nemmeno i produttori li usano su tutti i loro sistemi, figuriamoci noi utenti.
In ambito “amatoriale” invece uno dei programmi più utilizzati è senza dubbio IOmeter. E’ un programma molto facile da usare, che permette di realizzare test molto velocemente. Purtroppo non consente di realizzare test molto realistici: è facile misurare le prestazioni massime di uno storage, ma non verificarne le potenzialità in situazioni produttive. E’ un pò come fare le gare di accelerazioni da 0 a 100 kmh, piuttosto che cronometrare un giro di pista. Un dragster è sicuramente quanto di più veloce ci sia per accelerare, ma non è certamente la soluzione migliore per circolare in strada.
Ultimamente oltretutto IOmeter è diventato ancora più inaffidabile, in particolare da quando i vari sistemi di storage possiedono cache o tier su SSD, oppure quando si usano soluzioni di server side caching. IOmeter non prevede la creazione di “hot spots”, come spiega perfettamente Howard Marks. Una volta creato il file di test da alcuni GB, IOmeter legge e scrive uniformemente tutto questo file. Non vi è quindi la possibilità di avere un blocco di dati “nuovo” che il sistema di caching non abbia mai visto, e quindi simulare una “read miss”.
Un’altra metodologia, spesso citata quando si parla di ambienti VMware, è VMmark. Realizzato direttamente da VMware, configura una serie di virtual machine con vari applicativi a bordo (Exchange Server, Web Server, Application server vari…) sulle quali vengono poi eseguite attività tipiche. Sicuramente è quanto di più realistico si possa usare a parte un vero ambiente produttivo, ma di contro la sua configurazione è impegnativa e lunga da realizzare, e richiede un numero elevato di virtual machines.
Per ovviare a questi limiti, ho deciso di seguire una strada differente e ho creato una mia personalissima soluzione. Non ho la pretesa che questa sia la migliore, per carità. Ma a mio avviso è un modo molto semplice di realizzare test sufficientemente affidabili, e soprattutto offre la possibilità di replicarli in vari ambienti con poco sforzo, e poterli quindi comparare.
Nel mio laboratorio utilizzo uno storage NetApp FAS2020, del quale potete leggere caratteristiche dettagliate nella pagina dedicata. Per avere un riferimento iniziale, ho eseguito le varie prove con i differenti software su questo storage. Nel futuro potrò quindi confrontare i vari risultati con questi.
La Virtual Machine
La mia soluzione si basa su una singola virtual machine Microsoft Windows Server 2008 R2 Standard; questa è dotata di 4 vCPU configurate come 1 socket e 4 core, 4 GB di RAM e un disco thick da 30 Gb, più un disco secondario da 350 Gb dove eseguire i test. La presenza di tante vCPU e un disco così grande è dettata dall’assoluta necessità di creare una quantità di dati e I/O per riuscire a saturare la cache dei vari storage e dei dischi SSD eventualmente montati sui server ESXi usati dai vari software di Server-Side Caching, altrimenti i dati stessi non vengono mai letti o scritti sui dischi e quindi i risultati finali sono troppo elevati, e non veritieri.
La versione del virtual hardware è 9, e sistema operativo e VMware tools sono aggiornati a Novembre 2013. Per mantenere costanti i risultati nel tempo, non effettuo nessun update successivo.
Infine, ho esportato la VM in formato OVA, per poterla installare in altri ambienti.
FIO
Ho scoperto FIO (Flexible IO tester) grazie a una segnalazione da parte dei ragazzi di Fusion-IO (oltretutto l’abbreviazione sia del tool che della società è il medesimo, quindi… :D). Anche se è molto meno conosciuto, dopo averlo provato posso dire con certezza che è molto migliore di IOmeter. Innanzitutto, il suo codice è continuamente aggiornato, e al momento in cui ho scritto questo articolo l’ultima versione era la 2.1.2, rilasciata il 7 Agosto 2013. Se ci pensate, l’ultimo IOmeter è del 2006… Potete utilizzarlo sia su linux che su Windows, per il quale è disponibile un porting della penultima versione 2.1.1 a questo indirizzo.
FIO possiede alcune configurazioni tramite le quali si possono generare differenti file binari su cui lavorare, mixare l’IO tra di essi e accedervi in modo completamente random; il tutto al fine di generare quanta più entropia sullo storage e quindi metterlo in crisi quanto più possibile.
FIO è utilizzabile da riga di comando, si possono passare i vari parametri tramite dei file di configurazione semplicemente eseguendo “fio config_file“. Ho realizzato diverse prove prima di ottenere un risultato soddisfacente, potete prendere questa configurazione come esempio se volete eseguire i vostri test. Questi file di configurazione sono realizzati per la versione Windows, in caso voleste usarli su linux vanno modificati. Potete anche variare i valori di IO depth e numero di jobs per vedere come i valori cambino. Ecco i vari files (cambiate l’estensione in .fio prima di usarli)
FIO Max Real I/O: 100% read, 100% sequential, Block Size 8k, IO depth 32, 16 jobs
FIO Max Bandwidth: 100% read, 100% sequential, Block size 1M, IO depth 32, 16 jobs
FIO Real Life Test: 80% read, 100% random, Block Size 8k, IO depth 32, 16 jobs
Con questi test, il mio storage NetApp FAS2020 ha ottenuto Max I/O 12717 IOPS, e Max Bandiwidth 199,57 MBs, mentre nel Real Test ha raggiunto 2800 IOPS, con una bandwidth di 22.40 MBs e una latenza media di 181 ms.
Ho anche provato per curiosità a produrre un risultato totalmente stupido, ovvero il massimo IO ottenibile, impostando il block size a 512 byte. Il mio NetApp è arrivato a oltre 23.000 IOPS. Semplicemente innalzando il blocksize a 8k il valore scende a 12717 IOPS. Ecco un altro esempio del perchè ci servono test che abbiano senso.
JetStress
JetStress è lo strumento ufficiale di Microsoft per effettuare simulazioni del carico di lavoro di un Exchange Server. Rispetto all’altro tool disponibile (LoadGen) non richiede la presenza di un Exchange Server installato e configurato per poter realizzare i test. Ho scelto di utilizzare la versione 2010 anche se è già disponibile la versione 2013, dal momento che sono molto più diffusi sistemi Exchange 2010 che 2013, quindi il test può essere ad oggi più interessante. In questo tutorial è spiegato in modo dettagliato come installarlo e configurarlo.
Una volta installato, il suo utilizzo è molto semplice e immediato. Avviamo direttamente la versione grafica del programma (usando “Run as Administrator”) e scegliamo di iniziare un nuovo test. Abbiamo a disposizione numerose opzioni di configurazione; io ho creato un test di tipo performance, che potete riprodurre anche voi utilizzando questi parametri:
La durata minima di un test è 2 ore, e durante questo periodo JetStress simula continuamente le varie attività di un Exchange Server. Possiamo leggere infatti dal log informazioni come:
Operation mix: Sessions 8, Inserts 40%, Deletes 20%, Replaces 5%, Reads 35%, Lazy Commits 70%.
Vedete quindi come le attività sono multi-thread, e prevedono scritture, update, letture, cancellazioni in varie percentuali. Una volta ultimato il test, il risultato che ci viene sottoposto è questo (ho rimosso alcuni dettagli che non servono ai nostri scopi):
Microsoft Exchange Jetstress 2010
Performance Test Result Report
Complessivamente, è un test molto affidabile per mettere sotto stress il nostro storage. Come vedete, da un risultato “puro” di FIO di 2800 IOPS, siamo scesi a 1013, semplicemente utilizzando un worklaod più “reale”.
HammerDB
Ho cercato per diverso tempo un tool che permettesse di simulare un database server. Non contate su Microsoft: c’è un loro tool denominato SQLio, che con SQL però non ha nulla a che fare, ed è un semplice tool di I/O benchmark, come IOmeter o FIO. Vi è poi SQLioSim, che è si un simulatore SQL ma con l’I/O non c’entra assolutamente nulla, dato che punta a verificare la resistenza di uno storage all’introduzione di errori voluti nei database, e genera un pattern di I/O troppo randomico che rende ogni ripetizione del test differente dalla precedente.
Stesso problema per Oracle: esiste Orion, ma alla fine è un’altro simulatore di I/O, anche se specifico per Oracle, e oltretutto alcuni link interni al sito del produttore non funzionano… Esiste in alternativa SLOB, ma da diversi mesi i binari non sono più scaricabili e l’autore non ha dato più risposte sul suo blog circa questo problema… (AGGIORNAMENTO: l’autore di SLOB2, Kevin Closson, ha corretto il link rotto, potete recuperare il suo tool qui).
Ho scelto alla fine HammerDB. Richiede l’installazione di un database server completo per eseguire i test, ma il lavoro è facilitato dalla possibilità di utilizzare le versioni free dei vari database, e dalla disponibilità di una comoda guida per i più diffusi database che si volessero usare. Inoltre, HammerDB è disponibile sia per Linux che per Windows, e questo mi ha permesso di mantenere una unica VM per tutti i test.
Seguendo la guida indicata, ho provveduto a installare e configurare PostgreSQL. Il vantaggio rispetto all’uso di Microsoft SQL Server Express o Oracle Express è di non avere alcuna limitazione sull’uso di CPU o RAM, PostgreSQL è completamente free e può essere spinto fino al limite della macchina su cui viene eseguito.
Installato il database server e HammerDB, possiamo passare ai test. HammerDB permette di realizzare un completo test OLTP basato sulle specifiche TPC-C, e questo rende il tool molto vantaggioso. Si possono infatti ottenere valori comparabili tra sistemi differenti. Esistono diverse guide che aiutano a realizzare i test TPC-C, io ho utilizzato la versione per PostgreSQL. Questo documento oltretutto è un’ottima occasione per imparare molte cose sui test TPC-C.
Per realizzare i test, HammerDB deve essere installato su un differente sistema rispetto al database server, ho avviato quindi i tests da un’altra macchina del mio laboratorio, ospitata su un differente sistema di storage, e tramite vMotion ho provveduto a separare le due VM su due hosts differenti.
I test possono essere configurati con differenti parametri. Utilizzando una VM con 4 vCPU, ho configurato 100 Warehouses (5 ogni vCPU, arrotondati al 100 superiore) e 10 Virtual Users, 1 ogni 10 Warehouses. Non sono alla ricerca della migliore prestazione assoluta con TPC-C, ma unicamente di una configurazione riutilizzabile e comparabile in differenti condizioni.
L’obiettivo finale di TPC-C è valutare le capacità transazionali di un database server. HammerDB ci restituisce il valore di TPM, ovvero di Transactions per Minute, unitamente al valore NOPM, ovvero Number of Orders per Minute. Dovete sapere infatti che TPC-C simula un database per la gestione degli ordini di un’azienda…
La mia VM di test eseguita sul FAS2020 ha ottenuto 17790 TPM e 7845 NOPM, e come si vede dal grafico, la cache del controller ha avuto i suoi bei problemi a tentare di garantire un flusso di I/O costante. A fronte di un picco di 28896 TPM, si sono visti anche valori molto inferiori:
Conclusioni
I test prestazionali sono un’arte molto difficile da padroneggiare. Spesso si rischia di ottenere dei valori che hanno unicamente senso nell’ambiente di test in cui vengono svolti, specie se sono dei laboratori “casalinghi” come il mio. Ci sono sempre in agguato colli di bottiglia a livello di CPU, Memoria, Disk Controller, Rete, che possono falsare i risultati ottenuti sullo storage, e dare in ultima analisi informazioni sbagliate ai lettori. Esistono laboratori specializzati in queste attività, e se nemmeno loro sono perfetti, figuriamoci il mio lab.
Per questo motivo, non prendete i miei risultati o quelli di altri blogger come valori assoluti, anche se alcuni di loro diranno il contrario. Piuttosto, prendete spunto da questi test che ho fatto per realizzare i VOSTRI test, e soprattutto fare in modo che questi siano ripetibili anche su sistemi differenti, in momenti differenti.