Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Remove PSG from SimGrid git
[simgrid.git] / contrib / psg / src / example / bittorrent / BitTorrent.java
diff --git a/contrib/psg/src/example/bittorrent/BitTorrent.java b/contrib/psg/src/example/bittorrent/BitTorrent.java
deleted file mode 100644 (file)
index 1604a4d..0000000
+++ /dev/null
@@ -1,1989 +0,0 @@
-/*
- * Copyright (c) 2007-2008 Fabrizio Frioli, Michele Pedrolli
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License version 2 as
- * published by the Free Software Foundation.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
- *
- * --
- *
- * Please send your questions/suggestions to:
- * {fabrizio.frioli, michele.pedrolli} at studenti dot unitn dot it
- *
- */
-
-package example.bittorrent;
-
-import peersim.core.*;
-import peersim.config.*;
-import peersim.edsim.*;
-import peersim.transport.*;
-
-/**
- *     This is the class that implements the BitTorrent module for Peersim
- */
-public class BitTorrent implements EDProtocol {
-       /**
-        *      The size in Megabytes of the file being shared.
-        *      @config
-        */
-       private static final String PAR_SIZE="file_size";
-       /**
-        *      The Transport used by the the protocol.
-        *      @config
-        */
-       private static final String PAR_TRANSPORT="transport";
-       /**
-        *      The maximum number of neighbor that a node can have. 
-        *      @config
-        */
-       private static final String PAR_SWARM="max_swarm_size";
-       /**
-        *      The maximum number of peers returned by the tracker when a new
-        *      set of peers is requested through a <tt>TRACKER</tt> message.
-        *      @config
-        */
-       private static final String PAR_PEERSET_SIZE="peerset_size";
-       /**
-        *      Defines how much the network can grow with respect to the <tt>network.size</tt> 
-        *  when {@link NetworkDynamics} is used.
-        *      @config
-        */
-       private static final String PAR_MAX_GROWTH="max_growth";
-       /**
-        *      Is the number of requests of the same block sent to different peers.
-        *      @config
-        */
-       private static final String PAR_DUP_REQ = "duplicated_requests";
-       
-       /**
-        *      KEEP_ALIVE message.
-        *      @see SimpleEvent#type "Event types"
-        */
-       private static final int KEEP_ALIVE = 1;
-       
-       /**
-        *      CHOKE message.
-        *      @see SimpleEvent#type "Event types"
-        */
-       private static final int CHOKE = 2;
-       
-       /**
-        *      UNCHOKE message.
-        *      @see SimpleEvent#type "Event types"
-        */
-       private static final int UNCHOKE = 3;
-       
-       /**
-        *      INTERESTED message.
-        *      @see SimpleEvent#type "Event types"
-        */
-       private static final int INTERESTED = 4;
-       
-       /**
-        *      NOT_INTERESTED message.
-        *      @see SimpleEvent#type "Event types"
-        */
-       private static final int NOT_INTERESTED = 5;
-       
-       /**
-        *      HAVE message.
-        *      @see SimpleEvent#type "Event types"
-        */
-       private static final int HAVE = 6;
-       
-       /**
-        *      BITFIELD message.
-        *      @see SimpleEvent#type "Event types"
-        */
-       private static final int BITFIELD = 7;
-       
-       /**
-        *      REQUEST message.
-        *      @see SimpleEvent#type "Event types"
-        */
-       private static final int REQUEST = 8;
-       
-       /**
-        *      PIECE message.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int PIECE = 9;
-
-       /**
-        *      CANCEL message.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int CANCEL = 10;
-       
-       /**
-        *      TRACKER message.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int TRACKER = 11;
-       
-       /**
-        *      PEERSET message.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int PEERSET = 12;
-       
-       /**
-        *      CHOKE_TIME event.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int CHOKE_TIME = 13;
-       
-       /**
-        *      OPTUNCHK_TIME event.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int OPTUNCHK_TIME = 14;
-       
-       /**
-        *      ANTISNUB_TIME event.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int ANTISNUB_TIME = 15;
-       
-       /**
-        *      CHECKALIVE_TIME event.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int CHECKALIVE_TIME = 16;
-       
-       /**
-        *      TRACKERALIVE_TIME event.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int TRACKERALIVE_TIME = 17;
-       
-       /**
-        *      DOWNLOAD_COMPLETED event.
-        *      @see SimpleEvent#type "Event types"
-        */     
-       private static final int DOWNLOAD_COMPLETED = 18;
-
-       /**
-        *      The maxium connection speed of the local node.
-        */
-       int maxBandwidth;
-       
-       /**
-        *      Stores the neighbors ordered by ID.
-        *  @see Element
-        */
-       private example.bittorrent.Element byPeer[];
-       
-       /**
-        *      Contains the neighbors ordered by bandwidth as needed by the unchocking
-        *      algorithm.
-        */
-       private example.bittorrent.Element byBandwidth[];
-       
-       /**
-        *      The Neighbors list.
-        */
-       private Neighbor cache[];
-       
-       /**
-        *      Reference to the neighbors that unchocked the local node.
-        */
-       private boolean unchokedBy[];
-       
-       /**
-        *      Number of neighbors in the cache. When it decreases under 20, a new peerset
-        *      is requested to the tracker.
-        */
-       private int nNodes = 0;
-       
-       /**
-        *      Maximum number of nodes in the network.
-        */
-       private int nMaxNodes;
-       
-       /**
-        *      The status of the local peer. 0 means that the current peer is a leecher, 1 a seeder.
-        */ 
-       private int peerStatus;
-       
-       /**
-        *      Defines how much the network can grow with respect to the <tt>network.size</tt> 
-        *  when {@link NetworkDynamics} is used.
-        */
-       public int maxGrowth;
-       
-       /**
-        *      File status of the local node. Contains the blocks owned by the local node.
-        */
-       private int status[];
-       
-       /**
-        *      Current number of Bitfield request sent. It must be taken into account 
-        *      before sending another one.
-        */
-       private int nBitfieldSent = 0;
-       
-       /**
-        *      Current number of pieces in upload from the local peer.
-        */
-       public int nPiecesUp = 0;
-       /**
-        *      Current number of pieces in download to the local peer.
-        */
-       public int nPiecesDown = 0;
-       
-       /**
-        *      Current number of piece completed.
-        */
-       private int nPieceCompleted = 0;
-       
-       /**
-        *      Current downloading piece ID, the previous lastInterested piece.
-        */
-       int currentPiece = -1;
-       
-       /**
-        *      Used to compute the average download rates in choking algorithm. Stores the
-        *      number of <tt>CHOKE</tt> events.
-        */
-       int n_choke_time = 0;
-       
-       /**
-        *      Used to send the <tt>TRACKER</tt> message when the local node has 20 neighbors
-        *      for the first time.
-        */
-       boolean lock = false;
-       
-       /**
-        *      Number of peers interested to my pieces.
-        */
-       int numInterestedPeers = 0;
-       
-       /**
-        *      Last piece for which the local node sent an <tt>INTERESTED</tt> message.
-        */
-       int lastInterested = -1;
-       
-       /** 
-        *      The status of the current piece in download. Length 16, every time the local node
-        *      receives a PIECE message, it updates the corrisponding block's cell. The cell
-        *      contains the ID for that block of that piece. If an already owned
-        *      block is received this is discarded.
-        */
-       private int pieceStatus[];
-       
-       /**     
-        *      Length of the file. Stored as number of pieces (256KB each one).
-        */
-       int nPieces;
-       
-       /**
-        *      Contains the neighbors's status of the file. Every row represents a
-        *      node and every a cell has value O if the neighbor doesn't 
-        *      have the piece, 1 otherwise. It has {@link #swarmSize} rows and {@link #nPieces}
-        *      columns.
-        */
-       int [][]swarm;
-       
-       /**     
-        *      The summation of the swarm's rows. Calculated every time a {@link #BITFIELD} message
-        *      is received and updated every time HAVE message is received.
-        */
-       int rarestPieceSet[];
-       
-       /**
-        *      The five pending block requests.
-        */
-       int pendingRequest[];
-       
-       /**
-        *      The maximum swarm size (default is 80)
-        */
-       int swarmSize;
-       
-       /**
-        *      The size of the peerset. This is the number of "friends" nodes
-        *      sent from the tracker to each new node (default: 50)
-        */
-       int peersetSize;
-       
-       /**
-        * The ID of the current node
-        */
-       private long thisNodeID;
-       
-       /**
-     * Number of duplicated requests as specified in the configuration file.
-        *      @see BitTorrent#PAR_DUP_REQ
-        */
-       private int numberOfDuplicatedRequests;
-       
-       /**
-        *      The queue where the requests to serve are stored.
-        *      The default dimension of the queue is 20.
-        */
-       Queue requestToServe = null;
-       
-       /**
-        *      The queue where the out of sequence incoming pieces are stored
-        *      waiting for the right moment to be processed.
-     * The default dimension of the queue is 100.
-        */
-       Queue incomingPieces = null;
-       
-       /**
-        *      The Transport ID.
-        *      @see BitTorrent#PAR_TRANSPORT
-        */
-       int tid;
-       
-       /**
-        *      The reference to the tracker node. If equals to <tt>null</tt>, the local
-        *      node is the tracker.
-        */
-       private Node tracker = null;
-       
-       /**
-        *      The default constructor. Reads the configuration file and initializes the
-        *      configuration parameters.
-        *      @param prefix the component prefix declared in the configuration file
-        */
-       public BitTorrent(String prefix){ // Used for the tracker's protocol
-               tid = Configuration.getPid(prefix+"."+PAR_TRANSPORT);
-               nPieces = (int)((Configuration.getInt(prefix+"."+PAR_SIZE))*1000000/256000);
-               swarmSize = (int)Configuration.getInt(prefix+"."+PAR_SWARM);
-               peersetSize = (int)Configuration.getInt(prefix+"."+PAR_PEERSET_SIZE);
-               numberOfDuplicatedRequests = (int)Configuration.getInt(prefix+"."+PAR_DUP_REQ);
-               maxGrowth = (int)Configuration.getInt(prefix+"."+PAR_MAX_GROWTH);
-               nMaxNodes = Network.getCapacity()-1;
-       }
-       
-       /**
-        *      Gets the reference to the tracker node.
-        *      @return the reference to the tracker
-        */
-       public Node getTracker(){
-               return tracker;
-       }
-       
-       /**
-        *      Gets the number of neighbors currently stored in the cache of the local node.
-        *      @return the number of neighbors in the cache
-        */
-       public int getNNodes(){
-               return this.nNodes;
-       }
-       
-       /**
-        *      Sets the reference to the tracker node.
-        *      @param t the tracker node
-        */
-       public void setTracker(Node t){
-               tracker = t;
-       }
-       
-       /**
-        *      Sets the ID of the local node.
-        *      @param id the ID of the node
-        */
-       public void setThisNodeID(long id) {
-               this.thisNodeID = id;
-       }
-       
-       /**
-        *      Gets the ID of the local node.
-        *      @return the ID of the local node
-        */
-       public long getThisNodeID(){
-               return this.thisNodeID;
-       }
-       
-       /**
-        *      Gets the file status of the local node.
-        *      @return the file status of the local node
-        */
-       public int[] getFileStatus(){
-               return this.status;
-       }
-       
-       /**
-        *      Initializes the tracker node. This method
-        *      only performs the initialization of the tracker's cache.
-        */
-       public void initializeTracker() {
-               cache = new Neighbor[nMaxNodes+maxGrowth];
-               for(int i=0; i<nMaxNodes+maxGrowth; i++){
-                       cache[i]= new Neighbor();
-               }
-       }
-       
-       /**
-        *      <p>Checks the number of neighbors and if it is equal to 20
-        *      sends a TRACKER messages to the tracker, asking for a new
-        *      peer set.</p>
-        *
-        *      <p>This method *must* be called after every call of {@link #removeNeighbor}
-        *      in {@link #processEvent}.
-        *      </p>
-        */
-       private void processNeighborListSize(Node node, int pid) {
-               if (nNodes==20) {
-                       Object ev;
-                       long latency;
-                       ev = new SimpleMsg(TRACKER, node);
-                       Node tracker = ((BitTorrent)node.getProtocol(pid)).tracker;
-                       if(tracker != null){
-//                             latency = ((Transport)node.getProtocol(tid)).getLatency(node, tracker);
-//                             EDSimulator.add(latency,ev,tracker,pid);
-                               ((Transport) node.getProtocol(tid)).send(node, tracker, ev, pid);
-                       }
-               }
-       }
-       
-       /**
-        *      The standard method that processes incoming events.
-        *      @param node reference to the local node for which the event is going to be processed
-        *      @param pid BitTorrent's protocol id
-        *      @param event the event to process
-        */
-       public void processEvent(Node node, int pid, Object event){
-               
-               Object ev;
-               long latency;
-               switch(((SimpleEvent)event).getType()){
-                       
-                       case KEEP_ALIVE: // 1
-                       {
-                               Node sender = ((IntMsg)event).getSender();
-                               int isResponse = ((IntMsg)event).getInt();
-                               //System.out.println("process, keep_alive: sender is "+sender.getID()+", local is "+node.getID());
-                               Element e = search(sender.getID());
-                               if(e!= null){ //if I know the sender
-                                       cache[e.peer].isAlive();
-                                       if(isResponse==0 && alive(sender)){
-                                               Object msg = new IntMsg(KEEP_ALIVE,node,1,0);
-//                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node, sender);
-//                                             EDSimulator.add(latency,msg,sender,pid);
-                                               ((Transport) node.getProtocol(tid)).send(node, sender, msg, pid);
-                                               cache[e.peer].justSent();
-                                       }
-                               }
-                               else{
-                                       System.err.println("despite it should never happen, it happened");
-                                       ev = new BitfieldMsg(BITFIELD, true, false, node, status, nPieces);
-//                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                     EDSimulator.add(latency,ev,sender,pid);                                 
-                                       ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                       nBitfieldSent++;
-                               }
-                               
-                       };break;
-                               
-                       case CHOKE: // 2, CHOKE message.
-                       {
-                               Node sender = ((SimpleMsg)event).getSender();
-                               //System.out.println("process, choke: sender is "+sender.getID()+", local is "+node.getID());
-                               Element e = search(sender.getID());
-                               if(e!= null){ //if I know the sender
-                                       cache[e.peer].isAlive();
-                                       unchokedBy[e.peer]= false; // I'm choked by it
-                               }
-                               else{
-                                       System.err.println("despite it should never happen, it happened");
-                                       ev = new BitfieldMsg(BITFIELD, true, false, node, status, nPieces);
-//                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                     EDSimulator.add(latency,ev,sender,pid);
-                                       ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                       nBitfieldSent++;
-                               }
-                       };break;
-                               
-                       case UNCHOKE: // 3, UNCHOKE message.
-                       {                       
-                               Node sender = ((SimpleMsg)event).getSender();
-                               //System.out.println("process, unchoke: sender is "+sender.getID()+", local is "+node.getID());
-                               Element e = search(sender.getID());
-                               if(e != null){ // If I know the sender
-                                       int senderIndex = e.peer;
-                                       cache[senderIndex].isAlive();
-                                       /* I send to it some of the pending requests not yet satisfied. */
-                                       int t = numberOfDuplicatedRequests;
-                                       for(int i=4;i>=0 && t>0;i--){
-                                               if(pendingRequest[i]==-1)
-                                                       break;
-                                               if(alive(cache[senderIndex].node) && swarm[senderIndex][decode(pendingRequest[i],0)]==1){ //If the sender has that piece
-                                                       ev = new IntMsg(REQUEST, node,pendingRequest[i],0);
-//                                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                                     EDSimulator.add(latency,ev, sender,pid);
-                                                       ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                                       cache[senderIndex].justSent();
-                                               }
-                                               if(!alive(cache[senderIndex].node)){
-                                                       System.out.println("unchoke1 rm neigh "+ cache[i].node.getID() );
-                                                       removeNeighbor(cache[senderIndex].node);
-                                                       processNeighborListSize(node,pid);
-                                                       return;
-                                               }
-                                               t--;
-                                       }
-                                       // I request missing blocks to fill the queue
-                                       int block = getBlock();
-                                       int piece;
-                                       while(block != -2){ //while still available request to send
-                                               if(block < 0){ // No more block to request for the current piece 
-                                                       piece = getPiece();
-                                                       if(piece == -1){ // no more piece to request
-                                                               break;
-                                                       }
-                                                       for(int j=0; j<swarmSize; j++){// send the interested message to those  
-                                                                                                       // nodes which have that piece
-                                                               lastInterested = piece;
-                                                               if(alive(cache[j].node) && swarm[j][piece]==1){                                                                 
-                                                                       ev = new IntMsg(INTERESTED, node, lastInterested,0);
-//                                                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,cache[j].node);
-//                                                                     EDSimulator.add(latency,ev,cache[j].node,pid);  
-                                                                       ((Transport) node.getProtocol(tid)).send(node, cache[j].node, ev, pid);
-                                                                       cache[j].justSent();
-                                                               }
-                                                               
-                                                               if(!alive(cache[j].node)){
-                                                                       //System.out.println("unchoke2 rm neigh "+ cache[j].node.getID() );
-                                                                       removeNeighbor(cache[j].node);
-                                                                       processNeighborListSize(node,pid);
-                                                               }
-                                                       }
-                                                       block = getBlock();
-                                               }
-                                               else{ // block value referred to a real block
-                                                       if(alive(cache[senderIndex].node) && swarm[senderIndex][decode(block,0)]==1 && addRequest(block)){ // The sender has that block
-                                                               ev = new IntMsg(REQUEST, node, block,0);
-//                                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                                             EDSimulator.add(latency,ev,sender,pid);
-                                                               ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-
-                                                               cache[senderIndex].justSent();
-                                                       }
-                                                       else{
-                                                               if(!alive(cache[senderIndex].node)){
-                                                                       System.out.println("unchoke3 rm neigh "+ cache[senderIndex].node.getID() );
-                                                                       removeNeighbor(cache[senderIndex].node);
-                                                                       processNeighborListSize(node,pid);
-                                                               }
-                                                               return;
-                                                       }
-                                                       block = getBlock();
-                                               }
-                                       }
-                                       unchokedBy[senderIndex] = true; // I add the sender to the list
-                               }
-                               else // It should never happen.
-                               {
-                                       System.err.println("despite it should never happen, it happened");
-                                       for(int i=0; i<swarmSize; i++)
-                                               if(cache[i].node !=null)
-                                                       System.err.println(cache[i].node.getID());
-                                       ev = new BitfieldMsg(BITFIELD, true, false, node, status, nPieces);
-//                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                     EDSimulator.add(latency,ev,sender,pid);
-                                       ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                       nBitfieldSent++;
-                               }
-                       };break;
-                               
-                       case INTERESTED: // 4, INTERESTED message.
-                       {
-                               numInterestedPeers++;
-                               Node sender = ((IntMsg)event).getSender();
-                               //System.out.println("process, interested: sender is "+sender.getID()+", local is "+node.getID());
-                               int value = ((IntMsg)event).getInt();
-                               Element e = search(sender.getID());
-                               if(e!=null){
-                                       cache[e.peer].isAlive();
-                                       cache[e.peer].interested = value;
-                               }
-                               else{
-                                       System.err.println("despite it should never happen, it happened");
-                                       ev = new BitfieldMsg(BITFIELD, true, false, node, status, nPieces);
-//                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                     EDSimulator.add(latency,ev,sender,pid);
-                                       ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                       nBitfieldSent++;
-                               }
-                               
-                       }; break;
-                               
-                       case NOT_INTERESTED: // 5, NOT_INTERESTED message.
-                       {
-                               numInterestedPeers--;
-                               Node sender = ((IntMsg)event).getSender();
-                               //System.out.println("process, not_interested: sender is "+sender.getID()+", local is "+node.getID());
-                               int value = ((IntMsg)event).getInt();
-                               Element e = search(sender.getID());
-                               if(e!=null){
-                                       cache[e.peer].isAlive();
-                                       if(cache[e.peer].interested == value)
-                                               cache[e.peer].interested = -1; // not interested
-                               }
-                       }; break;
-                               
-                       case HAVE: // 6, HAVE message.
-                       {               
-                               Node sender = ((IntMsg)event).getSender();
-                               //System.out.println("process, have: sender is "+sender.getID()+", local is "+node.getID());
-                               int piece = ((IntMsg)event).getInt();
-                               Element e = search(sender.getID());
-                               if(e!=null){
-                                       cache[e.peer].isAlive();
-                                       swarm[e.peer][piece]=1;
-                                       rarestPieceSet[piece]++;
-                                       boolean isSeeder = true;
-                                       for(int i=0; i<nPieces; i++){
-                                               isSeeder = isSeeder && (swarm[e.peer][i]==1);   
-                                       }
-                                       e.isSeeder = isSeeder;
-                               }
-                               else{
-                                       System.err.println("despite it should never happen, it happened");
-                                       ev = new BitfieldMsg(BITFIELD, true, false, node, status, nPieces);
-//                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                     EDSimulator.add(latency,ev,sender,pid);
-                                       ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                       nBitfieldSent++;
-                               }
-                       }; break;
-                               
-                       case BITFIELD: // 7, BITFIELD message
-                       {                       
-                               Node sender = ((BitfieldMsg)event).getSender();
-                               int []fileStatus = ((BitfieldMsg)event).getArray();
-                               /*Response with NACK*/
-                               if(!((BitfieldMsg)event).isRequest && !((BitfieldMsg)event).ack){
-                                       Element e = search(sender.getID());
-                                       if(e == null) // if is a response with nack that follows a request
-                                               nBitfieldSent--;
-                                       // otherwise is a response with ack that follows a duplicate
-                                       // insertion attempt
-                                       //System.out.println("process, bitfield_resp_nack: sender is "+sender.getID()+", local is "+node.getID());
-                                       return;
-                               }
-                               /*Request with NACK*/
-                               if(((BitfieldMsg)event).isRequest && !((BitfieldMsg)event).ack){
-                                       //System.out.println("process, bitfield_req_nack: sender is "+sender.getID()+", local is "+node.getID());
-                                       if(alive(sender)){
-                                               Element e = search(sender.getID());
-                                               ev = new BitfieldMsg(BITFIELD, false, true, node, status, nPieces); //response with ack
-//                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                             EDSimulator.add(latency,ev,sender,pid);
-                                               ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                               cache[e.peer].justSent();
-                                       }
-                               }
-                               /*Response with ACK*/
-                               if(!((BitfieldMsg)event).isRequest && ((BitfieldMsg)event).ack){
-                                       nBitfieldSent--;
-                                       //System.out.println("process, bitfield_resp_ack: sender is "+sender.getID()+", local is "+node.getID());
-                                       if(alive(sender)){
-                                               if(addNeighbor(sender)){
-                                                       Element e = search(sender.getID());
-                                                       cache[e.peer].isAlive();
-                                                       swarm[e.peer] = fileStatus;
-                                                       boolean isSeeder = true;
-                                                       for(int i=0; i<nPieces; i++){
-                                                               rarestPieceSet[i]+= fileStatus[i];
-                                                               isSeeder = isSeeder && (fileStatus[i]==1);
-                                                       }
-                                                       e.isSeeder = isSeeder;
-                                                       
-                                                       if(nNodes==10 && !lock){ // I begin to request pieces
-                                                               lock = true;
-                                                               int piece = getPiece();
-                                                               if(piece == -1)
-                                                                       return;
-                                                               lastInterested = piece;
-                                                               currentPiece = lastInterested;
-                                                               ev = new IntMsg(INTERESTED, node, lastInterested,0);
-                                                               for(int i=0; i<swarmSize; i++){// send the interested message to those  
-                                                                                                               // nodes which have that piece
-                                                                       if(alive(cache[i].node) && swarm[i][piece]==1){                                                                         
-//                                                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,cache[i].node);
-//                                                                             EDSimulator.add(latency,ev,cache[i].node,pid);
-                                                                               ((Transport) node.getProtocol(tid)).send(node, cache[i].node, ev, pid);
-                                                                               cache[i].justSent();
-                                                                       }
-                                                               }
-                                                               
-                                                       }
-                                                       
-                                               }
-                                       }
-                                       else
-                                               System.out.println("Sender "+sender.getID()+" not alive");
-                               }
-                               /*Request with ACK*/
-                               if(((BitfieldMsg)event).isRequest && ((BitfieldMsg)event).ack){
-                                       //System.out.println("process, bitfield_req_ack: sender is "+sender.getID()+", local is "+node.getID());
-                                       if(alive(sender)){
-                                               if(addNeighbor(sender)){
-                                                       Element e = search(sender.getID()); 
-                                                       cache[e.peer].isAlive();
-                                                       swarm[e.peer] = fileStatus;
-                                                       boolean isSeeder = true;
-                                                       for(int i=0; i<nPieces; i++){
-                                                               rarestPieceSet[i]+= fileStatus[i]; // I update the rarestPieceSet with the pieces of the new node
-                                                               isSeeder = isSeeder && (fileStatus[i]==1); // I check if the new node is a seeder
-                                                       }
-                                                       e.isSeeder = isSeeder;
-                                                       ev = new BitfieldMsg(BITFIELD, false, true, node, status, nPieces); //response with ack
-//                                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                                     EDSimulator.add(latency,ev,sender,pid);
-                                                       ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                                       cache[e.peer].justSent();
-                                                       if(nNodes==10 && !lock){ // I begin to request pieces
-                                                               int piece = getPiece();
-                                                               if(piece == -1)
-                                                                       return;
-                                                               lastInterested = piece;
-                                                               currentPiece = lastInterested;
-                                                               ev = new IntMsg(INTERESTED, node, lastInterested,0);
-                                                               for(int i=0; i<swarmSize; i++){// send the interested message to those  
-                                                                                                               // nodes which have that piece
-                                                                       if(alive(cache[i].node) && swarm[i][piece]==1){
-//                                                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,cache[i].node);
-//                                                                             EDSimulator.add(latency,ev,cache[i].node,pid);
-                                                                               ((Transport) node.getProtocol(tid)).send(node, cache[i].node, ev, pid);
-                                                                               cache[i].justSent();
-                                                                       }
-                                                               }
-                                                               
-                                                       }
-                                               }
-                                               else {
-                                                       Element e;
-                                                       if((e = search(sender.getID()))!=null){ // The sender was already in the cache
-                                                               cache[e.peer].isAlive();
-                                                               ev = new BitfieldMsg(BITFIELD, false, true, node, status, nPieces); //response with ack
-//                                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                                             EDSimulator.add(latency,ev,sender,pid);
-                                                               ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                                               cache[e.peer].justSent();
-                                                       }
-                                                       else{ // Was not be possible add the sender (nBitfield+nNodes > swarmSize)
-                                                               ev = new BitfieldMsg(BITFIELD, false, false, node, status, nPieces); //response with nack
-//                                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,sender);
-//                                                             EDSimulator.add(latency,ev,sender,pid);
-                                                               ((Transport) node.getProtocol(tid)).send(node, sender, ev, pid);
-                                                       }
-                                               }
-                                               
-                                       }
-                                       else
-                                               System.out.println("Sender "+sender.getID()+" not alive");
-                               }
-                       };break;
-                               
-                       case REQUEST: // 8, REQUEST message.
-                       {
-                               Object evnt;
-                               Node sender = ((IntMsg)event).getSender();
-                               int value = ((IntMsg)event).getInt();
-                               Element e;
-                               BitTorrent senderP;
-                               int remoteRate;
-                               int localRate;
-                               int bandwidth;
-                               int downloadTime;
-                               
-                               e = search(sender.getID());
-                               if (e==null)
-                                       return;
-                               cache[e.peer].isAlive();
-                               
-                               requestToServe.enqueue(value, sender);
-                                                               
-                               /*I serve the enqueued requests until 10 uploding pieces or an empty queue*/
-                               while(!requestToServe.empty() && nPiecesUp <10){ 
-                                       Request req = requestToServe.dequeue();
-                                       e = search(req.sender.getID());
-                                       if(e!=null && alive(req.sender)){
-//                                             ev = new IntMsg(PIECE, node, req.id);
-                                               nPiecesUp++;
-                                               e.valueUP++;
-                                               senderP = ((BitTorrent)req.sender.getProtocol(pid));
-                                               senderP.nPiecesDown++;
-                                               remoteRate = senderP.maxBandwidth/(senderP.nPiecesUp + senderP.nPiecesDown);
-                                               localRate = maxBandwidth/(nPiecesUp + nPiecesDown);
-                                               bandwidth = Math.min(remoteRate, localRate);
-                                               downloadTime = ((16*8)/(bandwidth))*1000; // in milliseconds
-                                               
-                                               ev = new IntMsg(PIECE, node, req.id, 16*8 * 1024);
-                                               ((Transport) node.getProtocol(tid)).send(node, req.sender, ev, pid);
-                                               
-//                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,req.sender);
-//                                             EDSimulator.add(latency+downloadTime,ev,req.sender,pid);
-                                               cache[e.peer].justSent();
-                                               
-                                               /*I send to me an event to indicate that the download is completed.
-                                               This prevent that, when the receiver death occurres, my value nPiecesUp
-                                               doesn't decrease.*/
-                                               evnt = new SimpleMsg(DOWNLOAD_COMPLETED, req.sender);
-//                                             EDSimulator.add(latency+downloadTime,evnt,node,pid); 
-                                               ((Transport) node.getProtocol(tid)).send(node, node, evnt, pid);
-                                       }
-                               }
-                       }; break;
-                               
-                       case PIECE: // 9, PIECE message.
-                       {
-                               Node sender = ((IntMsg)event).getSender();
-                               /*      Set the correct value for the local uploading and remote 
-                               downloading number of pieces */
-                               nPiecesDown--;
-                               
-                               if(peerStatus == 1)// To save CPU cycles
-                                       return;
-                               //System.out.println("process, piece: sender is "+sender.getID()+", local is "+node.getID());
-                               Element e = search(sender.getID());
-                               
-                               if(e==null){ //I can't accept a piece not wait
-                                       return;
-                               }
-                               e.valueDOWN++;
-                               
-                               cache[e.peer].isAlive();
-                               
-                               int value = ((IntMsg)event).getInt();
-                               int piece = decode(value,0);
-                               int block = decode(value,1);
-                               /* If the block has not been already downloaded and it belongs to
-                                       the current downloading piece.*/
-                               if(piece == currentPiece && decode(pieceStatus[block],0)!= piece){
-                                       pieceStatus[block] = value;
-                                       status[piece]++;
-                                       removeRequest(value);                                   
-                                       requestNextBlocks(node, pid, e.peer);
-                                       
-                               }else{ // Either a future piece or an owned piece
-                                       if(piece!=currentPiece && status[piece]!=16){ // Piece not owned, will be considered later
-                                               incomingPieces.enqueue(value, sender);
-                                       }
-                                       
-                               }
-                               ev = new IntMsg(CANCEL, node, value,0);
-                               /* I send a CANCEL to all nodes to which I previously requested the block*/
-                               for(int i=0; i<swarmSize; i++){ 
-                                       if(alive(cache[i].node) && unchokedBy[i]==true && swarm[i][decode(block,0)]==1 && cache[i].node != sender){
-//                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,cache[i].node);
-//                                             EDSimulator.add(latency,ev,cache[i].node,pid);
-                                               ((Transport) node.getProtocol(tid)).send(node, cache[i].node, ev, pid);
-                                               cache[i].justSent();
-                                       }
-                               }
-                               
-                               if(status[currentPiece]==16){ // if piece completed, I change the currentPiece to the next wanted                                       
-                                       nPieceCompleted++;
-                                       ev = new IntMsg(HAVE, node, currentPiece,0);
-                                       for(int i=0; i<swarmSize; i++){ // I send the HAVE for the piece
-                                               if(alive(cache[i].node)){
-//                                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,cache[i].node);
-//                                                     EDSimulator.add(latency,ev,cache[i].node,pid);
-                                                       ((Transport) node.getProtocol(tid)).send(node, cache[i].node, ev, pid);
-                                                       cache[i].justSent();
-                                               }
-                                               if(!alive(cache[i].node)){
-                                                       //System.out.println("piece3 rm neigh "+ cache[i].node.getID() );                                                       
-                                                       removeNeighbor(cache[i].node);
-                                                       processNeighborListSize(node,pid);
-                                               }
-                                       }
-                                       ev = new IntMsg(NOT_INTERESTED, node, currentPiece,0);
-                                       for(int i=0; i<swarmSize; i++){ // I send the NOT_INTERESTED to which peer I sent an INTERESTED
-                                               if(swarm[i][piece]==1 && alive(cache[i].node)){
-//                                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node,cache[i].node);
-//                                                     EDSimulator.add(latency,ev,cache[i].node,pid);
-                                                       ((Transport) node.getProtocol(tid)).send(node, cache[i].node, ev, pid);
-                                                       cache[i].justSent();
-                                               }
-                                               if(!alive(cache[i].node)){
-                                                       //System.out.println("piece4 rm neigh "+ cache[i].node.getID() );                                                       
-                                                       removeNeighbor(cache[i].node);
-                                                       processNeighborListSize(node,pid);
-                                               }
-                                       }
-                                       if(nPieceCompleted == nPieces){
-                                               System.out.println("FILE COMPLETED for peer "+node.getID());
-                                               this.peerStatus = 1;    
-                                       }
-                                       
-                                       /*      I set the currentPiece to the lastInterested. Then I extract 
-                                               the queued received blocks
-                                               */
-                                       
-                                       currentPiece = lastInterested;
-                                       int m = incomingPieces.dim;
-                                       while(m > 0){ // I process the queue
-                                               m--;
-                                               Request temp = incomingPieces.dequeue();
-                                               int p = decode(temp.id,0); // piece id
-                                               int b = decode(temp.id,1); // block id
-                                               Element s = search(temp.sender.getID());
-                                               if(s==null) // if the node that sent the block in the queue is dead
-                                                       continue;
-                                               if(p==currentPiece && decode(pieceStatus[b],0)!= p){
-                                                       pieceStatus[b] = temp.id;
-                                                       status[p]++;
-                                                       removeRequest(temp.id);
-                                                       requestNextBlocks(node, pid, s.peer);
-                                               }
-                                               else{ // The piece not currently desired will be moved to the tail
-                                                       if(p!= currentPiece) // If not a duplicate block but belongs to another piece
-                                                               incomingPieces.enqueue(temp.id,temp.sender);
-                                                       else // duplicate block
-                                                               requestNextBlocks(node, pid, s.peer);
-                                               }
-                                       }
-                               }
-                       }; break;
-                               
-                       case CANCEL:
-                       {
-                               Node sender = ((IntMsg)event).getSender();
-                               int value = ((IntMsg)event).getInt();
-                               requestToServe.remove(sender, value);
-                       };break;
-                               
-                       case PEERSET: // PEERSET message
-                       {
-                               Node sender = ((PeerSetMsg)event).getSender();
-                               //System.out.println("process, peerset: sender is "+sender.getID()+", local is "+node.getID());
-                               Neighbor n[] = ((PeerSetMsg)event).getPeerSet();
-                               
-                               for(int i=0; i<peersetSize; i++){
-                                       if( n[i]!=null && alive(n[i].node) && search(n[i].node.getID())==null && nNodes+nBitfieldSent <swarmSize-2) {
-                                               ev = new BitfieldMsg(BITFIELD, true, true, node, status, nPieces);
-//                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node,n[i].node);
-//                                             EDSimulator.add(latency,ev,n[i].node,pid);
-                                               ((Transport) node.getProtocol(tid)).send(node, n[i].node, ev, pid);
-
-                                               nBitfieldSent++;
-                                               // Here I should call the Neighbor.justSent(), but here
-                                               // the node is not yet in the cache.
-                                       }
-                               }
-                       }; break;
-                               
-                       case TRACKER: // TRACKER message
-                       {
-                               
-                               int j=0;
-                               Node sender = ((SimpleMsg)event).getSender();
-                               //System.out.println("process, tracker: sender is "+sender.getID()+", local is "+node.getID());
-                               if(!alive(sender))
-                                       return;
-                               Neighbor tmp[] = new Neighbor[peersetSize];
-                               int k=0;
-                               if(nNodes <= peersetSize){
-                                       for(int i=0; i< nMaxNodes+maxGrowth; i++){
-                                               if(cache[i].node != null && cache[i].node.getID()!= sender.getID()){
-                                                       tmp[k]=cache[i];
-                                                       k++;
-                                               }
-                                       }
-                                       ev = new PeerSetMsg(PEERSET, tmp, node);
-//                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node, sender);
-//                                     EDSimulator.add(latency,ev,sender,pid);
-                                       ((Transport) node.getProtocol(tid)).send(node,sender, ev, pid);
-                                       return;
-                               }
-                               
-                               while(j < peersetSize){
-                                       int i = CommonState.r.nextInt(nMaxNodes+maxGrowth);
-                                       for (int z=0; z<j; z++){
-                                               if(cache[i].node==null || tmp[z].node.getID() == cache[i].node.getID() || cache[i].node.getID() == sender.getID()){
-                                                       z=0;
-                                                       i= CommonState.r.nextInt(nMaxNodes+maxGrowth);
-                                               }
-                                       }
-                                       if(cache[i].node != null){
-                                               tmp[j] = cache[i];
-                                               j++;
-                                       }
-                               }
-                               ev = new PeerSetMsg(PEERSET, tmp, node);
-//                             latency = ((Transport)node.getProtocol(tid)).getLatency(node, sender);
-//                             EDSimulator.add(latency,ev,sender,pid);
-                               ((Transport) node.getProtocol(tid)).send(node,sender, ev, pid);
-                       }; break;
-                               
-                       case CHOKE_TIME: //Every 10 secs.
-                       {       
-                               n_choke_time++;
-                               
-                               ev = new SimpleEvent(CHOKE_TIME);
-                               EDSimulator.add(10000,ev,node,pid);
-                               int j=0;
-                               /*I copy the interested nodes in the byBandwidth array*/
-                               for(int i=0;i< swarmSize && byPeer[i].peer != -1; i++){
-                                       if(cache[byPeer[i].peer].interested > 0){
-                                               byBandwidth[j]=byPeer[i]; //shallow copy
-                                               j++;
-                                       }
-                               }
-                               
-                               /*It ensures that in the next 20sec, if there are less nodes interested
-                                       than now, those in surplus will not be ordered. */
-                               for(;j<swarmSize;j++){
-                                       byBandwidth[j]=null;
-                               }
-                               sortByBandwidth();
-                               int optimistic = 3;
-                               int luckies[] = new int[3];
-                               try{ // It takes the first three neighbors
-                                       luckies[0] = byBandwidth[0].peer;
-                                       optimistic--;
-                                       luckies[1] = byBandwidth[1].peer;
-                                       optimistic--;
-                                       luckies[2] = byBandwidth[2].peer;
-                               }
-                               catch(NullPointerException e){ // If not enough peer in byBandwidth it chooses the other romdomly 
-                                       for(int z = optimistic; z>0;z--){
-                                               int lucky = CommonState.r.nextInt(nNodes);
-                                               while(cache[byPeer[lucky].peer].status ==1 && alive(cache[byPeer[lucky].peer].node) && 
-                                                         cache[byPeer[lucky].peer].interested == 0)// until the lucky peer is already unchoked or not interested
-                                                       lucky = CommonState.r.nextInt(nNodes);
-                                               luckies[3-z]= byPeer[lucky].peer;
-                                       }
-                               }
-                               for(int i=0; i<swarmSize; i++){ // I perform the chokes and the unchokes
-                                       if((i==luckies[0] || i==luckies[1] || i==luckies[2]) &&  alive(cache[i].node) && cache[i].status != 2){ //the unchokes
-                                               cache[i].status = 1;
-                                               ev = new SimpleMsg(UNCHOKE, node);
-//                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node, cache[i].node);
-//                                             EDSimulator.add(latency,ev,cache[i].node,pid);
-                                               ((Transport) node.getProtocol(tid)).send(node,cache[i].node, ev, pid);
-                                               cache[i].justSent();
-                                               //System.out.println("average time, unchoked: "+cache[i].node.getID());
-                                       }
-                                       else{ // the chokes
-                                               if(alive(cache[i].node) && (cache[i].status == 1 || cache[i].status == 2)){
-                                                       cache[i].status = 0;
-                                                       ev = new SimpleMsg(CHOKE, node);
-//                                                     latency = ((Transport)node.getProtocol(tid)).getLatency(node, cache[i].node);
-//                                                     EDSimulator.add(latency,ev,cache[i].node,pid);
-                                                       ((Transport) node.getProtocol(tid)).send(node,cache[i].node, ev, pid);
-                                                       cache[i].justSent();
-                                               }
-                                       }
-                               }
-                               
-                               if(n_choke_time%2==0){ //every 20 secs. Used in computing the average download rates
-                                       for(int i=0; i<nNodes; i++){
-                                               if(this.peerStatus == 0){ // I'm a leeacher
-                                                       byPeer[i].head20 = byPeer[i].valueDOWN;
-                                               }
-                                               else{
-                                                       byPeer[i].head20 = byPeer[i].valueUP;
-                                               }
-                                       }
-                               }
-                       }; break;
-                               
-                       case OPTUNCHK_TIME:
-                       {
-                               
-                               //System.out.println("process, optunchk_time");
-                               
-                               ev = new SimpleEvent(OPTUNCHK_TIME);
-                               EDSimulator.add(30000,ev,node,pid);
-                               int lucky = CommonState.r.nextInt(nNodes);
-                               while(cache[byPeer[lucky].peer].status ==1)// until the lucky peer is already unchoked
-                                       lucky = CommonState.r.nextInt(nNodes);
-                               if(!alive(cache[byPeer[lucky].peer].node))
-                                       return;
-                               cache[byPeer[lucky].peer].status = 1;
-                               Object msg = new SimpleMsg(UNCHOKE,node);
-//                             latency = ((Transport)node.getProtocol(tid)).getLatency(node, cache[byPeer[lucky].peer].node);
-//                             EDSimulator.add(latency,msg,cache[byPeer[lucky].peer].node,pid);
-                               ((Transport) node.getProtocol(tid)).send(node,cache[byPeer[lucky].peer].node, msg, pid);
-                               cache[byPeer[lucky].peer].justSent();
-                       }; break;
-                               
-                       case ANTISNUB_TIME:
-                       {
-                               if(this.peerStatus == 1) // I'm a seeder, I don't update the event
-                                       return;
-                               //System.out.println("process, antisnub_time");
-                               for(int i=0; i<nNodes; i++){
-                                       if(byPeer[i].valueDOWN >0 && (byPeer[i].valueDOWN - byPeer[i].head60)==0){// No blocks downloaded in 1 min
-                                               cache[byPeer[i].peer].status = 2; // I'm snubbed by it
-                                       }
-                                       byPeer[i].head60 = byPeer[i].valueDOWN;
-                               }
-                               ev = new SimpleEvent(ANTISNUB_TIME);
-                               EDSimulator.add(60000,ev,node,pid);
-                               long time = CommonState.getTime();
-                       }; break;
-                               
-                       case CHECKALIVE_TIME:
-                       {
-                               
-                               //System.out.println("process, checkalive_time");
-                               
-                               long now = CommonState.getTime();
-                               for(int i=0; i<swarmSize; i++){
-                                       /*If are at least 2 minutes (plus 1 sec of tolerance) that
-                                       I don't send anything to it.*/
-                                       if(alive(cache[i].node) && (cache[i].lastSent < (now-121000))){
-                                               Object msg = new IntMsg(KEEP_ALIVE,node,0,0);
-//                                             latency = ((Transport)node.getProtocol(tid)).getLatency(node, cache[i].node);
-//                                             EDSimulator.add(latency,msg,cache[i].node,pid);
-                                               ((Transport) node.getProtocol(tid)).send(node,cache[i].node, msg, pid);
-                                               cache[i].justSent();
-                                       }
-                                       /*If are at least 2 minutes (plus 1 sec of tolerance) that I don't
-                                       receive anything from it though I sent a keepalive 2 minutes ago*/
-                                       else{
-                                               if(cache[i].lastSeen <(now-121000) && cache[i].node != null && cache[i].lastSent < (now-121000)){
-                                                       System.out.println("process, checkalive_time, rm neigh " + cache[i].node.getID());
-                                                       if(cache[i].node.getIndex() != -1){
-                                                               System.out.println("This should never happen: I remove a node that is not effectively died");
-                                                       }
-                                                       removeNeighbor(cache[i].node);
-                                                       processNeighborListSize(node,pid);
-                                               }
-                                       }
-                               }
-                               ev = new SimpleEvent(CHECKALIVE_TIME);
-                               EDSimulator.add(120000,ev,node,pid);
-                       }; break;
-                               
-                       case TRACKERALIVE_TIME:
-                       {
-                               //System.out.println("process, trackeralive_time");
-                               if(alive(tracker)){
-                                       ev = new SimpleEvent(TRACKERALIVE_TIME);
-                                       EDSimulator.add(1800000,ev,node,pid);
-                               }
-                               else
-                                       tracker=null;
-                               
-                       }; break;
-                               
-                       case DOWNLOAD_COMPLETED:
-                       {
-                               nPiecesUp--;
-                       }; break;
-                               
-               }
-       }
-       
-       /**
-        *      Given a piece index and a block index it encodes them in an unique integer value.
-        *      @param piece the index of the piece to encode.
-        *      @param block the index of the block to encode.
-        *      @return the encoding of the piece and the block indexes.
-        */
-       private int encode(int piece, int block){
-               return (piece*100)+block;
-               
-       }
-       /** 
-        *      Returns either the piece or the block that contained in the <tt>value</tt> depending
-        *      on <tt>part</tt>: 0 means the piece value, 1 the block value.
-        *      @param value the ID of the block to decode.
-        *      @param part the information to extract from <tt>value</tt>. 0 means the piece index, 1 the block index.
-        *      @return the piece or the block index depending about the value of <tt>part</tt>
-        */
-       private int decode(int value, int part){
-               if (value==-1) // Not a true value to decode
-                       return -1;
-               if(part == 0) // I'm interested to the piece
-                       return value/100;
-               else // I'm interested to the block
-                       return value%100;
-       }
-       
-       /**
-        *      Used by {@link NodeInitializer#choosePieces(int, BitTorrent) NodeInitializer} to set 
-        *      the number of piece completed from the beginning in according with
-        *      the distribution in the configuration file.
-        *      @param number the number of piece completed
-        */
-       public void setCompleted(int number){
-               this.nPieceCompleted = number;
-       }
-       
-       /**
-        *      Sets the status (the set of blocks) of the file for the current node.
-        *  Note that a piece is considered <i>completed</i> if the number
-        *  of downloaded blocks is 16.
-        *  @param index The index of the piece
-        *  @param value Number of blocks downloaded for the piece index.
-        */
-       public void setStatus(int index, int value){
-               status[index]=value;
-       }
-       
-       /**
-        *      Sets the status of the local node.
-        *      @param status The status of the node: 1 means seeder, 0 leecher
-        */
-       public void setPeerStatus(int status){
-               this.peerStatus = status;
-       }
-       
-       /**
-        *      Gets the status of the local node.
-        *      @return The status of the local node: 1 means seeder, 0 leecher
-        */
-       public int getPeerStatus(){
-               return peerStatus;
-       }
-       
-       /**
-        *  Gets the number of blocks for a given piece owned by the local node.
-        *      @param index The index of the piece
-        *      @return Number of blocks downloaded for the piece index
-        */
-       public int getStatus(int index){
-               return status[index];   
-       }
-       
-       /**
-        *      Sets the maximum bandwdith for the local node.
-        *      @param value The value of bandwidth in Kbps
-        */
-       public void setBandwidth(int value){
-               maxBandwidth = value;
-       }
-       
-       /**
-        *      Checks if a node is still alive in the simulated network.
-        *      @param node The node to check
-        *      @return true if the node <tt>node</tt> is up, false otherwise
-        *      @see peersim.core.GeneralNode#isUp
-        */
-       public boolean alive(Node node){
-               if(node == null)
-                       return false;
-               else
-                       return node.isUp();
-       }
-               
-       /**     
-        *      Adds a neighbor to the cache of the local node.
-        *  The new neighbor is put in the first null position.
-        *      @param neighbor The neighbor node to add
-        *  @return <tt>false</tt> if the neighbor is already present in the cache (this can happen when the peer requests a
-        *      new peer set to the tracker an there is still this neighbor within) or no place is available.
-        *      Otherwise, returns true if the node is correctly added to the cache.
-        */
-       public boolean addNeighbor(Node neighbor){
-               if(search(neighbor.getID()) !=null){// if already exists
-               //      System.err.println("Node "+neighbor.getID() + " not added, already exist.");
-                       return false;
-               }
-               if(this.tracker == null){ // I'm in the tracker's BitTorrent protocol
-                       for(int i=0; i< nMaxNodes+maxGrowth; i++){
-                               if(cache[i].node == null){
-                                       cache[i].node = neighbor;
-                                       cache[i].status = 0; //chocked
-                                       cache[i].interested = -1; //not interested
-                                       this.nNodes++;
-                                       
-                                       //System.err.println("i: " + i +" nMaxNodes: " + nMaxNodes);
-                                       return true;
-                               }
-                       }
-               }
-               else{
-                       if((nNodes+nBitfieldSent) < swarmSize){
-                               //System.out.println("I'm the node " + this.thisNodeID + ", trying to add node "+neighbor.getID());
-                               for(int i=0; i<swarmSize; i++){
-                                       if(cache[i].node == null){
-                                               cache[i].node = neighbor;
-                                               cache[i].status = 0; //choked
-                                               cache[i].interested = -1; // not interested
-                                               byPeer[nNodes].peer = i;
-                                               byPeer[nNodes].ID = neighbor.getID();
-                                               sortByPeer();
-                                               this.nNodes++;
-                                               //System.out.println(neighbor.getID()+" added!");
-                                               return true;
-                                       }
-                               }
-                               System.out.println("Node not added, no places available");
-                       }
-               }
-               return false;
-       }
-       
-       /**
-        *      Removes a neighbor from the cache of the local node.
-        *      @param neighbor The node to remove
-        *      @return true if the node is correctly removed, false otherwise.
-     */
-       public boolean removeNeighbor(Node neighbor) {
-               
-               if (neighbor == null)
-                       return true;
-               
-               // this is the tracker's bittorrent protocol
-               if (this.tracker == null) {
-                       for (int i=0; i< (nMaxNodes+maxGrowth); i++) {
-                               
-                               // check the feasibility of the removal
-                               if ( (cache[i] != null) && (cache[i].node != null) &&
-                                        (cache[i].node.getID() == neighbor.getID()) ) {
-                                       cache[i].node = null;
-                                       this.nNodes--;
-                                       return true;
-                               }
-                       }
-                       return false;
-               }
-               // this is the bittorrent protocol of a peer
-               else {
-                       
-                       Element e = search(neighbor.getID());
-                       
-                       if (e != null) {
-                               for (int i=0; i<nPieces; i++) {
-                                       rarestPieceSet[i] -= swarm[e.peer][i];
-                                       swarm[e.peer][i] = 0;
-                               }
-                               
-                               cache[e.peer].node = null;
-                               cache[e.peer].status = 0;
-                               cache[e.peer].interested = -1;
-                               unchokedBy[e.peer] = false;
-                               this.nNodes--;
-                               e.peer = -1;
-                               e.ID = Integer.MAX_VALUE;
-                               e.valueUP = 0;
-                               e.valueDOWN = 0;
-                               e.head20 = 0;
-                               e.head60 = 0;
-                               sortByPeer();
-                               
-                               return true;
-                       }
-               }
-               return false;
-       }
-       
-       /**
-     * Adds a request to the pendingRequest queue.
-        *      @param block The requested block
-        *      @return true if the request has been successfully added to the queue, false otherwise
-        */
-       private boolean addRequest(int block){
-               int i=4;
-               while(i>=0 && pendingRequest[i]!=-1){
-                       i--;
-               }
-               if(i>=0){
-                       pendingRequest[i] = block;
-                       return true;
-               }
-               else { // It should never happen
-                          //System.err.println("pendingRequest queue full");
-                       return false;           
-               }
-       }
-       
-       /**
-        *      Removes the block with the given <tt>id</tt> from the {@link #pendingRequest} queue
-        *  and sorts the queue leaving the empty cell at the left.
-        *      @param id the id of the requested block
-        */
-       private void removeRequest(int id){
-               int i = 4;
-               for(; i>=0; i--){
-                       if(pendingRequest[i]==id)
-                               break;
-               }
-               for(; i>=0; i--){
-                       if(i==0)
-                               pendingRequest[i] = -1;
-                       else
-                               pendingRequest[i] = pendingRequest[i-1];
-               }
-       }
-       
-       /**
-        *      Requests new block until the {@link #pendingRequest} is full to the sender of the just received piece.
-        *      It calls {@link #getNewBlock(Node, int)} to implement the <i>strict priority</i> strategy. 
-        *      @param node the local node
-        *      @param pid the BitTorrent protocol id
-        *      @param sender the sender of the just received received piece. 
-        */
-       private void requestNextBlocks(Node node, int pid, int sender){
-               int block = getNewBlock(node, pid);
-               while(block != -2){
-                       if(unchokedBy[sender]==true && alive(cache[sender].node) && addRequest(block)){
-                               Object ev = new IntMsg(REQUEST, node, block,0);
-                               
-//                             long latency = ((Transport)node.getProtocol(tid)).getLatency(node,cache[sender].node);
-//                             EDSimulator.add(latency,ev,cache[sender].node,pid);
-                               
-                               ((Transport) node.getProtocol(tid)).send(node,cache[sender].node, ev, pid);
-                               cache[sender].justSent();
-                       }
-                       else{ // I cannot send request
-                               if(!alive(cache[sender].node) && cache[sender].node!=null){
-                                       System.out.println("piece2 rm neigh "+ cache[sender].node.getID() );
-                                       removeNeighbor(cache[sender].node);
-                                       processNeighborListSize(node,pid);
-                               }
-                               return;
-                       }
-                       block = getNewBlock(node, pid);
-               }
-       }
-       
-       /**
-        *      It returns the id of the next block to request. Sends <tt>INTERESTED</tt> if the new
-        *      block belongs to a new piece.
-        *      It uses {@link #getBlock()} to get the next block of a piece and calls {@link #getPiece()}
-        *      when all the blocks for the {@link #currentPiece} have been requested.
-        *      @param node the local node
-        *      @param pid the BitTorrent protocol id
-        *      @return -2 if no more places available in the <tt>pendingRequest</tt> queue;<br/>
-        *                      the value of the next block to request otherwise</p>
-        */
-       private int getNewBlock(Node node, int pid){
-               int block = getBlock();
-               if(block < 0){ // No more block to request for the current piece 
-                       
-                       if(block ==-2) // Pending request queue full
-                               return -2;
-                       
-                       int newPiece = getPiece();
-                       if(newPiece == -1){ // no more piece to request
-                               return -2;
-                       }
-                       
-                       lastInterested = newPiece;
-                       Object ev = new IntMsg(INTERESTED, node, lastInterested,0);
-                       
-                       for(int j=0; j<swarmSize; j++){// send the interested message to those  
-                                                                       // nodes which have that piece
-                               if(alive(cache[j].node) && swarm[j][newPiece]==1){
-//                                     long latency = ((Transport)node.getProtocol(tid)).getLatency(node,cache[j].node);
-//                                     EDSimulator.add(latency,ev,cache[j].node,pid);
-                                       ((Transport) node.getProtocol(tid)).send(node,cache[j].node, ev, pid);
-                                       cache[j].justSent();
-                               }
-                               if(!alive(cache[j].node)){
-                                       //System.out.println("piece1 rm neigh "+ cache[j].node.getID() );
-                                       
-                                       removeNeighbor(cache[j].node);
-                                       processNeighborListSize(node,pid);
-                               }
-                       }
-                       block = getBlock();
-                       return block;
-               }
-               else{
-                       // block value referred to a real block
-                       return block;
-               }
-       }
-       
-       /**
-        *      Returns the next block to request for the {@link #currentPiece}.
-        *      @return an index of a block of the <tt>currentPiece</tt> if there are still 
-        *                      available places in the {@link #pendingRequest} queue;<br/>
-        *                      -2 if the <tt>pendingRequest</tt> queue is full;<br/>
-        *                      -1 if no more blocks to request for the current piece. 
-        */
-       private int getBlock(){
-               int i=4;
-               while(i>=0 && pendingRequest[i]!=-1){ // i is the first empty position from the head
-                       i--;
-               }
-               if(i==-1){// No places in the pendingRequest available
-                                 //System.out.println("Pendig request queue full!");
-                       return -2;
-               }
-               int j;
-               //The queue is not empty & last requested block belongs to lastInterested piece 
-               if(i!=4 && decode(pendingRequest[i+1],0)==lastInterested)
-                       j=decode(pendingRequest[i+1],1)+1; // the block following the last requested
-               else // I don't know which is the next block, so I search it.
-                       j=0; 
-               /*      I search another block until the current has been already received. 
-                       *       If in pieceStatus at position j there is a block that belongs to
-                       *       lastInterested piece, means that the block j has been already
-                       *       received, otherwise I can request it.
-                       */
-               while(j<16 && decode(pieceStatus[j],0)==lastInterested){
-                       j++;
-               }
-               if(j==16) // No more block to request for lastInterested piece
-                       return -1;
-               return encode(lastInterested,j);
-       }
-       
-       /**
-        *      Returns the next correct piece to download. It choose the piece by using the
-        *      <i>random first</i> and <i>rarest first</i> policy. For the beginning 4 pieces
-        *      of a file the first one is used then the pieces are chosen using <i>rarest first</i>.
-        *      @see "Documentation about the BitTorrent module"
-        *      @return the next piece to download. If the whole file has been requested
-        *      -1 is returned.
-        */
-       private int getPiece(){
-               int piece = -1;
-               if(nPieceCompleted < 4){ //Uses random first piece
-                       piece = CommonState.r.nextInt(nPieces);
-                       while(status[piece]==16 || piece == currentPiece) // until the piece is owned
-                               piece = CommonState.r.nextInt(nPieces);
-                       return piece;
-               }
-               else{ //Uses rarest piece first
-                       int j=0;
-                       for(; j<nPieces; j++){ // I find the first not owned piece
-                               if(status[j]==0){
-                                       piece = j;
-                                       if(piece != lastInterested) // teoretically it works because
-                                                                                               // there should be only one interested 
-                                                                                               // piece not yet downloaded
-                                               break;
-                               }
-                       }
-                       if(piece==-1){ // Never entered in the previous 'if' statement; for all
-                                                  // pieces an has been sent
-                               return -1;
-                       }
-                       
-                       int rarestPieces[] = new int[nPieces-j]; // the pieces with the less number of occurences\
-                       rarestPieces[0] = j;
-                       int nValues = 1; // number of pieces less distributed in the network
-                       for(int i=j+1; i<nPieces; i++){ // Finds the rarest piece not owned
-                               if(rarestPieceSet[i]< rarestPieceSet[rarestPieces[0]] && status[i]==0){ // if strictly less than the current one
-                                       rarestPieces[0] = i; 
-                                       nValues = 1;
-                               }
-                               if(rarestPieceSet[i]==rarestPieceSet[rarestPieces[0]] && status[i]==0){ // if equal
-                                       rarestPieces[nValues] = i;
-                                       nValues++;
-                               }
-                       }
-                       
-                       piece = CommonState.r.nextInt(nValues); // one of the less owned pieces
-                       return rarestPieces[piece];
-               }
-       }
-       
-       /**
-        *      Returns the file's size as number of pieces of 256KB.
-        *      @return number of pieces that compose the file.
-        */
-       public int getNPieces(){
-               return nPieces; 
-       }
-       /**
-        *      Clone method of the class. Returns a deep copy of the BitTorrent class. Used
-        *      by the simulation to initialize the {@link peersim.core.Network}
-        *      @return the deep copy of the BitTorrent class.
-        */
-       public Object clone(){
-               Object prot = null;
-               try{
-                       prot = (BitTorrent)super.clone();
-               }
-               catch(CloneNotSupportedException e){};
-               
-               ((BitTorrent)prot).cache = new Neighbor[swarmSize];
-               for(int i=0; i<swarmSize; i++){
-                       ((BitTorrent)prot).cache[i] = new Neighbor();
-               }
-               
-               ((BitTorrent)prot).byPeer = new Element[swarmSize];
-               for(int i=0; i<swarmSize; i++){
-                       ((BitTorrent)prot).byPeer[i] = new Element();
-               }
-               
-               ((BitTorrent)prot).unchokedBy = new boolean[swarmSize];
-               
-               ((BitTorrent)prot).byBandwidth = new Element[swarmSize];
-               ((BitTorrent)prot).status = new int[nPieces];
-               ((BitTorrent)prot).pieceStatus = new int[16];
-               for(int i=0; i<16;i++)
-                       ((BitTorrent)prot).pieceStatus[i] = -1;
-               ((BitTorrent)prot).pendingRequest = new int[5];
-               for(int i=0; i<5;i++)
-                       ((BitTorrent)prot).pendingRequest[i] = -1;
-               ((BitTorrent)prot).rarestPieceSet = new int[nPieces];
-               for(int i=0; i<nPieces;i++)
-                       ((BitTorrent)prot).rarestPieceSet[i] = 0;
-               ((BitTorrent)prot).swarm = new int[swarmSize][nPieces];
-               ((BitTorrent)prot).requestToServe = new Queue(20);
-               ((BitTorrent)prot).incomingPieces = new Queue(100);
-               return prot;
-       }
-       
-       /**
-        *      Sorts {@link #byPeer} array by peer's ID. It implements the <i>InsertionSort</i>
-        *      algorithm. 
-        */
-       public void sortByPeer(){
-               int i;
-               
-               for(int j=1; j<swarmSize; j++)   // out is dividing line
-               {
-                       Element key = new Element(); 
-                       byPeer[j].copyTo(key) ;    // remove marked item
-                       i = j-1;           // start shifts at out
-                       while(i>=0 && (byPeer[i].ID > key.ID)) // until one is smaller,
-                       {
-                               byPeer[i].copyTo(byPeer[i+1]);      // shift item right,
-                               i--;            // go left one position
-                       }
-                       key.copyTo(byPeer[i+1]);         // insert marked item
-               } 
-               
-       }
-       
-       /**
-        *      Sorts the array {@link #byBandwidth} using <i>QuickSort</i> algorithm.
-        *      <tt>null</tt> elements and seeders are moved to the end of the array.
-        */
-       public void sortByBandwidth() {
-        quicksort(0, swarmSize-1);
-    }
-       
-       /**
-        *      Used by {@link #sortByBandwidth()}. It's the implementation of the
-        *      <i>QuickSort</i> algorithm.
-        *      @param left the leftmost index of the array to sort.
-        *      @param right the rightmost index of the array to sort.
-        */
-       private void quicksort(int left, int right) {
-        if (right <= left) return;
-        int i = partition(left, right);
-        quicksort(left, i-1);
-        quicksort(i+1, right);
-    }
-       
-       /**
-        *      Used by {@link #quicksort(int, int)}, partitions the subarray to sort returning
-        *      the splitting point as stated by the <i>QuickSort</i> algorithm.
-        *      @see "The <i>QuickSort</i> algorithm".
-        */
-       private int partition(int left, int right) {
-        int i = left - 1;
-        int j = right;
-        while (true) {
-            while (greater(byBandwidth[++i], byBandwidth[right]))      // find item on left to swap
-                ;                               // a[right] acts as sentinel
-            while (greater(byBandwidth[right], byBandwidth[--j])) {      // find item on right to swap
-                if (j == left) break;  // don't go out-of-bounds
-                       }
-            if (i >= j) break;                  // check if pointers cross
-            swap(i, j);                      // swap two elements into place
-        }
-        swap(i, right);                      // swap with partition element
-        return i;
-    }
-       
-       /**
-        *      Aswers to the question "is x > y?". Compares the {@link Element}s given as 
-        *      parameters. <tt>Element x</tt> is greater than <tt>y</tt> if isn't <tt>null</tt>
-        *      and in the last 20 seconds the local node has downloaded ("uploaded" if the local node is a 
-        *      seeder) more blocks than from <tt>y</tt>.
-        *      @param x the first <tt>Element</tt> to compare.
-        *      @param y the second <tt>Element</tt> to compare
-        *      @return <tt>true</tt> if x > y;<br/>
-        *                      <tt>false</tt> otherwise.
-        */
-    private boolean greater(Element x, Element y) {
-               /*
-                * Null elements and seeders are shifted at the end
-                * of the array
-                */
-               if (x==null) return false;
-               if (y==null) return true;
-               if (x.isSeeder) return false;
-               if (y.isSeeder) return true;
-               
-               // if the local node is a leecher
-               if (peerStatus==0) {
-                       if ((x.valueDOWN - x.head20) >
-                               (y.valueDOWN -y.head20))
-                               return true;
-                       else return false;
-               }
-               
-               // if peerStatus==1 (the local node is a seeder)
-               else {                  
-                       if ((x.valueUP - x.head20) >
-                               (y.valueUP -y.head20))
-                               return true;
-                       else return false;
-               }
-    }
-       
-       /**
-        *      Swaps {@link Element} <tt>i</tt> with <tt>j</tt> in the {@link #byBandwidth}.<br/>
-        *      Used by {@link #partition(int, int)}
-        *      @param i index of the first element to swap
-        *      @param j index of the second element to swap
-        */
-       private void swap(int i, int j) {
-        Element swap = byBandwidth[i];
-        byBandwidth[i] = byBandwidth[j];
-        byBandwidth[j] = swap;
-    }
-       
-       /**     Searches the node with the given ID. It does a dychotomic 
-        *      search.
-        *      @param ID ID of the node to search.
-        *      @return the {@link Element} in {@link #byPeer} which represents the node with the
-        *      given ID.
-        */
-       public Element search(long ID){
-               int low = 0;
-               int high = swarmSize-1;
-               int p = low+((high-low)/2);              //Initial probe position
-               while ( low <= high) {
-                       if ( byPeer[p] == null || byPeer[p].ID > ID)
-                               high = p - 1;
-                       else { 
-                               if( byPeer[p].ID < ID )  //Wasteful second comparison forced by syntax limitations.
-                                       low = p + 1;
-                               else
-                                       return byPeer[p];
-                       }
-                       p = low+((high-low)/2);         //Next probe position.
-               }
-               return null;    
-       }
-}
-
-/**
- *     This class is used to store the main informations about a neighbors regarding
- *     the calculation of the Downloading/Uploading rates. Is the class of items in 
- *     {@link example.bittorrent.BitTorrent#byPeer} and {@link example.bittorrent.BitTorrent#byBandwidth}.
- */
-class Element{
-       /**
-        *      ID of the represented node.
-        */
-       public long ID = Integer.MAX_VALUE;
-       /**
-        *      Index position of the node in the {@link example.bittorrent.BitTorrent#cache} array.
-        */
-       public int peer = -1; 
-       /**
-        *      Number of blocks uploaded to anyone since the beginning.
-        */
-       public int valueUP = 0;
-       /**
-        *      Number of blocks downloaded from anyone since the beginning.
-        */
-       public int valueDOWN = 0; 
-       /**
-        *      Value of either {@link #valueUP} or {@link #valueDOWN} (depending by 
-        *      {@link example.bittorrent.BitTorrent#peerStatus}) 20 seconds before.
-        */
-       public int head20 = 0;
-       /**
-        *      Value of either {@link #valueUP} or {@link #valueDOWN} (depending by 
-        *      {@link example.bittorrent.BitTorrent#peerStatus}) 60 seconds before.
-        */
-       public int head60 = 0; 
-       /**
-        *      <tt>true</tt> if the node is a seeder, <tt>false</tt> otherwise.
-        */
-       public boolean isSeeder = false;
-       /**
-        *      Makes a deep copy of the Element to <tt>destination</tt>
-        *      @param destination Element instance where to make the copy
-        */
-       public void copyTo(Element destination){
-               destination.ID = this.ID;
-               destination.peer = this.peer;
-               destination.valueUP = this.valueUP;
-               destination.valueDOWN = this.valueDOWN;
-               destination.head20 = this.head20;
-               destination.head60 = this.head60;
-       }
-}
-
-/**
- *     This class stores information about the neighbors regarding their status. It is 
- *     the type of the items in the {@link example.bittorrent.BitTorrent#cache}.
- */
-class Neighbor{
-       /**
-        *      Reference to the node in the {@link peersim.core.Network}.
-        */
-       public Node node = null;
-       /**
-        *      -1 means not interested<br/>
-        *      Other values means the last piece number for which the node is interested.
-        */
-       public int interested;
-       /**
-        *      0 means CHOKED<br/>
-        *      1 means UNCHOKED<br/>
-        *      2 means SNUBBED_BY. If this value is set and the node is to be unchocked,
-        *      value 2 has the priority.
-        */
-       public int status;
-       /**
-        *      Last time a message from the node represented has been received.
-        */
-       public long lastSeen = 0; 
-       /**
-        *      Last time a message to the node represented has been sent.
-        */
-       public long lastSent = 0;
-       
-       /**
-        * Sets the last time the neighbor was seen.
-        */
-       public void isAlive(){
-               long now = CommonState.getTime();
-               this.lastSeen = now;
-       }
-       
-       /*
-        * Sets the last time the local peer sent something to the neighbor.
-        */
-       public void justSent(){
-               long now = CommonState.getTime();
-               this.lastSent = now;
-       }
-       
-}
-
-/**
- *     Class type of the queues's items in {@link example.bittorrent.BitTorrent#incomingPieces} 
- *     and {@link example.bittorrent.BitTorrent#requestToServe}.
- */
-class Queue{
-       int maxSize;
-       int head = 0;
-       int tail = 0;
-       int dim = 0;
-       Request queue[];
-       
-       /**
-        *      Public constructor. Creates a queue of size <tt>size</tt>.
-        */
-       public Queue(int size){
-               maxSize = size;
-               queue = new Request[size];
-               for(int i=0; i< size; i++)
-                       queue[i]= new Request();
-       }
-       
-       /**
-        *      Enqueues the request of the block <tt>id</tt> and its <tt>sender</tt>
-        *      @param id the id of the block in the request
-        *      @param sender a reference to the sender of the request
-        *      @return <tt>true</tt> if the request has been correctly added, <tt>false</tt>
-        *      otherwise.
-        */
-       public boolean enqueue(int id, Node sender){
-               if(dim < maxSize){
-                       queue[tail%maxSize].id = id;
-                       queue[tail%maxSize].sender = sender;
-                       tail++;
-                       dim++;
-                       return true;
-               }
-               else return false;
-       }
-       
-       /**
-        *      Returns the {@link Request} in the head of the queue.
-        *      @return the element in the head.<br/>
-        *                      <tt>null</tt> if the queue is empty.
-        */
-       public Request dequeue(){
-               Request value;
-               if(dim > 0){
-                       value = queue[head%maxSize];
-                       head++;
-                       dim--;
-                       return value;
-               }
-               else return null; //empty queue
-       }
-       
-       /**
-        *      Returns the status of the queue.
-        *      @return <tt>true</tt> if the queue is empty, <tt>false</tt>
-        *      otherwise.
-        */
-       public boolean empty(){
-               return (dim == 0);
-       }
-       
-       /**
-        *      Returns <tt>true</tt> if block given as parameter is in.
-        *      @param  value the id of the block to search.
-        *      @return <tt>true</tt> if the block <tt>value</tt> is in the queue, <tt>false</tt>
-        *      otherwise.
-        */
-       public boolean contains(int value){
-               if(empty())
-                       return false;
-               for(int i=head; i<head+dim; i++){
-                       if(queue[i%maxSize].id == value)
-                               return true;
-               }
-               return false;
-       }
-       
-       /**
-        *      Removes a request from the queue.
-        *      @param sender the sender of the request.
-        *      @param value the id of the block requested.
-        *      @return <tt>true</tt> if the request has been correctly removed, <tt>false</tt>
-        *      otherwise.
-        */
-       public boolean remove(Node sender, int value){
-               if(empty())
-                       return false;
-               for(int i=head; i<head+dim; i++){
-                       if(queue[i%maxSize].id == value && queue[i%maxSize].sender == sender){
-                               for(int j=i; j>head; j--){ // Shifts the elements for the removal
-                                       queue[j%maxSize]= queue[(j-1)%maxSize];
-                               }
-                               head++;
-                               dim--;
-                               return true;
-                       }
-               }
-               return false;
-       }
-}
-
-/**
- *     This class represent an enqueued request of a block.
- */
-class Request{
-       /**
-        *      The id of the block.
-        */
-       public int id;
-       /**
-        *      The sender of the request.
-        */
-       public Node sender;
-}
\ No newline at end of file