<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>/dev/zero</title>
	<atom:link href="http://www.devzero.it/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.devzero.it</link>
	<description>Unix power @ your service</description>
	<lastBuildDate>Fri, 16 Mar 2012 08:47:22 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=</generator>
		<item>
		<title>Sistemi Operativi: vmbo</title>
		<link>http://www.devzero.it/2012/03/sistemi-operativi-vmbo/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=sistemi-operativi-vmbo</link>
		<comments>http://www.devzero.it/2012/03/sistemi-operativi-vmbo/#comments</comments>
		<pubDate>Thu, 15 Mar 2012 09:34:49 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Software]]></category>
		<category><![CDATA[University]]></category>
		<category><![CDATA[belady]]></category>
		<category><![CDATA[fault]]></category>
		<category><![CDATA[I/O]]></category>
		<category><![CDATA[località]]></category>
		<category><![CDATA[locality]]></category>
		<category><![CDATA[mmu]]></category>
		<category><![CDATA[page]]></category>
		<category><![CDATA[thread]]></category>
		<category><![CDATA[virtual memory]]></category>
		<category><![CDATA[vm]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=219</guid>
		<description><![CDATA[Continua la serie di progetti sviluppati a scopi didattici per l&#8217;Università di Urbino &#8220;Carlo Bo&#8221;. Specifica del problema Scrivere un programma multithread che consenta di valutare le performance, in termini di numero di page fault, di algoritmi di rimpiazzamento delle pagine per la gestione della memoria virtuale. Il programma dovrà essere costituito da un’entità principale [...]]]></description>
			<content:encoded><![CDATA[<p>Continua la serie di progetti sviluppati a scopi didattici per l&#8217;Università di Urbino &#8220;Carlo Bo&#8221;.</p>
<h2>Specifica del problema</h2>
<p>Scrivere un programma multithread che consenta di valutare le performance, in termini di numero di <em>page fault</em>, di algoritmi di rimpiazzamento delle pagine per la gestione della memoria virtuale.<br />
<span id="more-219"></span><br />
Il programma dovrà essere costituito da un’entità principale che operi come una Memory Management Unit (MMU), un numero arbitrario (<em>n</em>) di thread, ove ogni thread emuli un singolo processo (PROCESSO) e, infine, da un’entità che emuli un dispositivo di I/O (DISPOSITIVO I/O).</p>
<p>Il programma dovrà simulare una sessione di lavoro, nella quale sono presenti <em>n</em> processi che possono accedere alla memoria e generare richieste di I/O. I processi dovranno generare indirizzi di memoria casuali. Infine, il programma terminerà una volta raggiunto il numero prestabilito di accessi in memoria totali.</p>
<h3>MMU</h3>
<p>L’entità MMU sarà la base del sistema ed utilizzerà l’algoritmo di rimpiazzamento delle pagine oggetto di test. Essa dovrà essere istanziata dal thread principale (<em>main</em>) e sarà gestita come oggetto condiviso tra i diversi thread dei PROCESSI. In particolare essa definirà la dimensione dello spazio di indirizzamento virtuale, la dimensione della memoria fisica disponibile e la dimensione della pagina.</p>
<p>La MMU dovrà, inoltre, contenere una lista di tabelle della pagine ciascuna relativa ad un PROCESSO. La definizione della specifica delle tabelle delle pagine sarà lasciata allo studente, e naturalmente dipenderà dal particolare algoritmo di rimpiazza mento implementato.</p>
<p>I PROCESSI dovranno generare indirizzi verso la MMU invocandone un metodo pubblico.</p>
<p>L’accesso a tale metodo dovrà garantire la mutua esclusione (un solo PROCESSO alla volta potrà invocare il suddetto metodo. La mutua esclusione dovrà essere ottenuta utilizzando le primitive di sincronizzazione messe a disposizione dal linguaggio di programmazione eccezion fatta per il costrutto monitor (per chiarezza, ad esempio, in java non sarà possibile utilizzare il costrutto <em>synchronized</em>) .</p>
<p>Il metodo in questione processerà la richiesta andando ad interrogare l’opportuna tabella delle pagine. Nel caso in cui, l’indirizzo generato sia relativo ad una pagina già mappata in memoria la MMU si limiterà ad incrementare un contatore statistico di <em>page hit</em>. D’altra parte, nel caso in cui l’indirizzo generato dal PROCESSO faccia riferimento ad un indirizzo contenuto in una pagina non mappata in memoria la MMU dovrà eseguire i seguenti passi:</p>
<ul>
<li>incrementare un contatore di <em>page fault</em></li>
<li>selezionare una pagina mappata da rimuovere (vittima) secondo la politica dell’algoritmo oggetto di test.</li>
<li>aggiornare le opportune tabelle delle pagine</li>
<li>indicare come non valida la pagina che è appena stata rimossa.</li>
<li>inserire una nuova entry nella tabella delle pagine del PROCESSO che ha</li>
<li>generato il <em>page fault</em> (la pagina è stata appena caricata).</li>
</ul>
<h3>PROCESSO</h3>
<p>L’entità PROCESSO dovrà emulare un processo in esecuzione su di un sistema multi programmato. Ogni processo dovrà essere emulato attraverso l’utilizzo di un singolo thread. Lo scheduling dei thread sarà delegato alle librerie messe a disposizione dal linguaggio di programmazione (configurazione default).</p>
<p>Il comportamento di ogni PROCESSO può essere descritto da una macchina a stati finiti comprendente due soli stati mutuamente esclusivi:</p>
<ul>
<li>Richiesta indirizzo di memoria (invocazione del metodo pubblico della MMU).</li>
<li>Richiesta operazione di I/O (invocazione del metodo pubblico del DISPOSITIVO di I/O).</li>
</ul>
<p>Le transizioni tra i due stati dovranno essere gestire in maniera probabilistica. In particolare, dovrà essere definita una probabilità <em>p</em> (input fornito al momento del lancio dell’applicazione) di generare indirizzi di memoria (“entrare nello stato a dato che ci si trovava nello stato b” = “rimanere nello stato a”) e una probabilità <em>q = 1-p</em> di generare richieste di I/O (“entrare nello stato b dato che ci si trovava nello stato a” = “rimanere nello stato b”)</p>
<p>I PROCESSI dovranno prevedere la possibilità di essere inizializzati con diversi valori di probabilità <em>p</em>.</p>
<h3><strong>DISPOSITIVO di I/O</strong></h3>
<p>L’entità DISPOSITIVO di I/O dovrà essere gestita come un ulteriore thread. Questa avrà un metodo pubblico attraverso il quale i PROCESSI potranno effettuare una richiesta di I/O.</p>
<p>Le richieste di I/O dovranno essere gestite con un coda di tipo FIFO. Le richieste saranno, ovviamente, bloccanti, mettendo il PROCESSO chiamante in uno stato di attesa fino al soddisfacimento della richiesta.</p>
<p>Il DISPOSITIVO di I/O determinerà il tempo di servizio di ciascuna richiesta in modo casuale estraendo a caso un valore intero, espresso in millisecondi, compreso fra <em>Tmin</em> e <em>Tmax</em> (parametri di inizializzazione del DISPOSITIVO di I/O).</p>
<h3><strong>Dati di INPUT</strong></h3>
<p>Il programma dovrà ricevere in input i seguenti parametri di inizializzazione:</p>
<ul>
<li>Numero di PROCESSI</li>
<li>Probabilità p di generare accessi in memoria (una p per ogni PROCESSO; la probabilità di accedere al dispositivo di I/O sarà pari a 1-p)</li>
<li>Tempi di servizio minimi e massimi del DISPOSITIVO di I/O (<em>Tmin</em> e <em>Tmax</em>).</li>
<li>Numero totale di accessi in memoria raggiunto il quale il programma dovrà terminare.</li>
</ul>
<h3><strong>Dati di OUTPUT</strong></h3>
<p>Al termine della simulazione il programma dovrà stampare a video la percentuale di <em>page fault</em> totale (relativa a tutti i processi), la percentuale di <em>page fault</em> relativa a ciascun PROCESSO, il tempo medio di servizio del DISPOSITIVO di I/O ed il tempo medio di attesa per una richiesta di I/O relativo a ciascun PROCESSO.</p>
<p>Ciascun PROCESSO dovrà scrivere in un proprio file di log la successione di indirizzi generata e le chiamate al dispositivo di I/O.</p>
<h2>Analisi del problema</h2>
<p>Il problema richiede di realizzare un simulatore elementare di memoria virtuale, utile all’analisi del comportamento e relative prestazioni di un algoritmo di rimpiazzo delle pagine. Il sistema realizzato simulerà un ambiente di lavoro multi programmato, nel quale operano più processi contemporaneamente.</p>
<p>Un’analisi iniziale ci suggerisce che questo problema sia di tipo <strong>decidibile</strong>, ovvero presuppone l’esistenza di un algoritmo che lo risolva in tempo finito e per una qualunque istanza di dati, espressa in termini di numero di processi contemporanei, dimensione della pagina e così via.</p>
<p>Come da specifica, il simulatore non avrà bisogno di alcun dato di ingresso per funzionare. Un insieme esteso di parametri da riga di comando permetterà di alterare alcuni aspetti e funzionalità del simulatore.</p>
<p>L’output del programma sarà costituito da alcuni dati statistici, prodotti a seguito del numero prestabilito di accessi alla memoria.</p>
<h2>Progettazione dell&#8217;algoritmo</h2>
<p>La scelta della struttura dati e del relativo algoritmo tiene conto dei parametri dettati dalla specifica del problema: l’attenzione sarà dunque focalizzata sulla politica di rimpiazzo delle pagine, sulle strutture dati necessarie ed sullo scenario che tali scelte determinano; l’analisi non terrà quindi in considerazione l’impatto che il <em>paging</em> nella memoria secondaria possa avere sull’efficienza complessiva del sistema, né dei tempi d’accesso alla memoria o di caricamento di una pagina.</p>
<p>Si è scelto di articolare il programma in tre fasi distinte:</p>
<ol>
<li>analisi dei parametri forniti su riga di comando: di particolare rilievo, la possibilità di modificare alcuni parametri di funzionamento del simulatore;</li>
<li>inizializzazione delle strutture dati e successiva esecuzione dei singoli thread;</li>
<li>attesa del completamento dei thread, relativa deallocazione delle strutture dati e successiva stampa delle statistiche.</li>
</ol>
<h3><strong>Descrizione del simulatore</strong></h3>
<p>Un sistema dotato del meccanismo di memoria virtuale consente ad un processo di allocare una quantità di memoria superiore a quella effettivamente disponibile. La tecnica si basa sull’utilizzo di altri tipi di memoria, detta <em>secondaria</em>, che entrano in gioco quando la memoria fisica risulta piena. Il meccanismo di memoria virtuale implementato per il simulatore è quello della <strong>paginazione</strong>.</p>
<p>La paginazione prevede la suddivisione della memoria fisica in <em>frame</em>, tutti della stessa dimensione; analogamente, anche la memoria allocata da un processo viene diviso in <em>pagine</em>, la cui dimensione è pari a quella di un frame di memoria fisica: tale suddivisione avviene ad opera della mmu, in modo totalmente trasparente al processo utente.</p>
<p>Al pari di un sistema operativo, il simulatore terrà aggiornata una tabella dei processi attivi: ogni voce nella tabella è rappresentativa di un processo e delle pagine virtuali allocate.</p>
<div>
<p>Per semplicità, si suppone che la tabella dei processi e la relativa page table siano sempre residenti in memoria, ovvero che queste non vengano mai paginate a loro volta.</p>
</div>
<p>Perché un processo possa accedere ad un’informazione contenuta in una determinata pagina virtuale, è necessario che quest’ultima sia presente nella memoria fisica ovvero, nello specifico, che sia associata ad un frame. Quando la lista dei frame disponibili non è esaurita, sarà sufficiente associare la pagina richiesta ad un frame disponibile; nel caso contrario, si dovrà applicare una politica di rimpiazzo delle pagine, volta a selezionare una pagina tra quelle presenti in memoria, spostarla nella memoria secondaria e associare il frame appena liberato alla pagina richiesta.</p>
<p>L’algoritmo di rimpiazzo delle pagine scelto è l’<strong>enhanced </strong><strong>second chance</strong>, noto anche come <em>algoritmo dell’orologio</em>: tale soluzione nasce come una naturale evoluzione della tecnica fifo, superando il problema di rimuovere le pagine usate più di frequente.</p>
<p>La realizzazione di tale algoritmo impone che ogni pagina contenuta nella <em>page table</em> del processo, oltre le comuni informazioni, debba contenere due ulteriori bit:</p>
<ul>
<li>bit <em>reference</em> (R): verrà posto al valore uno (1) quando si accederà alla pagina in questione, sia in scrittura che lettura: tale informazione permetterà di sapere se ad una pagina presente in memoria si sia acceduto di recente o meno;</li>
<li>bit <em>dirty</em> (D): verrà posto ad uno (1) quando si accederà alla pagina  in scrittura: quando una pagina dovrà essere rimossa dalla memoria, il valore uno di questo bit suggerirà al sistema operativo di fare una copia della pagina nella memoria secondaria, prima della rimozione dalla memoria principale.</li>
</ul>
<p>La ricerca della pagina virtuale da rimuovere dovrà tenere conto delle quattro possibili combinazioni ottenute con questi due bit:</p>
<p>&nbsp;</p>
<div>
<table width="316" border="1" cellspacing="0" cellpadding="0">
<tbody>
<tr>
<td width="18">
<p align="center"><strong>r</strong></p>
</td>
<td width="18">
<p align="center"><strong>d</strong></p>
</td>
<td width="137">
<p align="center"><strong>descrizione</strong></p>
</td>
<td width="142">
<p align="center"><strong>azione</strong></p>
</td>
</tr>
<tr>
<td width="18">
<p align="center">0</p>
</td>
<td width="18">
<p align="center">0</p>
</td>
<td width="137">
<p align="center"><em>la pagina non è stata usata di recente e non è stata modificata</em></p>
</td>
<td width="142">
<p align="center"><em>rimpiazza la pagina</em></p>
</td>
</tr>
<tr>
<td width="18">
<p align="center">0</p>
</td>
<td width="18">
<p align="center">1</p>
</td>
<td width="137">
<p align="center"><em>la pagina non è stata usata di recente ma è stata modificata</em></p>
</td>
<td width="142">
<p align="center"><em>effettua un </em><em>write </em><em>back della pagina e imposta ad zero il bit D</em></p>
</td>
</tr>
<tr>
<td width="18">
<p align="center">1</p>
</td>
<td width="18">
<p align="center">0</p>
</td>
<td width="137">
<p align="center"><em>la pagina è stata usata di recente ma non è stata modificata</em></p>
</td>
<td width="142">
<p align="center"><em>imposta a zero il bit R</em></p>
</td>
</tr>
<tr>
<td width="18">
<p align="center">1</p>
</td>
<td width="18">
<p align="center">1</p>
</td>
<td width="137">
<p align="center"><em>la pagina è stata usata di recente ed è stata modificata</em></p>
</td>
<td width="142">
<p align="center"><em>imposta a zero il bit R ed effettua il </em><em>write</em><em> </em><em>back della pagina</em></p>
</td>
</tr>
</tbody>
</table>
</div>
<div></div>
<div>
<p>La ricerca della pagina migliore non solo si traduce nella selezione della pagina non usata di recente, ma anche di quella che non sia stata modificata. In questo modo, le pagine utilizzate più di frequente hanno alta probabilità di rimanere nella memoria principale, a discapito delle pagine a cui si è acceduto meno frequentemente.</p>
<p>Quando una pagina presente in memoria risulta <em>sporca</em>, si dovranno quindi effettuare due operazioni di I/O: il primo accesso alla memoria secondaria sarà necessario per effettuare il <em>page out</em>, ovvero copiare la pagina <em>sporca</em> sul disco, mentre una seconda operazione di lettura sarà necessaria per il <em>page in</em> della pagina che ha generato il <em>fault</em>. In questo scenario, l’algoritmo scelto, analizzando periodicamente le pagine che risultano <em>sporche</em> e provvedendo ad un preventivo <em>write back</em> nella memoria secondaria, migliora sensibilmente le prestazioni complessive, nonché il tempo medio d’accesso alla memoria.</p>
<p>Tale algoritmo, tuttavia, ha lo svantaggio di partizionare l’insieme delle pagine in due classi: quelle usate di recente e quelle usate con minor frequenza; quando termina la ricerca per il rimpiazzo, non è detto che la pagina identificata sia la più vecchia in assoluto, ma semplicemente una delle pagine meno utilizzate di recente.</p>
<p>Il caso migliore si verifica quando il primo frame analizzato ha i bit R e D posti a zero: la ricerca termina immediatamente e non sarà nemmeno necessaria un’operazione di I/O volta a fare una copia della pagina nella memoria secondaria.</p>
<div>
<p><em>Come da requisito, i processi effettuano soltanto l’operazione di lettura della memoria: è tuttavia possibile alterare questo comportamento specificando il parametro “–w” da riga di comando, per ottenere una simulazione che prevede l’uso del bit dirty.</em></p>
</div>
<p>Il caso peggiore dell’<em>enhanced</em> <em>second</em><em> chance</em> si verifica quando tutte le pagine residenti in memoria sono sia referenziate che modificate: in questo caso, l’MMU dovrà necessariamente scorrere interamente la lista delle pagine presenti, ottenendo la medesima complessità dell’algoritmo fifo.</p>
<p>Da tali considerazioni, è facilmente comprensibile che la complessità dell’algoritmo sia <em>O(n)</em>, ovvero lineare e proporzionale al numero di frame in cui è stata suddivisa la memoria.</p>
<p>Non meno importante è sottolineare che, essendo un’evoluzione della tecnica fifo, tale approccio soffre dell’anomalia di Belady (si veda a tal proposito il test 7).</p>
<p>Nei sistemi moderni, alcune funzionalità utili all’implementazione di tale algoritmo vengono implementate direttamente dall’hardware, quale, ad esempio, l’impostazione ad uno del bit <em>reference</em> e <em>dirty</em> ogni qualvolta una pagina venga referenziata o modificata.</p>
<p>Un algoritmo di rimpiazzo può essere di tipo <em>locale</em> o <em>globale</em>: il simulatore proposto effettua una ricerca <strong>globale</strong>, ovvero quando avviene un <em>page fault</em>, l’MMU cercherà la pagina candidata alla rimozione dalla memoria tra le pagine di tutti i processi attivi e non limitandosi alle pagine allocate del processo corrente. Sebbene una ricerca locale prevenga influenze da parte degli altri processi in termini di <em>page fault</em>, un algoritmo globale risulta complessivamente più efficiente nonché più semplice da implementare.</p>
<p>La modalità di generazione degli indirizzi, ad opera dei processi utente, è in linea con il <strong>principio di località</strong>, secondo cui se la CPU sta accedendo ad uno specifico dato (o istruzione), con molta probabilità i prossimi dati (o istruzioni) saranno ubicati nelle vicinanze di quella in corso: valutare tale principio ed i suoi impatti è di fondamentale importanza per il funzionamento e le prestazioni della memoria virtuale gerarchica dei moderni sistemi.</p>
<p>È stato, in ultimo, scelto un approccio di tipo <strong>pure </strong><strong>demand paging</strong>, il quale prevede di non assegnare alcun frame al processo fintanto che la pagina non venga referenziata.</p>
<p>I vantaggi di tale tecnica sono immediatamente percepibili:</p>
<ul>
<li>le pagine inutilizzate non vengono mai caricate in memoria, aumentando la quantità di memoria disponibile ad altri processi;</li>
<li>all’avvio di un programma, viene ridotta la latenza necessaria a caricare le pagine in memoria;</li>
<li>minor carico di I/O dovuto ad un minor numero di pagine da caricare.</li>
</ul>
<p>In presenza di un sistema con poca memoria fisica disponibile, il <em>demand paging</em> assicura un grado più elevato di concorrenza di processi.</p>
<div>
<p>Per semplicità, si è assunto che le pagine contenenti le istruzioni del processo siano sempre residenti in memoria: soltanto le pagine contenenti dati verranno gestite dalla MMU e dalla suddetta politica di rimpiazzo.</p>
</div>
<p><em>Il sistema emulato farà uso di indirizzi a 20 bit: da un punto di vista fisico, un simile spazio di indirizzamento consente di gestire una memoria fisica composta, al massimo, da 1,048,576 byte: il simulatore sarà appunto dotato di questo quantitativo, sebbene sia possibile alterare tale aspetto con l’opportuno parametro da riga di comando (-R).</em></p>
<p><em></em><br />
Anche i processi utente utilizzano un indirizzamento a 20 bit; lo spazio d’indirizzamento virtuale sarà ovviamente superiore a quello fisico in quanto si dovrà considerare anche la memoria secondaria. Sono dunque possibili due scenari che, in assenza del meccanismo di memoria virtuale, non potrebbero sussistere:</p>
<ul>
<li>più processi contemporanei, ognuno dei quali alloca il massimo della memoria fisica: la somma di tutti gli spazi d’indirizzamento risulta maggiore della memoria fisica;</li>
<li>un sistema dotato di una quantità ridotta di memoria fisica ma che consente ugualmente ad un processo di allocare 1Mb di memoria virtuale.</li>
</ul>
<p>Un indirizzo virtuale a 20 bit generato da un processo sarà suddiviso, in modo del tutto trasparente, in due parti distinte: i otto bit più significativi (da 19° al 12°) verranno usati come indice per consultare la <em>page table</em> del processo, mentre i restanti dodici bit rappresenteranno l’offset da sommare all’indirizzo di partenza del frame associato.</p>
</div>
<div><img class="aligncenter  wp-image-223" title="address" src="http://www.devzero.it/wp-content/uploads/2012/03/address.png" alt="" width="412" height="169" /></div>
<div>
<p>Una simile suddivisione consente ad ogni processo di allocare un massimo di 256 pagine virtuali (2<sup>8</sup>), la cui dimensione è pari a 4,096 byte (2<sup>12</sup>): ovviamente il numero di pagine virtuali disponibili per un processo è indipendente dal numero di frame disponibili.Qualora il rapporto tra i frame disponibili ed il numero massimo di processi concorrenti risulti vantaggioso, il programma attiverà automaticamente la <strong>paginazione anticipata</strong>: l’MMU, infatti, non si limiterà a caricare in memoria la pagina mancante, causa del <em>fault</em>, ma anche un ristretto numero di pagine adiacenti. In pratica il simulatore cerca di prevedere quali pagine saranno richieste in virtù della località dei dati e le carica prima di quando queste vengano effettivamente richieste.</p>
<div>
<p><em>La suddetta funzionalità è da considerarsi puramente dimostrativa ed embrionale.</em></p>
<p>Di seguito vengono riassunte le scelte progettuali che caratterizzano il simulatore.</p>
<table border="1" cellspacing="0" cellpadding="0">
<tbody>
<tr>
<td colspan="2" valign="top" width="253">
<p align="right"><strong>Hardware</strong></p>
</td>
</tr>
<tr>
<td width="113">
<p align="left">Dimensione indirizzo</p>
</td>
<td width="140">
<p align="right"><em>20 bit</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Dimensione RAM</td>
<td valign="top" width="140">
<p align="right"><em>1,048,576 byte</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Dimensione frame</td>
<td valign="top" width="140">
<p align="right"><em>4,096</em></p>
</td>
</tr>
<tr>
<td colspan="2" width="253">
<p align="right"><strong>Memoria virtuale</strong></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Tipo</td>
<td valign="top" width="140">
<p align="right"><em>paginata</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Politica di rimpiazzo</td>
<td valign="top" width="140">
<p align="right"><em>enhanced second chance</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Dimensione pagina</td>
<td valign="top" width="140">
<p align="right"><em>4,096</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Page table</td>
<td valign="top" width="140">
<p align="right"><em>sempre in memoria</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">
<p align="left">Max pagine/processo</p>
</td>
<td valign="top" width="140">
<p align="right"><em>256</em></p>
</td>
</tr>
<tr>
<td colspan="2" valign="top" width="253">
<p align="right"><strong>Dispositivo I/O</strong></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Tmin</td>
<td valign="top" width="140">
<p align="right"><em>1</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Tmax</td>
<td valign="top" width="140">
<p align="right"><em>100</em></p>
</td>
</tr>
<tr>
<td colspan="2" valign="top" width="253">
<p align="right"><strong>Processo<em></em></strong></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Probabilità accesso</td>
<td valign="top" width="140">
<p align="right"><em>80%</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Località temporale</td>
<td valign="top" width="140">
<p align="right"><em>30%</em></p>
</td>
</tr>
<tr>
<td valign="top" width="113">Località spaziale</td>
<td valign="top" width="140">
<p align="right"><em>Loop su un vettore </em></p>
</td>
</tr>
</tbody>
</table>
<h2> Descrizione moduli</h2>
<p>Di seguito verranno descritti,  con maggiore dettaglio, gli aspetti implementativi dei singoli moduli: l’MMU, il dispositivo di I/O ed il processo.</p>
<p style="text-align: center;"><img class="aligncenter  wp-image-224" title="modules" src="http://www.devzero.it/wp-content/uploads/2012/03/modules.png" alt="" width="430" height="185" /></p>
<p>Ogni singolo modulo del simulatore viene inizializzato direttamente dal <em>main()</em> attraverso le rispettive funzioni e sulla base dei parametri specificati da riga di comando. Terminata questa fase, inizierà l’interazione tra i singoli thread.</p>
<h3>Memory Management Unit (MMU)</h3>
<p>Il thread che emula l’MMU è il primo ad essere istanziato dal simulatore, direttamente all’interno del <em>main</em>: questo si occupa della traduzione di un indirizzo virtuale, generato da un processo, in un equivalente indirizzo fisico di memoria.</p>
<p>La funzione mmu_init è incaricata di configurare l’ambiente del simulatore nonché di partizionare la memoria fisica in frame. Ad ogni frame verranno associate le seguenti informazioni:</p>
<ul>
<li><strong>id</strong>: tale valore identifica univocamente un frame;</li>
<li><strong>physical_addr</strong>: questa variabile conterrà l’indirizzo di memoria fisica di partenza del frame; durante il ciclo di vita del simulatore, la lista dei frame non sarà ordinata per <em>id</em>: questo è il valore di base cui sommare l’offset dell’indirizzo virtuale;</li>
<li><strong>valid</strong>: il bit verrà posto ad uno (1) quando il frame è utilizzato;</li>
</ul>
<p>Ad ogni frame vengono inoltre associate due ulteriori campi, <em>pid</em> e <em>page_id</em>: sebbene non siano necessari al funzionamento del simulatore, hanno il solo scopo di rendere più semplice il <em>debug</em>, nonché offrono la possibilità di mantenere un’associazione frame -&gt; processo -&gt; pagina.</p>
<p><img class="aligncenter size-full wp-image-225" title="frames" src="http://www.devzero.it/wp-content/uploads/2012/03/frames.png" alt="" width="326" height="195" /></p>
<p>&nbsp;</p>
<p>L’MMU fa uso di due liste semplici: la prima, free_frames, per tenere traccia dei frame liberi (ovvero non associati ad alcuna pagina) ed used_frames per i frame utilizzati. Terminata l’inizializzazione della memoria, tutti i frame saranno presenti nella lista free_frames, condizione dettata dal <em>demand paging</em>. Un’ulteriore lista, active_pages, conterrà solo le pagine presenti in memoria.</p>
<p>La funzione thread_mmu viene eseguita come thread e simula l’MMU: l’interazione tra questo thread ed i processi è resa possibile dalla funzione memory_read, invocata direttamente dai processi che tentano un accesso alla memoria. Quest’ultima si occuperà di inserire in una struttura temporanea i dati relativi al processo chiamante, nonché l’indirizzo virtuale richiesto e segnalerà alla MMU la presenza di una richiesta; l’MMU, nel vagliare la richiesta, sceglierà quale frame associare alla pagina equivalente ed, al termine, restituirà l’indirizzo di memoria fisico.</p>
<p>Di seguito verrà illustrato lo schema a blocchi del funzionamento della MMU.</p>
</div>
<div><img class="aligncenter  wp-image-227" title="mmu" src="http://www.devzero.it/wp-content/uploads/2012/03/mmu.png" alt="" width="358" height="366" /></div>
<div>
<table cellspacing="0" cellpadding="0">
<tbody>
<tr>
<td width="89" height="0"></td>
</tr>
<tr>
<td></td>
<td></td>
</tr>
</tbody>
</table>
<p><br clear="ALL" /> L’algoritmo <em>enhanced second chance</em> viene applicato solo quando la pagina richiesta non è presente in memoria ed, al contempo, tutti i frame risultano occupati. Ha quindi inizio una ricerca della pagina candidata alla rimozione: i due bit precedentemente descritti, <em>reference</em> e <em>dirty</em>, tengono traccia dell’uso e della modifica delle pagine.</p>
<div>
<p><em>L’algoritmo prevede che l’elenco delle pagine utilizzate sia rappresentato da una lista circolare, mentre è stata usata una lista doppiamente concatenata che, nel caso peggiore, viene visitata per intero.</em></p>
</div>
<h3>Processo</h3>
<p>La funzione thread_proc, eseguita come thread, si occupa di simulare un processo utente.</p>
<p>La rappresentazione in memoria del singolo processo, nonché delle caratteristiche che lo contraddistinguono, è affidata alla struttura proc. Avendo come riferimento un sistema operativo reale, al proprio interno, il simulatore gestisce una lista di tutti i processi attivi, detta <em>process table</em>: ogni voce in questa tabella è di tipo proc e contiene le seguenti informazioni:</p>
<ul>
<li><strong>pid</strong>: identificativo univoco del processo;<strong><em></em></strong></li>
<li><strong>tid</strong>: identificativo univoco del thread che simula il processo;<strong><em></em></strong></li>
<li><strong>page_count</strong>: numero di pagine virtuali allocate dal processo;<strong><em></em></strong></li>
<li><strong>page_table</strong>: tabella delle pagine del processo; questa informazione non deve essere accessibile al processo;<strong><em></em></strong></li>
<li><strong>percentile</strong>: probabilità del processo di effettuare un accesso alla memoria piuttosto che al dispositivo di I/O;<strong><em></em></strong></li>
<li><strong>io_cond/io_lock</strong>: condizione e relativo mutex nel quale il thread resta in attesa di completamento di una richiesta di I/O;<strong><em></em></strong></li>
<li><strong>log_file</strong>: file di log del processo;<strong><em></em></strong></li>
<li><strong>proc_stats</strong>: struttura per contenere le statistiche d’accesso del processo.<strong><em></em></strong></li>
</ul>
<p>Nei sistemi reali, un processo ha visibilità solo di alcune informazioni contenute nella <em>process table</em> o relative al sistema ospite: per esempio, un processo potrà sapere qual è il proprio pid o la dimensione della memoria virtuale, ma non potrà tuttavia accedere alla lista delle pagine o dei frame, informazioni ad unico appannaggio del sistema operativo. Seguendo le implementazioni dei più comuni sistemi *nix si è dunque scelto di non far gestire alla mmu la tabella delle pagine virtuali del processo, garantendo opportunamente la protezione dello spazio d’indirizzamento: l’mmu farà piuttosto uso di una propria struttura dati per gestire l’associazione delle pagine ai frame. Questa scelta trova ulteriore giustificazione nel fatto che ogni processo può allocare una quantità variabile di memoria e l’mmu, che viene inizializzata prima della <em>process table</em>, non può conoscere a priori tale quantità.</p>
<p>Poiché il simulatore non è stato implementato con un linguaggio orientato ad oggetti quale Java o C++, le api di accesso alla memoria ed al dispositivo di I/O devono contenere necessariamente l’identificativo del richiedente, nello specifico il pid.</p>
<p>La funzione proc_init ha il compito di creare <em>n </em>istanze del thread processo, per ognuno dei quali associa un numero casuale di pagine virtuali.</p>
<div>
<p><em>Il numero casuale di pagine virtuali è compreso tra 1 e 256, in modo tale che tutti i processi abbiano almeno una pagina associata e comunque non superiore al limite massimo di 256. È tuttavia possibile massimizzare tale valore per tutti i processi usando il parametro –M.</em></p>
</div>
<p>La funzione thread_proc, si occupa di scegliere se effettuare un accesso alla memoria o al dispositivo di I/O, scegliendo tra le due operazioni con una probabilità impostata dall’utente: quando la funzione memory_access, utilizzata per accedere alla memoria, restituirà il valore -1, i processi termineranno la propria esecuzione.</p>
<p>L’accesso in memoria osserva il principio di località, secondo cui:</p>
<ul>
<li>se accedo ad un dato, probabilmente accederò anche a quelli vicini in un tempo non lontano (<strong>località spaziale</strong>);</li>
<li>se accedo ad un dato è probabile che debba accedervi nuovamente in breve tempo (<strong>località temporale</strong>).</li>
</ul>
<p style="text-align: center;"><img class="aligncenter  wp-image-228" title="locality" src="http://www.devzero.it/wp-content/uploads/2012/03/locality.png" alt="" width="435" height="293" /></p>
<p>La realizzazione della località spaziale viene offerta dalla funzione simulate_loop che si occupa di simulare un accesso ad un vettore di <em>n</em> elementi: poiché in C gli elementi di un vettore occupano indirizzi di memoria contigui, simulare un accesso ad ognuno di essi coincide ad una località spaziale.</p>
<p>Quando il processo effettua invece un accesso pseudo casuale alla memoria, subentra la località temporale, ovvero la possibilità di accedere ad un dato recentemente utilizzato. In quest’ottica, il processo avrà il 30% di probabilità di accedere ad un indirizzo di memoria usato in precedenza.</p>
<div>
<p><em>Il parametro “–L” permette di variare la percentuale di località temporale, di default pari a 30%; ponendo uguale a zero tale valore, si elimina l’effetto di località.</em></p>
</div>
<p>L’operazione di lettura merita ulteriori considerazioni:</p>
<ol>
<li>nel caso di accesso alla memoria, l’indirizzo virtuale è generato casualmente, ma è sempre compreso nello spazio d’indirizzamento virtuale del processo: qualora l’indirizzo fuoriuscisse da tale spazio, il simulatore avrebbe il compito di generare un fault e terminare il processo;</li>
<li>per una migliore simulazione dell’algoritmo scelto, che prevede l’uso del bit <em>dirty</em>, è stata implementata l’operazione di scrittura in una zona di memoria: la funzione che realizza tale operazione è sempre memory_access ma con il parametro <em>rw</em> posto ad uno; non sarà tuttavia presente un parametro utile a rappresentare l’informazione da scrivere in memoria, in quanto esula lo scopo della presente analisi;</li>
<li>per entrambe le tipologie di accesso, alla memoria od al dispositivo di I/O, il processo non ha visibilità diretta dei rispettivi thread: la possibilità di effettuare una richiesta viene offerta dall’uso di due funzioni pubbliche che svolgono il ruolo di intermediario.</li>
</ol>
<p>Sussiste una sottile differenza tra i due tipi di accesso che un processo utente può effettuare: l’MMU rappresenta un oggetto condiviso tra più processi e può assolvere una richiesta per volta; se <em>n </em>processi tentassero l’accesso alla memoria, soltanto uno riuscirà nell’intento mentre gli altri “<em>n-1”</em> processi restano in attesa (mutua esclusione).</p>
<p>Di contro, l’accesso al dispositivo di I/O prevede che effettuare una richiesta d’accesso non sia bloccante, per cui se <em>n</em> processi tentassero l’accesso al dispositivo, tutti quanti riuscirebbero ad inserire la propria richiesta in coda: l’attesa avviene immediatamente dopo, non bloccando quindi gli altri attori della contesa, ma solo il processo che attende il risultato.</p>
<div>Di seguito viene illustrato il diagramma a blocchi del funzionamento del thread processo.</div>
</div>
<div><img class="aligncenter  wp-image-229" title="thread" src="http://www.devzero.it/wp-content/uploads/2012/03/thread-580x423.png" alt="" width="406" height="296" /></div>
</div>
<div></div>
<div>
<p>La prima condizione, <em>uscita</em>, viene soddisfatta quando la MMU ha effettuato il numero richiesto di accessi.</p>
<h2>Dispositivo di I/O</h2>
<p>Il dispositivo di I/O viene emulato dalla funzione thread_io_device, anch’essa eseguita come thread. Questo viene inizializzato ed istanziato immediatamente dopo aver creato il sottostrato di memoria virtuale.</p>
<p>Il funzionamento del dispositivo di I/O, a differenza della MMU, si basa su una lista di tipo fifo: i processi che effettuano una richiesta a tale dispositivo vengono inseriti in coda e serviti in modo sequenziale. La richiesta è di tipo bloccante: un processo, in attesa che la richiesta venga soddisfatta, non può effettuare altre operazioni.</p>
<p>La funzione io_device_read rappresenta il metodo pubblico per inserire una richiesta in coda, al pari di memory_access per le lettura in memoria.</p>
<p>La coda di richieste di I/O costituisce una risorsa condivisa tra il thread (<em>lettore</em>) e la funzione io_device_read (<em>scrittore</em>) ed, in tal senso, l’accesso alla fifo va gestito all’interno di una sezione critica: il mutex fifo_lock viene utilizzato dalle due entità al fine di mantenere coerente lo stato delle richieste.</p>
<p>Il thread terminerà la propria esecuzione su richiesta dell’MMU, quando questa avrà espletato il numero di richieste previsto.</p>
</div>
<div>Di seguito viene illustrato il diagramma a blocchi del dispositivo.</div>
<div><img class="aligncenter  wp-image-232" title="thread_io" src="http://www.devzero.it/wp-content/uploads/2012/03/thread_io.png" alt="" width="271" height="347" /></div>
<div>
<p>Come da specifica, il dispositivo viene configurato con due parametri, <em>Tmin</em> e <em>Tmax</em>, rispettivamente il tempo minimo e massimo perché una richiesta di lettura venga effettuata; il thread, una volta esaminata la richiesta, si occuperà di generare un numero casuale compreso in tale intervallo ed infine segnalerà al processo l’avvenuta operazione: il processo sarà nuovamente libero di effettuare altre operazioni con le modalità precedentemente descritte.</p>
<h3>Prima fase: analisi dei parametri</h3>
<p>Il programma inizierà la propria esecuzione analizzando i parametri specificati su riga di comando; sebbene questi non siano necessari per il funzionamento del simulatore, è disponibile un insieme di parametri per modificare alcuni comportamenti predefiniti dell’applicativo.</p>
<p>Di seguito vengono riassunti i possibili parametri:</p>
<p>-v | &#8211;version: Stampa la versione del programma ed esce<br />
-d | &#8211;debug: Aumenta il livello di debug dell’output (disattivato per default)<br />
-a | &#8211;anticipatory-paging: Disabilita la paginazione anticipata<br />
-h | &#8211;help: Stampa la sinossi del programma ed esce</p>
<p>-l <em>lista</em> | &#8211;probabilities=<em>lista</em>: Specifica la probabilità d’accesso alla memoria per i processi<br />
-L <em>num</em> | &#8211;locality=<em>num</em>: Specifica la località temporale (default: <em>30%</em>)<br />
-M | &#8211;all-memory: Forza i processi ad allocare il massimo della memoria (default: <em>no</em>)<br />
-m <em>num</em> | &#8211;max-read=<em>num</em>: Imposta il numero massimo di accessi alla memoria (default: <em>50</em>)<br />
-p <em>num</em> | &#8211;max-processes=<em>num</em>: Imposta il numero massimo di processi concorrenti (default <em>5</em>)<br />
-P <em>num</em> | &#8211;probability=<em>num</em>: Imposta la probabilità con cui un processo effettua un accesso alla memoria (default: <em>80%</em>)<br />
-r <em>lista</em> | &#8211;reference=<em>lista</em>: Imposta la <em>reference string</em> per determinare gli accessi<br />
-R <em>num</em> | &#8211;ram-size=<em>num</em>: Imposta la dimensione della RAM disponibile (default: <em>1,048,576</em>)<br />
-s <em>num</em> | &#8211;frame-size=<em>num</em>: Imposta la dimensione della pagina e del frame (default: <em>4,096</em>)<br />
-t <em>num</em> | &#8211;Tmin=<em>num</em>: Imposta il parametro Tmin del dispositivo di I/O (default: <em>1</em>)<br />
-T <em>num</em> | &#8211;Tmax=<em>num</em>: Imposta il parametro Tmax del dispositivo di I/O (default: <em>100</em>)<br />
-w | &#8211;write-enabled: Consente ai programmi di accedere alla memoria anche in scrittura (default: <em>no</em>)</p>
<h3>Seconda fase: inizializzazione ed esecuzione thread</h3>
<p>La corretta analisi dei parametri specificati su riga di comando permette di passare alla inizializzazione delle singole strutture dati ed all’esecuzione dei thread finora descritti.</p>
<p>La prima entità istanziata è appunto l’MMU, seguita successivamente dalla creazione del thread per il dispositivo di I/O ed in ultimo dai thread che simulano i processi utente.</p>
<h3>Terza fase: stampa dei risultati</h3>
<p>La terza fase ha inizio quando i processi utente hanno effettuato il  numero massimo di accessi alla memoria: questa condizione determina la fine di tutti i thread istanziati, siano essi utente, MMU o del dispositivo di I/O.</p>
<p>Una corretta conclusione prevede quindi di effettuare una pthread_join di tutti quanti i thread e la relativa deallocazione delle strutture dati fino a quel momento utilizzate.</p>
<p>Al termine di questa operazione, il simulatore si dovrà preoccupare di stampare a video le statistiche richieste. Oltre le suddette statistiche, saranno inoltre disponibili, nella directory di lavoro, i file di log di ogni singolo processo, all’interno dei quali si potrà trovare la lista delle operazioni effettuate dai processi utente.</p>
<p>Scarica l&#8217;intero progetto <a href="http://www.devzero.it/?attachment_id=235">qui</a>.</p>
</div>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2012/03/sistemi-operativi-vmbo/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>YABI meets MobileMe Calendar Beta</title>
		<link>http://www.devzero.it/2010/10/yabi-meets-mobileme-calendar-beta/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=yabi-meets-mobileme-calendar-beta</link>
		<comments>http://www.devzero.it/2010/10/yabi-meets-mobileme-calendar-beta/#comments</comments>
		<pubDate>Sun, 10 Oct 2010 05:52:00 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[anniversary]]></category>
		<category><![CDATA[birthday]]></category>
		<category><![CDATA[caldav]]></category>
		<category><![CDATA[ical]]></category>
		<category><![CDATA[macos]]></category>
		<category><![CDATA[mobileme]]></category>
		<category><![CDATA[sync]]></category>
		<category><![CDATA[yabi]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=208</guid>
		<description><![CDATA[Apple have recently released the beta version of new MobileMe Calendar: it&#8217;s cool, of course, but all calendars on your Mac won&#8217;t be local anymore, as they are replaced by CalDav ones. Unfortunately the Calendar Framework provided by Cocoa doesn&#8217;t fully support CalDav: then YABI tries to recreate the calendar, a new local calendar is [...]]]></description>
			<content:encoded><![CDATA[<p>Apple have recently released the beta version of new MobileMe Calendar: it&#8217;s cool, of course, but all calendars on your Mac won&#8217;t be local anymore, as they are replaced by CalDav ones.<br />
Unfortunately the Calendar Framework provided by Cocoa doesn&#8217;t fully support CalDav: then YABI tries to recreate the calendar, a new local calendar is created instead of a CalDav one.</p>
<p>I&#8217;ve already wrote the solution to this bug and soon I&#8217;ll release the new version which also includes a way to exclude person from sync.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2010/10/yabi-meets-mobileme-calendar-beta/feed/</wfw:commentRss>
		<slash:comments>21</slash:comments>
		</item>
		<item>
		<title>Follow YABI on Facebook</title>
		<link>http://www.devzero.it/2010/09/follow-yabi-on-facebook/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=follow-yabi-on-facebook</link>
		<comments>http://www.devzero.it/2010/09/follow-yabi-on-facebook/#comments</comments>
		<pubDate>Sun, 12 Sep 2010 17:15:29 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Software]]></category>
		<category><![CDATA[facebook]]></category>
		<category><![CDATA[ical]]></category>
		<category><![CDATA[like]]></category>
		<category><![CDATA[page]]></category>
		<category><![CDATA[yabi]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=202</guid>
		<description><![CDATA[If you &#8220;Like&#8221; YABI, follow it also on Facebook! Please, visit the following link: http://www.facebook.com/pages/YABI/]]></description>
			<content:encoded><![CDATA[<p>If you &#8220;Like&#8221; YABI, follow it also on Facebook!</p>
<p>Please, visit the following link: <a href="http://www.facebook.com/pages/YABI/128985247144819">http://www.facebook.com/pages/YABI/</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2010/09/follow-yabi-on-facebook/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>YABI 1.0.4 released!</title>
		<link>http://www.devzero.it/2010/09/yabi-1-0-4-released/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=yabi-1-0-4-released</link>
		<comments>http://www.devzero.it/2010/09/yabi-1-0-4-released/#comments</comments>
		<pubDate>Fri, 10 Sep 2010 05:32:20 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[Software]]></category>
		<category><![CDATA[anniversary]]></category>
		<category><![CDATA[birthday]]></category>
		<category><![CDATA[ical]]></category>
		<category><![CDATA[mobileme]]></category>
		<category><![CDATA[prefpane]]></category>
		<category><![CDATA[synchronization]]></category>
		<category><![CDATA[yabi]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=194</guid>
		<description><![CDATA[&#8220;This changes everything. Again.&#8221; YABI core functions have been totally reimplemented and, above all, completed. This version addresses few bugs, which caused YABI Agent crashes (e.g. when an event name is changed in AddressBook). I&#8217;ve also been asked for new interesting features, I&#8217;ll work on them in spare time: use remote calendar as target excluding [...]]]></description>
			<content:encoded><![CDATA[<blockquote><p>&#8220;This changes everything. Again.&#8221;</p></blockquote>
<p>YABI core functions have been totally reimplemented and, above all, completed.<br />
This version addresses few bugs, which caused YABI Agent crashes (e.g. when an event name is changed in AddressBook).</p>
<p>I&#8217;ve also been asked for new interesting features, I&#8217;ll work on them in spare time:</p>
<ul>
<li>use remote calendar as target</li>
<li>excluding birthdays</li>
<li>enhanced nickname support</li>
</ul>
<p><strong>Upgrade note</strong><br />
We suggest to deactivate YABI before upgrading; follow these few steps:</p>
<ul>
<li>Open YABI preference pane</li>
<li>Click on  Deactivate button and quit System Preferences</li>
<li>Upgrade YABI by double-clicking on the new icon</li>
</ul>
<p>Download YABI at <a href="http://www.devzero.it/yabi/">http://www.devzero.it/yabi/</a> and check it out!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2010/09/yabi-1-0-4-released/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>YABI 1.0.2 released</title>
		<link>http://www.devzero.it/2010/03/yabi-1-0-2-released/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=yabi-1-0-2-released</link>
		<comments>http://www.devzero.it/2010/03/yabi-1-0-2-released/#comments</comments>
		<pubDate>Sat, 20 Mar 2010 11:02:53 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[Software]]></category>
		<category><![CDATA[alarms]]></category>
		<category><![CDATA[anniversary]]></category>
		<category><![CDATA[birthday]]></category>
		<category><![CDATA[cocoa]]></category>
		<category><![CDATA[event title]]></category>
		<category><![CDATA[events]]></category>
		<category><![CDATA[ical]]></category>
		<category><![CDATA[macos]]></category>
		<category><![CDATA[minor release]]></category>
		<category><![CDATA[objective-c]]></category>
		<category><![CDATA[yabi]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=176</guid>
		<description><![CDATA[Say hello to YABI 1.0.2 and YABI Viewer. Here some changes: [FIX] Nicknames were not properly imported by from Sync Server and it was impossible to substitute in event title [FIX] Target calendar change is now saved [FIX] Event title changes are properly saved [FIX] Alarm icon column is no more bound to &#8220;data&#8221; binding [...]]]></description>
			<content:encoded><![CDATA[<p>Say hello to YABI 1.0.2 and YABI Viewer.</p>
<p>Here some changes:</p>
<ul>
<li>[FIX] Nicknames were not properly imported by from Sync Server and it was impossible to substitute in event title</li>
<li>[FIX] Target calendar change is now saved</li>
<li>[FIX] Event title changes are properly saved</li>
<li>[FIX] Alarm icon column is no more bound to &#8220;data&#8221; binding (&#8220;value&#8221; is now used: no more warning in your console about this deprecated construct)</li>
<li>[NEW] Agent deactivation removes application data file</li>
<li>[NEW] Deactivate button is now disabled when a fresh-sync is issued</li>
<li>[NEW] Added the new specifier &#8220;%yp&#8221; (equal to %y minus 1)</li>
</ul>
<p>Here what must still be implemented:</p>
<ul>
<li>Software autoupdate</li>
</ul>
<p>I&#8217;d like to thank all of you for your bug report and support.</p>
<p>You can download it at <a href="http://www.devzero.it/yabi">www.devzero.it/yabi</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2010/03/yabi-1-0-2-released/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>YABI 1.0.1 &#8211; minor bug fixes</title>
		<link>http://www.devzero.it/2010/01/yabi-1-0-1-minor-bug-fixes/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=yabi-1-0-1-minor-bug-fixes</link>
		<comments>http://www.devzero.it/2010/01/yabi-1-0-1-minor-bug-fixes/#comments</comments>
		<pubDate>Fri, 01 Jan 2010 10:09:00 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[Software]]></category>
		<category><![CDATA[anniversary]]></category>
		<category><![CDATA[birthday]]></category>
		<category><![CDATA[bug fixes]]></category>
		<category><![CDATA[ical]]></category>
		<category><![CDATA[minor release]]></category>
		<category><![CDATA[yabi]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=152</guid>
		<description><![CDATA[A new minor release of preference pane version of YABI has been released. Here some changes: 64-bit enabled minor memory leaks fixed added &#8220;partner&#8221; attribute for anniversary cross-check UI updates removed unused frameworks Here what must still be implemented: Save/restore event titles Software autoupdate You can download it at www.devzero.it/yabi]]></description>
			<content:encoded><![CDATA[<p>A new minor release of preference pane version of YABI has been released.</p>
<p>Here some changes:</p>
<ul>
<li>64-bit enabled</li>
<li>minor memory leaks fixed</li>
<li>added &#8220;partner&#8221; attribute for anniversary cross-check</li>
<li>UI updates</li>
<li>removed unused frameworks</li>
</ul>
<p>Here what must still be implemented:</p>
<ul>
<li>Save/restore event titles</li>
<li>Software autoupdate</li>
</ul>
<p>You can download it at <a href="http://www.devzero.it/yabi">www.devzero.it/yabi</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2010/01/yabi-1-0-1-minor-bug-fixes/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Selectable boxes</title>
		<link>http://www.devzero.it/2009/12/selectable-boxes/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=selectable-boxes</link>
		<comments>http://www.devzero.it/2009/12/selectable-boxes/#comments</comments>
		<pubDate>Tue, 15 Dec 2009 13:18:56 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[BSD]]></category>
		<category><![CDATA[class]]></category>
		<category><![CDATA[cocoa]]></category>
		<category><![CDATA[github]]></category>
		<category><![CDATA[Interface Builder]]></category>
		<category><![CDATA[macos]]></category>
		<category><![CDATA[nsbox]]></category>
		<category><![CDATA[objective-c]]></category>
		<category><![CDATA[opensource]]></category>
		<category><![CDATA[radio group]]></category>
		<category><![CDATA[selection]]></category>
		<category><![CDATA[source]]></category>
		<category><![CDATA[subclass]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=97</guid>
		<description><![CDATA[If you had ever used iSync, probably you&#8217;ve been asked to resolve a sync conflict at least one time: the panel shown to the user contains two boxes , mutually excluded i.e. you can only choose one of them. DZSelectableBox is a subclass of NSBox view which emulates this behavior. An instance of this class [...]]]></description>
			<content:encoded><![CDATA[<p>If you had ever used iSync, probably you&#8217;ve been asked to resolve a sync conflict at least one time: the panel shown to the user contains two boxes , mutually excluded i.e. you can only choose one of them.</p>
<p>DZSelectableBox is a subclass of NSBox view which emulates this behavior. An instance of this class comes with one more variable member, the box state: when the box is marked as <em>selected</em>, an inner rounded path is drawn inside its bounds; DZSelectableBox honors title position, if it&#8217;s visible. You can use this class in two different manners: standalone or as part of a radio group.<br />
<span id="more-97"></span></p>
<h3>Standalone version</h3>
<p style="margin: 0.0px 0.0px 0.0px 0.0px; font: 12.0px Menlo;"><span style="font-family: Georgia, 'Times New Roman', 'Bitstream Charter', Times, serif; font-size: 13px; line-height: 19px; "><span style="font-family: Georgia, 'Times New Roman', 'Bitstream Charter', Times, serif; font-size: 13px; line-height: 19px;"><span style="font-size: small;"><a href="http://www.devzero.it/wp-content/uploads/2009/12/box-standalone.png"> <img class="alignright size-thumbnail wp-image-105" title="Example of standalone use" src="http://www.devzero.it/wp-content/uploads/2009/12/box-standalone-150x150.png" alt="Example of standalone use" width="150" height="150" /></a></span></span></span></p>
<p>A standalone box works as described before: the only thing you&#8217;ve to do is open Interface Builder, place a common NSBox in your window, change its class name into DZSelectableBox and start using it.<br />
You can change box state programmatically by using the <strong>toggleState</strong> message, the <strong>setSelected</strong> method to set its state or simply by clicking on it.</p>
<p style="font: normal normal normal 12px/normal Menlo; margin: 0px;"><span style="font-family: Georgia, 'Times New Roman', 'Bitstream Charter', Times, serif; font-size: 13px; line-height: 19px;"><span style="font-family: Georgia, 'Times New Roman', 'Bitstream Charter', Times, serif; font-size: 13px; line-height: 19px;"><span style="font-size: small;"><a href="http://www.devzero.it/wp-content/uploads/2009/12/box-standalone.png"></a></span><a href="http://www.devzero.it/wp-content/uploads/2009/12/box-standalone.png"></a></span><a href="http://www.devzero.it/wp-content/uploads/2009/12/box-standalone.png"></a></span></p>
<p style="margin: 0.0px 0.0px 0.0px 0.0px; font: 12.0px Menlo;">
<h3>Radio group version</h3>
<p><a href="http://www.devzero.it/wp-content/uploads/2009/12/box-radiogroup.png"><img class="alignright size-thumbnail wp-image-107" title="Radio group boxes" src="http://www.devzero.it/wp-content/uploads/2009/12/box-radiogroup-150x150.png" alt="Radio group boxes" width="150" height="150" /></a></p>
<p>Whenever you need a group of boxes and the opportunity to select only one of them at time, you&#8217;ve to set a radio group; after you followed the steps described before to create your boxes, you&#8217;ve to add the following sample code to your application:</p>
<pre>leftBox<span style="color: #000000;">.</span>radioGroup<span style="color: #000000;"> = [</span><span style="color: #733ba7;">NSNumber</span><span style="color: #000000;"> </span><span style="color: #411b7f;">numberWithInt</span><span style="color: #000000;">:</span><span style="color: #3527d4;">1</span><span style="color: #000000;">];<span style="font-family: Consolas, Monaco, 'Courier New', Courier, monospace; line-height: 18px; "> </span></span>
rightBox<span style="color: #000000;">.</span>radioGroup<span style="color: #000000;"> = [</span><span style="color: #733ba7;">NSNumber</span><span style="color: #000000;"> </span><span style="color: #411b7f;">numberWithInt</span><span style="color: #000000;">:</span><span style="color: #3527d4;">1</span><span style="color: #000000;">];<span style="font-family: Consolas, Monaco, 'Courier New', Courier, monospace; line-height: 18px; "> </span></span>
<span style="color: #000000;">[</span><span style="color: #4f8187;">leftBox</span><span style="color: #000000;"> </span>setSelected<span style="color: #000000;">:</span><span style="color: #bc24a0;">YES</span><span style="color: #000000;">];<span style="font-family: Consolas, Monaco, 'Courier New', Courier, monospace; line-height: 18px; "> </span></span>
<span style="color: #000000;">[</span><span style="color: #4f8187;">rightBox</span><span style="color: #000000;"> </span>setSelected<span style="color: #000000;">:</span><span style="color: #bc24a0;">NO</span><span style="color: #000000;">];</span><span style="color: #000000;">
</span></pre>
<p><span style="color: #000000;">(we suppose you created two boxes and connected them to two outlets called leftBox and rightBox)</span></p>
<p>When a box belongs to a radio group, it listens for group changes notification: for example, if you select the right box (by clicking on it), the left one will be automatically unselected.</p>
<h3><span style="color: #000000;">Where can I download the code?</span></h3>
<p><span style="color: #000000;">Code is available on <a href="http://github.com/">GitHub</a> at the following url:</span></p>
<p><span style="color: #000000;"><a href="http://github.com/unixo/Selectable-Box" target="_blank">http://github.com/unixo/Selectable-Box</a></span></p>
<p><span style="color: #000000;">You can also download a <a rel="attachment wp-att-145" href="http://www.devzero.it/2009/12/selectable-boxes/selectedbox/">Test application</a></span></p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2009/12/selectable-boxes/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Give me a&#8230; second chance!</title>
		<link>http://www.devzero.it/2009/10/give-me-a-second-chance/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=give-me-a-second-chance</link>
		<comments>http://www.devzero.it/2009/10/give-me-a-second-chance/#comments</comments>
		<pubDate>Sat, 03 Oct 2009 18:18:46 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Software]]></category>
		<category><![CDATA[University]]></category>
		<category><![CDATA[ansi c]]></category>
		<category><![CDATA[enhanced]]></category>
		<category><![CDATA[frame]]></category>
		<category><![CDATA[I/O]]></category>
		<category><![CDATA[mmu]]></category>
		<category><![CDATA[page]]></category>
		<category><![CDATA[process]]></category>
		<category><![CDATA[second chance]]></category>
		<category><![CDATA[simulator]]></category>
		<category><![CDATA[thread]]></category>
		<category><![CDATA[virtual memory]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=91</guid>
		<description><![CDATA[As university assignment, I wrote a small virtual memory simulator which implements pagination; the algorithm chosen to replace a target page is the enhanced second chance, also known as &#8220;clock algorithm&#8221;: this solution comes out as natural evolution of FIFO algorithm, working out the problem of removing those pages which are frequently accessed. This algorithm requires [...]]]></description>
			<content:encoded><![CDATA[<p>As university assignment, I wrote a small virtual memory simulator which implements pagination; the algorithm chosen to replace a target page is the <strong>enhanced second chance</strong>, also known as &#8220;clock algorithm&#8221;: this solution comes out as natural evolution of FIFO algorithm, working out the problem of removing those pages which are frequently accessed.<br />
<span id="more-91"></span></p>
<p style="text-align: center;"><a rel="attachment wp-att-125" href="http://www.devzero.it/2009/10/give-me-a-second-chance/img208/"><img class="aligncenter size-thumbnail wp-image-125" title="Classical second chance algorithm" src="http://www.devzero.it/wp-content/uploads/2009/10/img208-150x150.png" alt="Classical second chance algorithm" width="150" height="150" /></a></p>
<p>This algorithm requires that each page contained in the <em>page table</em>, besides the common attributes, must also contains two further bits:</p>
<ul>
<li>reference bit (R): this bit will be 1 when the system accesses the page, both for read and write operations;</li>
<li>dirty bit (D): this bit will be 1 only when the page will be written: when a page must be removed from main memory, this bit will remember the operative system to make a copy into secondary storage, before wiping it out.</li>
</ul>
<p>Searching for a virtual page to be removed will take in account of four possible combinations:</p>
<ol>
<li>R=0, D=0: this page has never been used nor modified -&gt; remove this page</li>
<li>R=0, D=1: this page has not been recently used, but has been modified -&gt; write it back to secondary storage and set D=0;</li>
<li>R=1, D=0: this page has been recently used only for read access -&gt; set R=0</li>
<li>R=1, D=1: this page has been recently used and modified -&gt; set R=0, do a write back and set D=0.</li>
</ol>
<p>Searching for the best page to replace won&#8217;t only be equivalent to select the less used page, but also those pages that weren&#8217;t modified; in this way, the more the system uses a page, the less is the probability for that page to be removed.</p>
<p>When a page present into the main memory is <em>dirty</em>, the system must issue two I/O requests: the former to access the secondary memory for paging it out, the latter to bring the requested page into memory (page in). In this scenario, by analyzing the dirty pages periodically and writing them back to the storage, the algorithm improves the overall performances as well as average access time to memory.</p>
<p>This algorithm suffers the disadvantage of partitioning the main memory in two classes: pages which are frequently accessed and pages less frequently accessed; when searching for target page ends, it&#8217;s not assured that the victim page is the oldest, but only one of the less accessed pages.</p>
<p>The best instance happens when the first frame has both R &amp; D bits equal to zero: searching stops immediately and it&#8217;s not necessary to page it out.</p>
<p>The worst case happens when all pages are both referenced and modified: in this scenario the MMU must completely scan all the entries, just like a FIFO.</p>
<p>The simulator, written in C, is made up of different entities, which are:</p>
<ul>
<li><strong>process</strong>: it simulates a user process which can access to an random memory location or issue a I/O read</li>
<li><strong>i/o device</strong>: a dedicated thread is spawn to simulate an i/o device (it comes with a FIFO queue to serve processes requests)</li>
<li><strong>mmu</strong>: the MMU simulates the Memory Management Unit, i.e. the responsible to translate virtual addresses (generated by a user process) into physical address; it&#8217;s also implements the second chance algorithm.</li>
</ul>
<p>It let the user specify how many processes run, how much physical memory is installed, the page size and so on; it requires only a C compiler (like <em>gcc</em>) and the utility <em>Makefile</em>.</p>
<p>Its output is in italian language, even if very simple terms have been used.</p>
<p>Download <a href="http://www.devzero.it/files/vmbo.tar.gz">vmbo.tar.gz</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2009/10/give-me-a-second-chance/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>WordPress themes and page-links</title>
		<link>http://www.devzero.it/2009/07/wordpress-themes-and-page-links/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=wordpress-themes-and-page-links</link>
		<comments>http://www.devzero.it/2009/07/wordpress-themes-and-page-links/#comments</comments>
		<pubDate>Mon, 06 Jul 2009 05:13:07 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Web]]></category>
		<category><![CDATA[long post]]></category>
		<category><![CDATA[nextpage]]></category>
		<category><![CDATA[page-links]]></category>
		<category><![CDATA[php]]></category>
		<category><![CDATA[single.php]]></category>
		<category><![CDATA[split]]></category>
		<category><![CDATA[theme]]></category>
		<category><![CDATA[wordpress]]></category>
		<category><![CDATA[wp_link_pages]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=69</guid>
		<description><![CDATA[WordPress offers a cool feature to split a single post into different web pages, by using &#60;!&#8211;nextpage&#8211;&#62; keyword. The problem arises when you use a theme different from the default one: that&#8217;s why many theme writers forget to add the right code to the theme; if you have this problem, follow these steps: Go to [...]]]></description>
			<content:encoded><![CDATA[<p>WordPress offers a cool feature to split a single post into different web pages, by using <em>&lt;!&#8211;nextpage&#8211;&gt;</em> keyword.<br />
The problem arises when you use a theme different from the default one: that&#8217;s why many theme writers forget to add the right code to the theme; <span id="more-69"></span>if you have this problem, follow these steps:</p>
<ol>
<li>Go to the theme directory (DOC_ROOT/wp-contents/themes/<em>yourtheme</em>)</li>
<li>Look for file named <em>single.php</em></li>
<li>Look for the template tag named <em>the_content</em></li>
<li>Add a new line below and attach the following istructions:</li>
</ol>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 35px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;"><code>?php wp_link_pages(array('before' =&gt; '&lt;p&gt;&lt;strong&gt;Pages:&lt;/strong&gt; ',</code></div>
<p><code></p>
<div id="_mcePaste" style="position: absolute; left: -10000px; top: 35px; width: 1px; height: 1px; overflow-x: hidden; overflow-y: hidden;">'after' =&gt; '&lt;/p&gt;', 'next_or_number' =&gt; 'number')); ?&gt;</div>
<p></code></p>
<p><span style="font-family: monospace, 'Times New Roman', 'Bitstream Charter', Times, fantasy;"><span style="font-family: Consolas, Monaco, 'Courier New', Courier, monospace; line-height: 18px; font-size: 12px; white-space: pre;">&lt;</span>?php wp_link_pages(array(&#8216;before&#8217; =&gt; &#8216;&lt;p&gt;&lt;strong&gt;Pages:&lt;/strong&gt; &#8216;,&#8217;after&#8217; =&gt; &#8216;&lt;/p&gt;&#8217;, &#8216;next_or_number&#8217; =&gt; &#8216;number&#8217;)); ?&gt;</span></p>
<p>Try to reload the single post page and enjoy page-links.</p>
<p>For further informations about page-links, <a href="http://codex.wordpress.org/Styling_Page-Links">read this document</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2009/07/wordpress-themes-and-page-links/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Red-black trees</title>
		<link>http://www.devzero.it/2009/06/red-black-trees/?utm_source=rss&#038;utm_medium=rss&#038;utm_campaign=red-black-trees</link>
		<comments>http://www.devzero.it/2009/06/red-black-trees/#comments</comments>
		<pubDate>Sun, 07 Jun 2009 18:21:50 +0000</pubDate>
		<dc:creator>unixo</dc:creator>
				<category><![CDATA[Software]]></category>
		<category><![CDATA[University]]></category>
		<category><![CDATA[ansi]]></category>
		<category><![CDATA[C]]></category>
		<category><![CDATA[rb]]></category>
		<category><![CDATA[red black]]></category>
		<category><![CDATA[sort]]></category>
		<category><![CDATA[sources]]></category>
		<category><![CDATA[tree]]></category>
		<category><![CDATA[trees]]></category>

		<guid isPermaLink="false">http://www.devzero.it/?p=49</guid>
		<description><![CDATA[Example of Red-Black tree implementation, written in ANSI C. Archive contains sources and relation, written in italian, which describe the algorithm, its purpose and implementation. This was developed for university purposes. Download rb-sorter.tar.gz]]></description>
			<content:encoded><![CDATA[<p class="paragraph_style_3">Example of Red-Black tree implementation, written in ANSI C.</p>
<p class="paragraph_style_3">Archive contains sources and relation, written in italian, which describe the algorithm, its purpose and implementation. This was developed for university purposes.</p>
<p class="paragraph_style_3">Download <a href="http://www.devzero.it/files/rb-sorter.tar.gz">rb-sorter.tar.gz</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.devzero.it/2009/06/red-black-trees/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

