Index: /trunk/modules/vci_cc_xcache_wrapper_v4/caba/metadata/vci_cc_xcache_wrapper_v4.sd
===================================================================
--- /trunk/modules/vci_cc_xcache_wrapper_v4/caba/metadata/vci_cc_xcache_wrapper_v4.sd	(revision 133)
+++ /trunk/modules/vci_cc_xcache_wrapper_v4/caba/metadata/vci_cc_xcache_wrapper_v4.sd	(revision 134)
@@ -21,10 +21,10 @@
 		Uses('common:mapping_table'),
 		Uses('common:iss2'),
-		Uses('caba:write_buffer'),
+		Uses('caba:multi_write_buffer'),
 		Uses('caba:generic_cache', addr_t = 'uint32_t'),
 		],
 	ports = [
 		Port('caba:vci_initiator', 'p_vci_ini_rw'),
-        Port('caba:vci_initiator', 'p_vci_ini_c'),
+		Port('caba:vci_initiator', 'p_vci_ini_c'),
 		Port('caba:vci_target', 'p_vci_tgt'),
 		Port('caba:bit_in', 'p_irq', parameter.Constant('n_irq')),
@@ -45,16 +45,18 @@
 		parameter.Int('dcache_sets'),
 		parameter.Int('dcache_words'),
+		parameter.Int('ram_width_access'),
+		parameter.Int('wbuf_nwords'),
+		parameter.Int('wbuf_nlines'),
+		parameter.Int('wbuf_timeout'),
 		],
-	   extensions = [
-	'dsx:get_ident='
-        'initiator_rw_index:p_vci_ini_rw:mt,'
-        'initiator_c_index:p_vci_ini_c:mc,'
-        'target_index:p_vci_tgt:mc',
-	'dsx:cpu=wrapper:iss_t',
-	'dsx:addressable=target_index',
-    'dsx:on_segment=mc:add_index:initiator_rw_index',
-	'dsx:mapping_type=processor:proc_id',
-   ],
+	extensions = [
+		'dsx:get_ident='
+		'initiator_rw_index:p_vci_ini_rw:mt,'
+		'initiator_c_index:p_vci_ini_c:mc,'
+		'target_index:p_vci_tgt:mc',
+		'dsx:cpu=wrapper:iss_t',
+		'dsx:addressable=target_index',
+		'dsx:on_segment=mc:add_index:initiator_rw_index',
+		'dsx:mapping_type=processor:proc_id',
+		],
 )
-
-
Index: /trunk/modules/vci_cc_xcache_wrapper_v4/caba/source/include/vci_cc_xcache_wrapper_v4.h
===================================================================
--- /trunk/modules/vci_cc_xcache_wrapper_v4/caba/source/include/vci_cc_xcache_wrapper_v4.h	(revision 133)
+++ /trunk/modules/vci_cc_xcache_wrapper_v4/caba/source/include/vci_cc_xcache_wrapper_v4.h	(revision 134)
@@ -32,6 +32,7 @@
 #include <inttypes.h>
 #include <systemc>
+#include <queue>
 #include "caba_base_module.h"
-#include "write_buffer.h"
+#include "multi_write_buffer.h"
 #include "generic_cache.h"
 #include "vci_initiator.h"
@@ -40,4 +41,80 @@
 #include "static_assert.h"
 
+/*
+ * CC_XCACHE_WRAPPER_SELECT_VICTIM :
+ *   The selection and the update of cache (after a read miss)
+ *   are separated in two step
+ *   Also, the cleanup can be send in parallel at the read miss.
+ *
+ * CC_XCACHE_WRAPPER_FIFO_RSP
+ *   Two simple fifo (each 2x32 depth) receive the cache line from
+ *   RAM. Instead of two buffers (m_icache_words and m_dcache_words)
+ *   
+ * CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+ *   Update cache in "2*cache_words" cycles (read+mask, write)
+ *   
+ * CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+ *   Update cache with only modified data (be != 0)
+ *   
+ * CC_XCACHE_WRAPPER_WBUF_UPDATE_SCHEME
+ *   Write buffer scheme for update step :
+ *     1    - multi_scan
+ *     2    - round_robin_scan
+ *     3    - one_scan
+ *     else - default scheme
+ *
+ * CC_XCACHE_WRAPPER_VCI_CMD_PRIORITY
+ *   Write buffer access is conditionnal with dcache_miss_req and icache_miss_req
+ *     1    - two access authorized
+ *     2    - one access with static priority (dcache prior)
+ *     3    - one access with static priority (icache prior)
+ *     4    - one access with round robin priority
+ * 
+ * CC_XCACHE_WRAPPER_STOP_SIMULATION :
+ *   stop simulation if processor is stall after a long time
+ *   (configurable with "stop_simulation" function)
+ *
+ * CC_XCACHE_WRAPPER_DEBUG :
+ *   Add log to help the debugging
+ *
+ * CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN :
+ *   Number of cycle before to prinf debug message
+ *
+ * CC_XCACHE_WRAPPER_DEBUG_DCACHE_TRANSACTION
+ *   Print transaction between the cpu and the cache
+ */
+
+// implementation
+#ifndef CC_XCACHE_WRAPPER_SELECT_VICTIM
+#define CC_XCACHE_WRAPPER_SELECT_VICTIM             0
+#endif
+#ifndef CC_XCACHE_WRAPPER_FIFO_RSP
+#define CC_XCACHE_WRAPPER_FIFO_RSP                  0
+#endif
+#ifndef CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+#define CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE     1
+#endif
+#ifndef CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+#define CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT 1
+#endif
+#ifndef CC_XCACHE_WRAPPER_WBUF_UPDATE_SCHEME
+#define CC_XCACHE_WRAPPER_WBUF_UPDATE_SCHEME        0
+#endif
+#ifndef CC_XCACHE_WRAPPER_VCI_CMD_PRIORITY
+#define CC_XCACHE_WRAPPER_VCI_CMD_PRIORITY          2
+#endif  
+// debugging
+#ifndef CC_XCACHE_WRAPPER_STOP_SIMULATION
+#define CC_XCACHE_WRAPPER_STOP_SIMULATION           1
+#endif
+#ifndef CC_XCACHE_WRAPPER_DEBUG
+#define CC_XCACHE_WRAPPER_DEBUG                     0
+#endif
+#ifndef CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN
+#define CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN           200000
+#endif
+#ifndef CC_XCACHE_WRAPPER_DEBUG_DCACHE_TRANSACTION
+#define CC_XCACHE_WRAPPER_DEBUG_DCACHE_TRANSACTION  0
+#endif
 
 namespace soclib {
@@ -58,8 +135,11 @@
     typedef uint32_t    	be_t;
     typedef typename vci_param::fast_addr_t vci_addr_t;
+
     enum dcache_fsm_state_e {
         DCACHE_IDLE,
         DCACHE_WRITE_UPDT,
-        DCACHE_WRITE_REQ,
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+        DCACHE_MISS_VICTIM,
+#endif
         DCACHE_MISS_WAIT,
         DCACHE_MISS_UPDT,
@@ -67,4 +147,5 @@
         DCACHE_SC_WAIT,
         DCACHE_INVAL,
+        DCACHE_SYNC,
         DCACHE_ERROR,
         DCACHE_CC_CHECK,
@@ -76,4 +157,7 @@
     enum icache_fsm_state_e {
         ICACHE_IDLE,
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+        ICACHE_MISS_VICTIM,
+#endif
         ICACHE_MISS_WAIT,
         ICACHE_MISS_UPDT,
@@ -94,6 +178,4 @@
         CMD_DATA_WRITE,
         CMD_DATA_SC,
-        CMD_INS_CLEANUP,
-        CMD_DATA_CLEANUP,
     };
 
@@ -106,6 +188,4 @@
         RSP_DATA_WRITE,
         RSP_DATA_SC,
-        RSP_INS_CLEANUP,
-        RSP_DATA_CLEANUP,
     };
 
@@ -122,4 +202,28 @@
     };
 
+    enum cleanup_fsm_state_e {
+        CLEANUP_IDLE,
+        CLEANUP_DCACHE,
+        CLEANUP_ICACHE,
+    };
+
+    enum transaction_type_c_e {
+        // convention with memcache
+        TYPE_DATA_CLEANUP = 0x0,
+        TYPE_INS_CLEANUP  = 0x1
+    };
+
+    enum transaction_type_rw_e {
+        // convention with memcache
+        // b0 : 1 if cached
+        // b1 : 1 if instruction
+        // b2 : 1 if sc
+        TYPE_DATA_UNC     = 0x0,
+        TYPE_DATA_MISS    = 0x1,
+        TYPE_INS_UNC      = 0x2,
+        TYPE_INS_MISS     = 0x3,
+        TYPE_DATA_SC      = 0x4, // sc is data and no cached
+    };
+
 public:
 
@@ -143,8 +247,17 @@
     const size_t        m_dcache_ways;
     const size_t        m_dcache_words;
+    const uint32_t      m_dcache_words_shift;
     const size_t        m_dcache_yzmask;
     const size_t        m_icache_ways;
     const size_t        m_icache_words;
+    const uint32_t      m_icache_words_shift;
     const size_t        m_icache_yzmask;
+    const size_t        m_cache_words; // max between m_dcache_words and m_icache_words
+
+#if CC_XCACHE_WRAPPER_STOP_SIMULATION
+    bool                m_stop_simulation;
+    uint32_t            m_stop_simulation_nb_frz_cycles_max;
+    uint32_t            m_stop_simulation_nb_frz_cycles;
+#endif // CC_XCACHE_WRAPPER_STOP_SIMULATION
 
     // REGISTERS
@@ -154,7 +267,4 @@
     sc_signal<data_t>       r_dcache_wdata_save;
     sc_signal<data_t>       r_dcache_rdata_save;
-    sc_signal<data_64>      r_dcache_ll_data;
-    sc_signal<addr_40>      r_dcache_ll_addr;
-    sc_signal<bool>         r_dcache_ll_valid;
     sc_signal<int>          r_dcache_type_save;
     sc_signal<be_t>         r_dcache_be_save;
@@ -163,8 +273,14 @@
     sc_signal<addr_40>      r_dcache_cleanup_line;
     sc_signal<bool>         r_dcache_miss_req;
+    sc_signal<size_t>       r_dcache_miss_way;
+    sc_signal<size_t>       r_dcache_miss_set;
     sc_signal<bool>         r_dcache_unc_req;
     sc_signal<bool>         r_dcache_sc_req;
-    sc_signal<bool>         r_dcache_write_req;
     sc_signal<bool>         r_dcache_inval_rsp;
+    sc_signal<size_t>       r_dcache_update_addr;
+    sc_signal<data_64>      r_dcache_ll_data;
+    sc_signal<addr_40>      r_dcache_ll_addr;
+    sc_signal<bool>         r_dcache_ll_valid;
+    sc_signal<bool>         r_dcache_previous_unc;
 
     sc_signal<int>          r_icache_fsm;
@@ -172,8 +288,11 @@
     sc_signal<addr_40>      r_icache_addr_save;
     sc_signal<bool>         r_icache_miss_req;
+    sc_signal<size_t>       r_icache_miss_way;
+    sc_signal<size_t>       r_icache_miss_set;
     sc_signal<bool>         r_icache_unc_req;
     sc_signal<bool>         r_icache_cleanup_req;
     sc_signal<addr_40>      r_icache_cleanup_line;
     sc_signal<bool>         r_icache_inval_rsp;
+    sc_signal<size_t>       r_icache_update_addr;
 
     sc_signal<int>          r_vci_cmd_fsm;
@@ -181,4 +300,5 @@
     sc_signal<size_t>       r_vci_cmd_max;       
     sc_signal<size_t>       r_vci_cmd_cpt;       
+    sc_signal<bool>         r_vci_cmd_dcache_prior;
       
     sc_signal<int>          r_vci_rsp_fsm;
@@ -186,11 +306,22 @@
     sc_signal<bool>         r_vci_rsp_data_error;    
     sc_signal<size_t>       r_vci_rsp_cpt;  
-
-    data_t                  *r_icache_miss_buf;    
-    data_t                  *r_dcache_miss_buf;    
+    sc_signal<bool>         r_vci_rsp_ack;
+
+#if CC_XCACHE_WRAPPER_FIFO_RSP
+    std::queue<data_t>      r_icache_miss_buf;
+    std::queue<data_t>      r_dcache_miss_buf;
+#else
+    bool                   *r_icache_miss_val;    //[m_icache_words]
+    data_t                 *r_icache_miss_buf;    //[m_icache_words]
+    bool                   *r_dcache_miss_val;    //[m_dcache_words]
+    data_t                 *r_dcache_miss_buf;    //[m_dcache_words]
+#endif
     sc_signal<bool>         r_icache_buf_unc_valid;
 
-    data_t                  *r_tgt_buf;
-    be_t                    *r_tgt_be;
+    data_t                 *r_tgt_buf;            //[m_cache_words]
+    be_t                   *r_tgt_be;             //[m_cache_words]
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+    sc_signal<uint32_t>     r_cache_word;
+#endif
 
     sc_signal<int>          r_vci_tgt_fsm;
@@ -199,9 +330,9 @@
     sc_signal<bool>         r_tgt_update;
     sc_signal<bool>         r_tgt_update_data;
-    sc_signal<bool>         r_tgt_brdcast;
+  //sc_signal<bool>         r_tgt_brdcast;
     sc_signal<size_t>       r_tgt_srcid;
     sc_signal<size_t>       r_tgt_pktid;
     sc_signal<size_t>       r_tgt_trdid;
-    sc_signal<size_t>       r_tgt_plen;
+  //sc_signal<size_t>       r_tgt_plen;
     sc_signal<bool>         r_tgt_icache_req;
     sc_signal<bool>         r_tgt_dcache_req;
@@ -209,47 +340,59 @@
     sc_signal<bool>         r_tgt_dcache_rsp;
 
-    WriteBuffer<addr_40>        r_wbuf;
+    sc_signal<int>          r_cleanup_fsm;		// controls initiator port of the coherence network
+
+    MultiWriteBuffer<addr_40>   r_wbuf;
     GenericCache<vci_addr_t>    r_icache;
     GenericCache<vci_addr_t>    r_dcache;
 
+#if CC_XCACHE_WRAPPER_DEBUG_DCACHE_TRANSACTION
+    std::ofstream               log_dcache_transaction_file;
+#endif
+
     // Activity counters
-    uint32_t m_cpt_dcache_data_read;        // DCACHE DATA READ
-    uint32_t m_cpt_dcache_data_write;       // DCACHE DATA WRITE
-    uint32_t m_cpt_dcache_dir_read;         // DCACHE DIR READ
-    uint32_t m_cpt_dcache_dir_write;        // DCACHE DIR WRITE
-
-    uint32_t m_cpt_icache_data_read;        // ICACHE DATA READ
-    uint32_t m_cpt_icache_data_write;       // ICACHE DATA WRITE
-    uint32_t m_cpt_icache_dir_read;         // ICACHE DIR READ
-    uint32_t m_cpt_icache_dir_write;        // ICACHE DIR WRITE
-
-    uint32_t m_cpt_cc_update;               // number of coherence update packets 
-    uint32_t m_cpt_cc_inval;                // number of coherence inval packets
-
-    uint32_t m_cpt_frz_cycles;	            // number of cycles where the cpu is frozen
-    uint32_t m_cpt_total_cycles;	    // total number of cycles 
-
-    uint32_t m_cpt_read;                    // total number of read instructions
-    uint32_t m_cpt_write;                   // total number of write instructions
-    uint32_t m_cpt_data_miss;               // number of read miss
-    uint32_t m_cpt_ins_miss;                // number of instruction miss
-    uint32_t m_cpt_unc_read;                // number of read uncached
-    uint32_t m_cpt_write_cached;            // number of cached write
-
-    uint32_t m_cost_write_frz;              // number of frozen cycles related to write buffer         
-    uint32_t m_cost_data_miss_frz;          // number of frozen cycles related to data miss
-    uint32_t m_cost_unc_read_frz;           // number of frozen cycles related to uncached read
-    uint32_t m_cost_ins_miss_frz;           // number of frozen cycles related to ins miss
-
-    uint32_t m_cpt_imiss_transaction;       // number of VCI instruction miss transactions
-    uint32_t m_cpt_dmiss_transaction;       // number of VCI data miss transactions
-    uint32_t m_cpt_unc_transaction;         // number of VCI uncached read transactions
-    uint32_t m_cpt_write_transaction;       // number of VCI write transactions
-
-    uint32_t m_cost_imiss_transaction;      // cumulated duration for VCI IMISS transactions
-    uint32_t m_cost_dmiss_transaction;      // cumulated duration for VCI DMISS transactions
-    uint32_t m_cost_unc_transaction;        // cumulated duration for VCI UNC transactions
-    uint32_t m_cost_write_transaction;      // cumulated duration for VCI WRITE transactions
-    uint32_t m_length_write_transaction;    // cumulated length for VCI WRITE transactions
+    uint32_t m_cpt_dcache_data_read;             // * DCACHE DATA READ
+    uint32_t m_cpt_dcache_data_write;            // * DCACHE DATA WRITE
+    uint32_t m_cpt_dcache_dir_read;              // * DCACHE DIR READ
+    uint32_t m_cpt_dcache_dir_write;             // * DCACHE DIR WRITE
+                                                 
+    uint32_t m_cpt_icache_data_read;             // * ICACHE DATA READ
+    uint32_t m_cpt_icache_data_write;            // * ICACHE DATA WRITE
+    uint32_t m_cpt_icache_dir_read;              // * ICACHE DIR READ
+    uint32_t m_cpt_icache_dir_write;             // * ICACHE DIR WRITE
+
+    uint32_t m_cpt_cc_update_icache;             // number of coherence update packets (for icache)
+    uint32_t m_cpt_cc_update_dcache;             // number of coherence update packets (for dcache)
+    uint32_t m_cpt_cc_inval_broadcast;           // number of coherence inval packets
+    uint32_t m_cpt_cc_inval_icache;              // number of coherence inval packets
+    uint32_t m_cpt_cc_inval_dcache;              // number of coherence inval packets
+    uint32_t m_cpt_cc_update_icache_word_useful; // number of valid word in coherence update packets
+    uint32_t m_cpt_cc_update_dcache_word_useful; // number of valid word in coherence update packets
+
+    uint32_t m_cpt_frz_cycles;	                 // * number of cycles where the cpu is frozen
+    uint32_t m_cpt_total_cycles;	             // total number of cycles 
+
+    uint32_t m_cpt_data_read;                    //   number of data read
+    uint32_t m_cpt_data_read_miss;               //   number of data read miss
+    uint32_t m_cpt_data_read_uncached;           //   number of data read uncached
+    uint32_t m_cpt_data_write;                   //   number of data write
+    uint32_t m_cpt_data_write_miss;              //   number of data write miss
+    uint32_t m_cpt_data_write_uncached;          //   number of data write uncached
+    uint32_t m_cpt_ins_miss;                     // * number of instruction miss
+
+    uint32_t m_cost_write_frz;                   // * number of frozen cycles related to write buffer         
+    uint32_t m_cost_data_miss_frz;               // * number of frozen cycles related to data miss
+    uint32_t m_cost_unc_read_frz;                // * number of frozen cycles related to uncached read
+    uint32_t m_cost_ins_miss_frz;                // * number of frozen cycles related to ins miss
+
+    uint32_t m_cpt_imiss_transaction;            // * number of VCI instruction miss transactions
+    uint32_t m_cpt_dmiss_transaction;            // * number of VCI data miss transactions
+    uint32_t m_cpt_unc_transaction;              // * number of VCI uncached read transactions
+    uint32_t m_cpt_data_write_transaction;       // * number of VCI write transactions
+
+    uint32_t m_cost_imiss_transaction;           // * cumulated duration for VCI IMISS transactions
+    uint32_t m_cost_dmiss_transaction;           // * cumulated duration for VCI DMISS transactions
+    uint32_t m_cost_unc_transaction;             // * cumulated duration for VCI UNC transactions
+    uint32_t m_cost_write_transaction;           // * cumulated duration for VCI WRITE transactions
+    uint32_t m_length_write_transaction;         // * cumulated length for VCI WRITE transactions
 
 protected:
@@ -271,5 +414,9 @@
                        size_t dcache_ways,
                        size_t dcache_sets,
-                       size_t dcache_words );
+                       size_t dcache_words,
+                       size_t wbuf_nwords,
+                       size_t wbuf_nlines,
+                       size_t wbuf_timeout
+                         );
 
     ~VciCcXCacheWrapperV4();
@@ -278,4 +425,8 @@
     void print_cpi();
     void print_stats();
+
+// #if CC_XCACHE_WRAPPER_STOP_SIMULATION
+    void stop_simulation (uint32_t);
+// #endif // CC_XCACHE_WRAPPER_STOP_SIMULATION
 
 private:
@@ -300,5 +451,2 @@
 
 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
-
-
-
Index: /trunk/modules/vci_cc_xcache_wrapper_v4/caba/source/src/vci_cc_xcache_wrapper_v4.cpp
===================================================================
--- /trunk/modules/vci_cc_xcache_wrapper_v4/caba/source/src/vci_cc_xcache_wrapper_v4.cpp	(revision 133)
+++ /trunk/modules/vci_cc_xcache_wrapper_v4/caba/source/src/vci_cc_xcache_wrapper_v4.cpp	(revision 134)
@@ -56,17 +56,60 @@
 
 #include <cassert>
+#include <iomanip>
 #include "arithmetics.h"
 #include "../include/vci_cc_xcache_wrapper_v4.h"
 
-//#define DEBUG_CC_XCACHE_WRAPPER 1
+#if CC_XCACHE_WRAPPER_DEBUG
+# define PRINTF(msg...) do { if (m_cpt_total_cycles>=CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN) printf(msg); } while (0); 
+#else
+# define PRINTF(msg...)
+#endif
+
+# define ASSERT(cond,msg) assert ((cond) and msg);
+
+#if CC_XCACHE_WRAPPER_FIFO_RSP
+# define CACHE_MISS_BUF_ALLOC
+# define CACHE_MISS_BUF_DEALLOC
+# define CACHE_MISS_BUF_RESET(c)        while (r_##c##cache_miss_buf.size()>0) {r_##c##cache_miss_buf.pop();}
+# define CACHE_MISS_BUF_REQ_INIT(c)
+# define CACHE_MISS_BUF_RSP_VAL(c,n)    (r_##c##cache_miss_buf.size()>0)
+# define CACHE_MISS_BUF_RSP_ACK(c)      (r_##c##cache_miss_buf.size()<2)
+# define CACHE_MISS_BUF_RSP_DATA(c,n)   r_##c##cache_miss_buf.front()
+# define CACHE_MISS_BUF_RSP_POP(c)      do { r_##c##cache_miss_buf.pop();} while (0)
+# define CACHE_MISS_BUF_RSP_PUSH(c,n,d) do { r_##c##cache_miss_buf.push(d);} while (0)
+# define CACHE_MISS_BUF_RSP_PRINT(c)    do { PRINTF("    * cache_miss_buf - size : %d\n",r_##c##cache_miss_buf.size());} while (0)
+#else
+# define CACHE_MISS_BUF_ALLOC           do { \
+                                        r_icache_miss_val = new bool  [m_icache_words]; \
+                                        r_icache_miss_buf = new data_t[m_icache_words]; \
+                                        r_dcache_miss_val = new bool  [m_dcache_words]; \
+                                        r_dcache_miss_buf = new data_t[m_dcache_words]; \
+                                        } while (0)
+# define CACHE_MISS_BUF_DEALLOC         do { \
+                                        delete [] r_icache_miss_val; \
+                                        delete [] r_icache_miss_buf; \
+                                        delete [] r_dcache_miss_val; \
+                                        delete [] r_dcache_miss_buf; \
+                                        } while (0)
+# define CACHE_MISS_BUF_RESET(c)
+# define CACHE_MISS_BUF_REQ_INIT(c)     do {for (uint32_t i=0; i<m_##c##cache_words;++i) r_##c##cache_miss_val[i] = false;} while (0)
+# define CACHE_MISS_BUF_RSP_VAL(c,n)    r_##c##cache_miss_val[n]
+# define CACHE_MISS_BUF_RSP_ACK(c)      true
+# define CACHE_MISS_BUF_RSP_DATA(c,n)   r_##c##cache_miss_buf[n]
+# define CACHE_MISS_BUF_RSP_POP(c)
+# define CACHE_MISS_BUF_RSP_PUSH(c,n,d) do {r_##c##cache_miss_val[n] = true; r_##c##cache_miss_buf[n] = d;} while (0)
+# define CACHE_MISS_BUF_RSP_PRINT(c)    do {for (uint32_t i=0; i<m_##c##cache_words;++i) PRINTF("%d %x |",r_##c##cache_miss_val[i],r_##c##cache_miss_buf[i]); PRINTF("\n");} while (0)
+#endif
 
 namespace soclib { 
 namespace caba {
-
     namespace {
+
         const char *dcache_fsm_state_str[] = {
             "DCACHE_IDLE",
             "DCACHE_WRITE_UPDT",
-            "DCACHE_WRITE_REQ",
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+            "DCACHE_MISS_VICTIM",
+#endif
             "DCACHE_MISS_WAIT",
             "DCACHE_MISS_UPDT",
@@ -74,4 +117,5 @@
             "DCACHE_SC_WAIT",
             "DCACHE_INVAL",
+            "DCACHE_SYNC",
             "DCACHE_ERROR",
             "DCACHE_CC_CHECK",
@@ -82,4 +126,7 @@
         const char *icache_fsm_state_str[] = {
             "ICACHE_IDLE",
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+            "ICACHE_MISS_VICTIM",
+#endif
             "ICACHE_MISS_WAIT",
             "ICACHE_MISS_UPDT",
@@ -99,6 +146,4 @@
             "CMD_DATA_WRITE",
             "CMD_DATA_SC",
-            "CMD_INS_CLEANUP",
-            "CMD_DATA_CLEANUP",
         };
         const char *rsp_fsm_state_str[] = {
@@ -110,6 +155,4 @@
             "RSP_DATA_WRITE",
             "RSP_DATA_SC",
-            "RSP_INS_CLEANUP",
-            "RSP_DATA_CLEANUP",
         };
         const char *tgt_fsm_state_str[] = {
@@ -123,4 +166,10 @@
             "TGT_RSP_ICACHE",
             "TGT_RSP_DCACHE",
+        };
+
+        const char *cleanup_fsm_state_str[] = {
+            "CLEANUP_IDLE",
+            "CLEANUP_DCACHE",
+            "CLEANUP_ICACHE",
         };
     }
@@ -145,13 +194,17 @@
             size_t dcache_ways,
             size_t dcache_sets,
-            size_t dcache_words )
+            size_t dcache_words,
+            size_t wbuf_nwords,
+            size_t wbuf_nlines,
+            size_t wbuf_timeout
+                                     )
         : 
             soclib::caba::BaseModule(name),
 
-            p_clk("clk"),
-            p_resetn("resetn"),
+            p_clk       ("clk"),
+            p_resetn    ("resetn"),
             p_vci_ini_rw("vci_ini_rw"),
-            p_vci_ini_c("vci_ini_c"),
-            p_vci_tgt("vci_tgt"),
+            p_vci_ini_c ("vci_ini_c"),
+            p_vci_tgt   ("vci_tgt"),
 
             m_cacheability_table(mtp.getCacheabilityTable<vci_addr_t>()),
@@ -163,8 +216,11 @@
             m_dcache_ways(dcache_ways),
             m_dcache_words(dcache_words),
-            m_dcache_yzmask((~0)<<(uint32_log2(dcache_words) + 2)),
+            m_dcache_words_shift(uint32_log2(dcache_words)+2),
+            m_dcache_yzmask((~0)<<m_dcache_words_shift),
             m_icache_ways(icache_ways),
             m_icache_words(icache_words),
-            m_icache_yzmask((~0)<<(uint32_log2(icache_words) + 2)),
+            m_icache_words_shift(uint32_log2(icache_words)+2),
+            m_icache_yzmask((~0)<<m_icache_words_shift),
+            m_cache_words((dcache_words)?dcache_words:icache_words),
 
             r_dcache_fsm("r_dcache_fsm"),
@@ -173,7 +229,4 @@
             r_dcache_wdata_save("r_dcache_wdata_save"),
             r_dcache_rdata_save("r_dcache_rdata_save"),
-            r_dcache_ll_data("r_dcache_ll_data"),
-            r_dcache_ll_addr("r_dcache_ll_addr"),
-            r_dcache_ll_valid("r_dcache_ll_valid"),
             r_dcache_type_save("r_dcache_type_save"),
             r_dcache_be_save("r_dcache_be_save"),
@@ -182,6 +235,14 @@
             r_dcache_cleanup_line("r_dcache_cleanup_line"),
             r_dcache_miss_req("r_dcache_miss_req"),
+            r_dcache_miss_way("r_dcache_miss_way"),
+            r_dcache_miss_set("r_dcache_miss_set"),
             r_dcache_unc_req("r_dcache_unc_req"),
-            r_dcache_write_req("r_dcache_write_req"),
+            r_dcache_sc_req("r_dcache_sc_req"),
+            r_dcache_inval_rsp("r_dcache_inval_rsp"),
+            r_dcache_update_addr("r_dcache_update_addr"),
+            r_dcache_ll_data("r_dcache_ll_data"),
+            r_dcache_ll_addr("r_dcache_ll_addr"),
+            r_dcache_ll_valid("r_dcache_ll_valid"),
+            r_dcache_previous_unc("r_dcache_previous_unc"),
 
             r_icache_fsm("r_icache_fsm"),
@@ -189,6 +250,11 @@
             r_icache_addr_save("r_icache_addr_save"),
             r_icache_miss_req("r_icache_miss_req"),
+            r_icache_miss_way("r_icache_miss_way"),
+            r_icache_miss_set("r_icache_miss_set"),
+            r_icache_unc_req("r_icache_unc_req"),
             r_icache_cleanup_req("r_icache_cleanup_req"),
             r_icache_cleanup_line("r_icache_cleanup_line"),
+            r_icache_inval_rsp("r_icache_inval_rsp"),
+            r_icache_update_addr("r_icache_update_addr"),
 
             r_vci_cmd_fsm("r_vci_cmd_fsm"),
@@ -196,4 +262,5 @@
             r_vci_cmd_max("r_vci_cmd_max"),
             r_vci_cmd_cpt("r_vci_cmd_cpt"),
+            r_vci_cmd_dcache_prior("r_vci_cmd_dcache_prior"),
 
             r_vci_rsp_fsm("r_vci_rsp_fsm"),
@@ -201,6 +268,11 @@
             r_vci_rsp_data_error("r_vci_rsp_data_error"),
             r_vci_rsp_cpt("r_vci_rsp_cpt"),
+            r_vci_rsp_ack("r_vci_rsp_ack"),
 
             r_icache_buf_unc_valid("r_icache_buf_unc_valid"),
+
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+            r_cache_word("r_cache_word"),
+#endif
 
             r_vci_tgt_fsm("r_vci_tgt_fsm"),
@@ -208,19 +280,32 @@
             r_tgt_word("r_tgt_word"),
             r_tgt_update("r_tgt_update"),
+            r_tgt_update_data("r_tgt_update_data"),
+         // r_tgt_brdcast("r_tgt_brdcast"),
             r_tgt_srcid("r_tgt_srcid"),
             r_tgt_pktid("r_tgt_pktid"),
             r_tgt_trdid("r_tgt_trdid"),
+         // r_tgt_plen("r_tgt_plen"),
             r_tgt_icache_req("r_tgt_icache_req"),
             r_tgt_dcache_req("r_tgt_dcache_req"),
-
-            r_wbuf("r_wbuf", dcache_words ),
+            r_tgt_icache_rsp("r_tgt_icache_rsp"),
+            r_tgt_dcache_rsp("r_tgt_dcache_rsp"),
+
+            r_cleanup_fsm("r_cleanup_fsm"),
+
+            r_wbuf("r_wbuf", wbuf_nwords, wbuf_nlines, wbuf_timeout, dcache_words),
             r_icache("icache", icache_ways, icache_sets, icache_words),
             r_dcache("dcache", dcache_ways, dcache_sets, dcache_words)
-
             {
-                r_icache_miss_buf = new data_t[icache_words];
-                r_dcache_miss_buf = new data_t[dcache_words];
-                r_tgt_buf         = new data_t[dcache_words];
-                r_tgt_be          = new be_t[dcache_words];
+                // Size of word is 32 bits
+                ASSERT( (icache_words*vci_param::B) < (1<<vci_param::K),
+                        "I need more PLEN bits");
+
+                ASSERT( (vci_param::T > 2) and ((1<<(vci_param::T-1)) >= wbuf_nlines),
+                        "I need more TRDID bits");
+
+                CACHE_MISS_BUF_ALLOC;
+
+                r_tgt_buf = new data_t[m_cache_words];
+                r_tgt_be  = new be_t  [m_cache_words];
 
                 SC_METHOD(transition);
@@ -234,12 +319,24 @@
 
                 typename iss_t::CacheInfo cache_info;
-                cache_info.has_mmu = false;
+                cache_info.has_mmu          = false;
                 cache_info.icache_line_size = icache_words*sizeof(data_t);
-                cache_info.icache_assoc = icache_ways;
-                cache_info.icache_n_lines = icache_sets;
+                cache_info.icache_assoc     = icache_ways;
+                cache_info.icache_n_lines   = icache_sets;
                 cache_info.dcache_line_size = dcache_words*sizeof(data_t);
-                cache_info.dcache_assoc = dcache_ways;
-                cache_info.dcache_n_lines = dcache_sets;
+                cache_info.dcache_assoc     = dcache_ways;
+                cache_info.dcache_n_lines   = dcache_sets;
                 m_iss.setCacheInfo(cache_info);
+
+#if CC_XCACHE_WRAPPER_STOP_SIMULATION
+                m_stop_simulation               = false;
+                m_stop_simulation_nb_frz_cycles = 0;
+#endif // CC_XCACHE_WRAPPER_STOP_SIMULATION
+
+#if CC_XCACHE_WRAPPER_DEBUG_DCACHE_TRANSACTION
+                std::ostringstream filename("");
+                filename << "Instruction_flow_" << proc_id << ".log";
+                
+                log_dcache_transaction_file.open(filename.str().c_str() ,std::ios::out | std::ios::trunc);
+#endif
             } // end constructor
 
@@ -248,8 +345,12 @@
     ///////////////////////////////////
     {
-        delete [] r_icache_miss_buf;
-        delete [] r_dcache_miss_buf;
-        delete [] r_tgt_be;
+#if CC_XCACHE_WRAPPER_DEBUG_DCACHE_TRANSACTION
+        log_dcache_transaction_file.close();
+#endif
+
         delete [] r_tgt_buf;
+        delete [] r_tgt_be ;
+
+        CACHE_MISS_BUF_DEALLOC;
     }
 
@@ -266,62 +367,111 @@
     {
         float run_cycles = (float)(m_cpt_total_cycles - m_cpt_frz_cycles);
+
+        uint32_t m_cpt_data_read_cached  = m_cpt_data_read-m_cpt_data_read_uncached;
+        uint32_t m_cpt_data_write_cached = m_cpt_data_write-m_cpt_data_write_uncached;
         std::cout << "------------------------------------" << std:: dec << std::endl;
         std::cout << "CPU " << m_srcid_rw << " / Time = " << m_cpt_total_cycles << std::endl;
-        std::cout << "- CPI                = " << (float)m_cpt_total_cycles/run_cycles << std::endl ;
-        std::cout << "- READ RATE          = " << (float)m_cpt_read/run_cycles << std::endl ;
-        std::cout << "- WRITE RATE         = " << (float)m_cpt_write/run_cycles << std::endl;
-        std::cout << "- UNCACHED READ RATE = " << (float)m_cpt_unc_read/m_cpt_read << std::endl ;
-        std::cout << "- CACHED WRITE RATE  = " << (float)m_cpt_write_cached/m_cpt_write << std::endl ;
-        std::cout << "- IMISS_RATE         = " << (float)m_cpt_ins_miss/run_cycles << std::endl;
-        std::cout << "- DMISS RATE         = " << (float)m_cpt_data_miss/(m_cpt_read-m_cpt_unc_read) << std::endl ;
-        std::cout << "- INS MISS COST      = " << (float)m_cost_ins_miss_frz/m_cpt_ins_miss << std::endl;
-        std::cout << "- IMISS TRANSACTION  = " << (float)m_cost_imiss_transaction/m_cpt_imiss_transaction << std::endl;
-        std::cout << "- DMISS COST         = " << (float)m_cost_data_miss_frz/m_cpt_data_miss << std::endl;
-        std::cout << "- DMISS TRANSACTION  = " << (float)m_cost_dmiss_transaction/m_cpt_dmiss_transaction << std::endl;
-        std::cout << "- UNC COST           = " << (float)m_cost_unc_read_frz/m_cpt_unc_read << std::endl;
-        std::cout << "- UNC TRANSACTION    = " << (float)m_cost_unc_transaction/m_cpt_unc_transaction << std::endl;
-        std::cout << "- WRITE COST         = " << (float)m_cost_write_frz/m_cpt_write << std::endl;
-        std::cout << "- WRITE TRANSACTION  = " << (float)m_cost_write_transaction/m_cpt_write_transaction << std::endl;
-        std::cout << "- WRITE LENGTH       = " << (float)m_length_write_transaction/m_cpt_write_transaction << std::endl;
+        std::cout << "- CPI                            : " << (float)m_cpt_total_cycles/run_cycles << std::endl ;
+        std::cout << "- IPC                            : " << (float)run_cycles/m_cpt_total_cycles << std::endl ;
+        std::cout << "- DATA READ *                    : " << m_cpt_data_read << std::endl ;
+        std::cout << "  + Uncached                     : " << m_cpt_data_read_uncached << " (" << (float)m_cpt_data_read_uncached*100.0/(float)m_cpt_data_read << "%)" << std::endl ;
+        std::cout << "  + Cached and miss              : " << m_cpt_data_read_miss << " (" << (float)m_cpt_data_read_miss*100.0/(float)m_cpt_data_read_cached << "%)" << std::endl;
+        std::cout << "- DATA WRITE *                   : " << m_cpt_data_write << std::endl ;
+        std::cout << "  + Uncached                     : " << m_cpt_data_write_uncached << " (" << (float)m_cpt_data_write_uncached*100.0/(float)m_cpt_data_write << "%)" << std::endl ;
+        std::cout << "  + Cached and miss              : " << m_cpt_data_write_miss << " (" << (float)m_cpt_data_write_miss*100.0/(float)m_cpt_data_write_cached << "%)" << std::endl;
+        // std::cout << "- WRITE RATE                     : " << (float)m_cpt_data_write/run_cycles << std::endl;
+        // std::cout << "- UNCACHED READ RATE             : " << (float)m_cpt_data_read_uncached/m_cpt_data_read << std::endl ;
+        // std::cout << "- CACHED WRITE RATE              : " << (float)m_cpt_data_write_cached/m_cpt_data_write << std::endl ;
+        // std::cout << "- IMISS_RATE                     : " << (float)m_cpt_ins_miss/run_cycles << std::endl;
+        // std::cout << "- DMISS RATE                     : " << (float)m_cpt_data_miss/(m_cpt_data_read-m_cpt_data_read_uncached) << std::endl ;
+        // std::cout << "- INS MISS COST                  : " << (float)m_cost_ins_miss_frz/m_cpt_ins_miss << std::endl;
+        // std::cout << "- IMISS TRANSACTION              : " << (float)m_cost_imiss_transaction/m_cpt_imiss_transaction << std::endl;
+        // std::cout << "- DMISS COST                     : " << (float)m_cost_data_miss_frz/m_cpt_data_miss << std::endl;
+        // std::cout << "- DMISS TRANSACTION              : " << (float)m_cost_dmiss_transaction/m_cpt_dmiss_transaction << std::endl;
+        // std::cout << "- UNC COST                       : " << (float)m_cost_unc_read_frz/m_cpt_data_read_uncached << std::endl;
+        // std::cout << "- UNC TRANSACTION                : " << (float)m_cost_unc_transaction/m_cpt_unc_transaction << std::endl;
+        // std::cout << "- WRITE COST                     : " << (float)m_cost_write_frz/m_cpt_data_write << std::endl;
+        // std::cout << "- WRITE TRANSACTION              : " << (float)m_cost_write_transaction/m_cpt_data_write_transaction << std::endl;
+        // std::cout << "- WRITE LENGTH                   : " << (float)m_length_write_transaction/m_cpt_data_write_transaction << std::endl;
+
+        std::cout << "- CC_UPDATE_ICACHE               : " << m_cpt_cc_update_icache  << std::endl;
+        std::cout << "  + AVERAGE WORD USEFUL          : " << (float)m_cpt_cc_update_icache_word_useful/(float)m_cpt_cc_update_icache << " on " << m_icache_words << " words" << std::endl; 
+        std::cout << "- CC_UPDATE_DCACHE               : " << m_cpt_cc_update_dcache  << std::endl;
+        std::cout << "  + AVERAGE WORD USEFUL          : " << (float)m_cpt_cc_update_dcache_word_useful/(float)m_cpt_cc_update_dcache << " on " << m_dcache_words << " words" << std::endl; 
+        uint32_t m_cpt_cc_inval = m_cpt_cc_inval_broadcast+m_cpt_cc_inval_icache+m_cpt_cc_inval_dcache;
+        std::cout << "- CC_INVALID                     : " << m_cpt_cc_inval << std::endl;
+        std::cout << "  + ICACHE Only                  : " << (float)m_cpt_cc_inval_icache   *100.0/(float)m_cpt_cc_inval << "%" << std::endl;
+        std::cout << "  + DCACHE Only                  : " << (float)m_cpt_cc_inval_dcache   *100.0/(float)m_cpt_cc_inval << "%" << std::endl;
+        std::cout << "  + BROADCAST                    : " << (float)m_cpt_cc_inval_broadcast*100.0/(float)m_cpt_cc_inval << "%" << std::endl;
+        std::cout << "* : accepted or not by the cache" << std::endl ;
+
+        r_wbuf.printStatistics();
     }
+
     ////////////////////////////////////
     tmpl(void)::print_trace(size_t mode)
     ////////////////////////////////////
     {
+        // b0 : write buffer print trace
+        // b1 : write buffer verbose
+        // b2 : dcache print trace
+        // b3 : icache print trace
+
         typename iss_t::InstructionRequest  ireq;
         typename iss_t::DataRequest         dreq;
+
         m_iss.getRequests( ireq, dreq );
-
-        std::cout << std::dec << "CC_XCACHE_WRAPPER " << name() << std::endl;
-        std::cout << " proc state  : PC = " << std::hex << ireq.addr << " / AD = " << dreq.addr 
-                  << std::dec << " / V = " << dreq.valid << " / TYPE = " << dreq.type << std::endl;
-        std::cout << " cache state : " << icache_fsm_state_str[r_icache_fsm] << " / "
-                                       << dcache_fsm_state_str[r_dcache_fsm] << " / "
-                                       << cmd_fsm_state_str[r_vci_cmd_fsm] << " / "
-                                       << rsp_fsm_state_str[r_vci_rsp_fsm] << " / "
-                                       << tgt_fsm_state_str[r_vci_tgt_fsm] << std::endl;
-        if( r_vci_tgt_fsm != TGT_IDLE ) 
-        {
-            std::cout << "    ... coherence request address = " << std::hex << r_tgt_addr.read() << std::endl;
-        }
+        std::cout << std::dec << "Proc \"" << name() << "\"" << std::endl;
+        std::cout << ireq << std::endl;
+        std::cout << dreq << std::endl;
+        std::cout << "  " << dcache_fsm_state_str[r_dcache_fsm]
+                  << "  " << icache_fsm_state_str[r_icache_fsm]
+                  << "  " << cmd_fsm_state_str[r_vci_cmd_fsm]
+                  << "  " << rsp_fsm_state_str[r_vci_rsp_fsm]
+                  << "  " << tgt_fsm_state_str[r_vci_tgt_fsm]
+                  << "  " << cleanup_fsm_state_str[r_cleanup_fsm] << std::endl;
+
         if(mode & 0x1)
         {
-            r_wbuf.printTrace();
+            r_wbuf.printTrace((mode>>1)&1);
         }
+        if(mode & 0x4)
+        {
+            std::cout << "  Data cache" << std::endl;
+            r_dcache.printTrace();
+        }
+        if(mode & 0x8)
+        {
+            std::cout << "  Instruction cache" << std::endl;
+            r_icache.printTrace();
+        }
+
+        // if(mode & 0x10)
+        // {
+        //     std::cout << "  Icache miss buffer : ";
+        //     CACHE_MISS_BUF_RSP_PRINT(i);
+        //     std::cout << std::endl;
+
+        //     std::cout << "  Dcache miss buffer : ";
+        //     CACHE_MISS_BUF_RSP_PRINT(d);
+        //     std::cout << std::endl;
+        // }
     }
+
     //////////////////////////
     tmpl(void)::transition()
     //////////////////////////
     {
-        if ( ! p_resetn.read() ) {
+        if ( not p_resetn.read() ) {
 
             m_iss.reset();
 
             // FSM states
-            r_dcache_fsm = DCACHE_IDLE;
-            r_icache_fsm = ICACHE_IDLE;
+            r_dcache_fsm  = DCACHE_IDLE;
+            r_icache_fsm  = ICACHE_IDLE;
             r_vci_cmd_fsm = CMD_IDLE;
             r_vci_rsp_fsm = RSP_IDLE;
             r_vci_tgt_fsm = TGT_IDLE;
+            r_cleanup_fsm = CLEANUP_IDLE;
 
             // write buffer & caches
@@ -337,10 +487,17 @@
             r_dcache_unc_req     = false;
             r_dcache_sc_req      = false;
-            r_dcache_write_req   = false;
             r_dcache_cleanup_req = false;
+            r_dcache_previous_unc= false;
 
             // synchronisation flip-flops from TGT FSM to ICACHE & DCACHE FSMs
             r_tgt_icache_req     = false;
             r_tgt_dcache_req     = false;
+            r_tgt_icache_rsp     = false;
+            r_tgt_dcache_rsp     = false;
+
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+            r_cache_word         = 0;
+#endif
+
 
             // internal messages in DCACHE et ICACHE FSMs
@@ -351,29 +508,42 @@
             r_dcache_ll_valid      = false;
             r_icache_buf_unc_valid = false;
+
+            r_vci_cmd_dcache_prior = false;
+
             r_vci_rsp_data_error   = false;
             r_vci_rsp_ins_error    = false;
+
+            CACHE_MISS_BUF_RESET(i);
+            CACHE_MISS_BUF_RESET(d);
 
             // activity counters
             m_cpt_dcache_data_read  = 0;
             m_cpt_dcache_data_write = 0;
-            m_cpt_dcache_dir_read  = 0;
-            m_cpt_dcache_dir_write = 0;
+            m_cpt_dcache_dir_read   = 0;
+            m_cpt_dcache_dir_write  = 0;
             m_cpt_icache_data_read  = 0;
             m_cpt_icache_data_write = 0;
-            m_cpt_icache_dir_read  = 0;
-            m_cpt_icache_dir_write = 0;
-
-            m_cpt_cc_update = 0;
-            m_cpt_cc_inval = 0;
-
-            m_cpt_frz_cycles = 0;
+            m_cpt_icache_dir_read   = 0;
+            m_cpt_icache_dir_write  = 0;
+
+            m_cpt_cc_update_icache             = 0;
+            m_cpt_cc_update_dcache             = 0;
+            m_cpt_cc_inval_broadcast           = 0;
+            m_cpt_cc_inval_icache              = 0;
+            m_cpt_cc_inval_dcache              = 0;
+            m_cpt_cc_update_icache_word_useful = 0;
+            m_cpt_cc_update_dcache_word_useful = 0;
+
+            m_cpt_frz_cycles   = 0;
             m_cpt_total_cycles = 0;
 
-            m_cpt_read = 0;
-            m_cpt_write = 0;
-            m_cpt_data_miss = 0;
-            m_cpt_ins_miss = 0;
-            m_cpt_unc_read = 0;
-            m_cpt_write_cached = 0;
+            m_cpt_data_read            = 0;
+            m_cpt_data_read_miss       = 0;
+            m_cpt_data_read_uncached   = 0;
+            m_cpt_data_write           = 0;
+            m_cpt_data_write_miss      = 0;
+            m_cpt_data_write_uncached  = 0;
+
+            m_cpt_ins_miss     = 0;
 
             m_cost_write_frz = 0;
@@ -385,5 +555,5 @@
             m_cpt_dmiss_transaction = 0;
             m_cpt_unc_transaction = 0;
-            m_cpt_write_transaction = 0;
+            m_cpt_data_write_transaction = 0;
 
             m_cost_imiss_transaction = 0;
@@ -396,12 +566,24 @@
         }
 
-#if DEBUG_CC_XCACHE_WRAPPER
-        std::cout << "--------------------------------------------" << std::endl;
-        std::cout << std::dec << "CC_XCACHE_WRAPPER " << m_srcid_rw << " / Time = " << m_cpt_total_cycles << std::endl;
-        std::cout             << " tgt fsm    = " << tgt_fsm_state_str[r_vci_tgt_fsm] << std::endl
-            << " dcache fsm = " << dcache_fsm_state_str[r_dcache_fsm] << std::endl
-            << " icache fsm = " << icache_fsm_state_str[r_icache_fsm] << std::endl
-            << " cmd fsm    = " << cmd_fsm_state_str[r_vci_cmd_fsm] << std::endl
-            << " rsp fsm    = " << rsp_fsm_state_str[r_vci_rsp_fsm] << std::endl;
+        // printf("%d\n",(uint32_t)m_cpt_total_cycles);
+
+        PRINTF("--------------------------------------------\n");
+        PRINTF("  * CC_XCACHE_WRAPPER \"%s\" - Time = %d\n",name().c_str(),(uint32_t)m_cpt_total_cycles);
+        PRINTF("    * fsm dcache          = %s\n",dcache_fsm_state_str[r_dcache_fsm]);
+        PRINTF("    * fsm icache          = %s\n",icache_fsm_state_str[r_icache_fsm]);
+        PRINTF("    * fsm cmd             = %s\n",cmd_fsm_state_str[r_vci_cmd_fsm]);
+        PRINTF("    * fsm rsp             = %s\n",rsp_fsm_state_str[r_vci_rsp_fsm]);
+        PRINTF("    * fsm tgt             = %s\n",tgt_fsm_state_str[r_vci_tgt_fsm]);
+        PRINTF("    * fsm cleanup         = %s\n",cleanup_fsm_state_str[r_cleanup_fsm]);
+        PRINTF("    * ll info             : %d %llx %llx\n",r_dcache_ll_valid.read(), (uint64_t)r_dcache_ll_addr.read(), (uint64_t)r_dcache_ll_data.read());
+        PRINTF("    * dcache_previous_unc : %d\n",r_dcache_previous_unc.read());
+        // CACHE_MISS_BUF_RSP_PRINT(i);
+        // CACHE_MISS_BUF_RSP_PRINT(d);
+
+#if CC_XCACHE_WRAPPER_DEBUG
+        if (m_cpt_total_cycles>=CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN)
+            {
+                r_wbuf.printTrace(1);
+            }
 #endif
 
@@ -444,4 +626,6 @@
                 if ( p_vci_tgt.cmdval.read() ) 
                 {
+                    PRINTF("    * <TGT> request\n");
+
                     addr_40 address = p_vci_tgt.address.read();
 
@@ -450,16 +634,16 @@
                         std::cout << "error in component VCI_CC_XCACHE_WRAPPER " << name() << std::endl;
                         std::cout << "coherence request is not a write" << std::endl;
-                        std::cout << "oddress = " << std::hex << address << std::endl;
-                        std::cout << "srcid   = " << std::hex << p_vci_tgt.srcid.read() << std::endl;
+                        std::cout << "oddress = " << std::hex << address << std::dec << std::endl;
+                        std::cout << "srcid   = " << p_vci_tgt.srcid.read() << std::endl;
                         exit(0);
                     }
 
                     // multi-update or multi-invalidate for data type
-                    if ( ((address&0x3) != 0x3) && (! m_segment.contains(address)) ) 
+                    if ( ((address&0x3) != 0x3) and (not m_segment.contains(address)) ) 
                     {
                         std::cout << "error in component VCI_CC_XCACHE_WRAPPER " << name() << std::endl;
                         std::cout << "out of segment coherence request" << std::endl;
-                        std::cout << "oddress = " << std::hex << address << std::endl;
-                        std::cout << "srcid   = " << std::hex << p_vci_tgt.srcid.read() << std::endl;
+                        std::cout << "oddress = " << std::hex << address << std::dec << std::endl;
+                        std::cout << "srcid   = " << p_vci_tgt.srcid.read() << std::endl;
                         exit(0);
                     }
@@ -470,9 +654,13 @@
                     r_tgt_trdid = p_vci_tgt.trdid.read();
                     r_tgt_pktid = p_vci_tgt.pktid.read();
-                    r_tgt_plen  = p_vci_tgt.plen.read();
+                 // r_tgt_plen  = p_vci_tgt.plen.read();
                     
+                    PRINTF("    * <TGT> address : %llx\n",(uint64_t)address);
+                    PRINTF("    * <TGT> address : %llx\n",(uint64_t)((((addr_40) ((p_vci_tgt.be.read() & 0x3) << 32)) | 
+                                                                      ((addr_40) (p_vci_tgt.wdata.read()))) * m_dcache_words * 4));
+
                     if ( (address&0x3) == 0x3 )   // broadcast invalidate for data or instruction type
                     {
-                        if ( ! p_vci_tgt.eop.read() ) 
+                        if ( not p_vci_tgt.eop.read() ) 
                         {
                             std::cout << "error in component VCI_CC_XCACHE_WRAPPER " << name() << std::endl;
@@ -481,15 +669,15 @@
                         }
                         r_tgt_update = false; 
-                        r_tgt_brdcast= true;
+                        // r_tgt_brdcast= true;
                         r_vci_tgt_fsm = TGT_REQ_BROADCAST;
-                        m_cpt_cc_inval++ ;
+                        m_cpt_cc_inval_broadcast++ ;
                     }
                     else                    // multi-update or multi-invalidate for data type
                     { 
                         uint32_t cell = address - m_segment.baseAddress(); // addr_40
-                        r_tgt_brdcast = false;
+                        // r_tgt_brdcast = false;
                         if (cell == 0) 
                         {                                       // invalidate data
-                            if ( ! p_vci_tgt.eop.read() ) 
+                            if ( not p_vci_tgt.eop.read() ) 
                             {
                                 std::cout << "error in component VCI_CC_XCACHE_WRAPPER " << name() << std::endl;
@@ -499,9 +687,9 @@
                             r_tgt_update = false; 
                             r_vci_tgt_fsm = TGT_REQ_DCACHE;
-                            m_cpt_cc_inval++ ;
+                            m_cpt_cc_inval_dcache++ ;
                         } 
                         else if (cell == 4)                     // invalidate instruction
                         {                         
-                            if ( ! p_vci_tgt.eop.read() ) 
+                            if ( not p_vci_tgt.eop.read() ) 
                             {
                                 std::cout << "error in component VCI_CC_VCACHE_WRAPPER " << name() << std::endl;
@@ -511,7 +699,7 @@
                             r_tgt_update = false; 
                             r_vci_tgt_fsm = TGT_REQ_ICACHE;
-                            m_cpt_cc_inval++ ;
+                            m_cpt_cc_inval_icache++ ;
                         } 
-                        else if ( (cell == 8) || (cell==12) )    // update data or instruction
+                        else if ( (cell == 8) or (cell==12) )    // update data or instruction
                         {                                
                             if ( p_vci_tgt.eop.read() ) 
@@ -522,10 +710,15 @@
                             }
                             if(cell == 8)
+                            {
+                                m_cpt_cc_update_dcache++;
                                 r_tgt_update_data = true;
+                            }
                             else
+                            {
+                                m_cpt_cc_update_icache++;
                                 r_tgt_update_data = false;
+                            }
                             r_tgt_update = true; 
                             r_vci_tgt_fsm = TGT_UPDT_WORD;
-                            m_cpt_cc_update++ ;
                         } 
 
@@ -556,5 +749,5 @@
                 {
                     size_t word = r_tgt_word.read();
-                    if ( word >= m_dcache_words ) 
+                    if ( word >= m_cache_words ) 
                     {
                         std::cout << "error in component VCI_CC_XCACHE_WRAPPER " << name() << std::endl;
@@ -565,8 +758,25 @@
                     std::cout << "PROC " << m_srcid_rw << " update, data : " << p_vci_tgt.wdata.read() << " be : " << std::hex << p_vci_tgt.be.read() << std::dec << std::endl;
 #endif
+
                     r_tgt_buf[word] = p_vci_tgt.wdata.read();
-                    r_tgt_be[word] = p_vci_tgt.be.read();
+                    r_tgt_be [word] = p_vci_tgt.be.read();
+
+                    if (p_vci_tgt.be.read())
+                    {
+                        if(r_tgt_update_data.read())
+                            m_cpt_cc_update_dcache_word_useful++ ;
+                        else
+                            m_cpt_cc_update_icache_word_useful++ ;
+                    }
+
                     r_tgt_word = word + 1;
                     if (p_vci_tgt.eop.read()){
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+                      uint32_t word=0;
+                      for (; word<m_cache_words; ++word)
+                          if (r_tgt_be[word] != 0)
+                              break;
+                      r_cache_word = word;
+#endif
                       if(r_tgt_update_data.read()){
                         r_vci_tgt_fsm = TGT_REQ_DCACHE;
@@ -579,5 +789,5 @@
 
             case TGT_REQ_BROADCAST:
-                if ( !r_tgt_icache_req.read() && !r_tgt_dcache_req.read() ) 
+                if ( not r_tgt_icache_req.read() and not r_tgt_dcache_req.read() ) 
                 {
                     r_vci_tgt_fsm = TGT_RSP_BROADCAST; 
@@ -589,5 +799,5 @@
             case TGT_REQ_ICACHE:
                 {
-                    if ( !r_tgt_icache_req.read() ) 
+                    if ( not r_tgt_icache_req.read() ) 
                     {
                         r_vci_tgt_fsm = TGT_RSP_ICACHE; 
@@ -598,5 +808,5 @@
 
             case TGT_REQ_DCACHE:
-                if ( !r_tgt_dcache_req.read() ) 
+                if ( not r_tgt_dcache_req.read() ) 
                 {
                     r_vci_tgt_fsm = TGT_RSP_DCACHE; 
@@ -606,8 +816,8 @@
 
             case TGT_RSP_BROADCAST:
-                if ( !r_tgt_icache_req.read() && !r_tgt_dcache_req.read() ) 
+                if ( not r_tgt_icache_req.read() and not r_tgt_dcache_req.read() ) 
                 {
                     // one response
-                    if ( !r_tgt_icache_rsp || !r_tgt_dcache_rsp )
+                    if ( not r_tgt_icache_rsp or not r_tgt_dcache_rsp )
                     {
                         if ( p_vci_tgt.rspack.read() )
@@ -620,5 +830,5 @@
 
                     // if data and instruction have the inval line, need two responses  
-                    if ( r_tgt_icache_rsp && r_tgt_dcache_rsp )
+                    if ( r_tgt_icache_rsp and r_tgt_dcache_rsp )
                     {
                         if ( p_vci_tgt.rspack.read() )
@@ -629,5 +839,5 @@
 
                     // if there is no need for a response
-                    if ( !r_tgt_icache_rsp && !r_tgt_dcache_rsp )
+                    if ( not r_tgt_icache_rsp and not r_tgt_dcache_rsp )
                     {
                         r_vci_tgt_fsm = TGT_IDLE;
@@ -639,5 +849,5 @@
             case TGT_RSP_ICACHE:
                 {
-                    if ( (p_vci_tgt.rspack.read() || !r_tgt_icache_rsp.read()) && !r_tgt_icache_req.read() ) 
+                    if ( (p_vci_tgt.rspack.read() or not r_tgt_icache_rsp.read()) and not r_tgt_icache_req.read() ) 
                     {
                         r_vci_tgt_fsm = TGT_IDLE;
@@ -649,5 +859,5 @@
             case TGT_RSP_DCACHE:
                 {
-                    if ( (p_vci_tgt.rspack.read() || !r_tgt_dcache_rsp.read()) && !r_tgt_dcache_req.read() ) 
+                    if ( (p_vci_tgt.rspack.read() or not r_tgt_dcache_rsp.read()) and not r_tgt_dcache_req.read() ) 
                     {
                         r_vci_tgt_fsm = TGT_IDLE;
@@ -667,4 +877,5 @@
         // - r_icache_unc_req set
         // - r_icache_buf_unc_valid set
+        // - r_vci_rsp_icache_miss_ok reset
         // - r_vci_rsp_ins_error reset
         // - r_tgt_icache_req reset
@@ -692,11 +903,12 @@
         typename iss_t::InstructionResponse irsp = ISS_IRSP_INITIALIZER;
 
-        typename iss_t::DataRequest  dreq = ISS_DREQ_INITIALIZER;
-        typename iss_t::DataResponse drsp = ISS_DRSP_INITIALIZER;
+        typename iss_t::DataRequest         dreq = ISS_DREQ_INITIALIZER;
+        typename iss_t::DataResponse        drsp = ISS_DRSP_INITIALIZER;
 
         m_iss.getRequests( ireq, dreq );
 
-#if DEBUG_CC_XCACHE_WRAPPER
-        std::cout << " Instruction Request: " << ireq << std::endl;
+#if CC_XCACHE_WRAPPER_DEBUG
+        if (m_cpt_total_cycles>=CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN)
+            std::cout << "    * Instruction Request  : " << ireq << std::endl;
 #endif
 
@@ -715,18 +927,36 @@
                         bool    icache_hit = false;
                         bool    icache_cached = m_cacheability_table[(vci_addr_t)ireq.addr];
+                        bool    icache_cleanup_hit = r_icache_cleanup_req and (((addr_40)ireq.addr >> (addr_40)m_icache_words_shift) == r_icache_cleanup_line.read());
+
                         // icache_hit & icache_ins evaluation
                         if ( icache_cached ) {
                             icache_hit = r_icache.read((vci_addr_t) ireq.addr, &icache_ins);
                         } else {
-                            icache_hit = ( r_icache_buf_unc_valid && ((addr_40) ireq.addr == (addr_40)r_icache_addr_save) );
-                            icache_ins = r_icache_miss_buf[0];
+                            // if uncache, again in the icache_miss_buf
+                            icache_hit = ( r_icache_buf_unc_valid and ((addr_40) ireq.addr == (addr_40)r_icache_addr_save));
+                            icache_ins = CACHE_MISS_BUF_RSP_DATA(i,0);
+                            CACHE_MISS_BUF_RSP_POP(i);
                         }
-                        if ( ! icache_hit ) {
+
+                        PRINTF("    * <ICACHE> hit %d - cached %d - cleanup_hit %d\n",icache_hit, icache_cached, icache_cleanup_hit);
+
+                        ASSERT( not (icache_hit and icache_cleanup_hit),
+                                "Icache hit and icache_cleanup_hit");
+
+                        if ( not icache_hit and not icache_cleanup_hit) {
                             m_cpt_ins_miss++;
                             m_cost_ins_miss_frz++;
                             r_icache_addr_save = (addr_40) ireq.addr;
+
+                            CACHE_MISS_BUF_REQ_INIT(i);
+
                             if ( icache_cached ) {
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+                                r_icache_fsm = ICACHE_MISS_VICTIM;
+#else
                                 r_icache_fsm = ICACHE_MISS_WAIT;
+#endif
                                 r_icache_miss_req = true;
+                               
                             } else {
                                 r_icache_fsm = ICACHE_UNC_WAIT;
@@ -744,4 +974,25 @@
                 }
                 //////////////////////
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+            case ICACHE_MISS_VICTIM:
+                {
+                    if (not r_icache_cleanup_req)
+                    {
+                        size_t     way;
+                        size_t     set;
+                        vci_addr_t addr = (vci_addr_t) r_icache_addr_save.read();
+                        vci_addr_t victim;
+                        
+                        r_icache_cleanup_req  = r_icache.victim_select(addr, &victim, &way, &set );
+                        r_icache_cleanup_line = (addr_40) victim;
+                        r_icache_miss_way     = way;
+                        r_icache_miss_set     = set;
+                        
+                        r_icache_fsm = ICACHE_MISS_WAIT;
+                    }
+                    break;
+                }
+#endif
+                //////////////////////
             case ICACHE_MISS_WAIT:
                 {
@@ -751,20 +1002,41 @@
                         r_icache_fsm_save = r_icache_fsm.read();
                         break;
-                    } 
-                    if ( !r_icache_miss_req && !r_icache_inval_rsp ) { // Miss read response and no invalidation
-                        if ( r_vci_rsp_ins_error ) {
-                            r_icache_fsm = ICACHE_ERROR;
-                        } else {
-                            r_icache_fsm = ICACHE_MISS_UPDT;
-                        }
-                    }
-                    if ( !r_icache_miss_req && r_icache_inval_rsp ) { // Miss read response and invalidation
-                        if ( r_vci_rsp_ins_error ) {
-                            r_icache_inval_rsp = false;
-                            r_icache_fsm = ICACHE_ERROR;
-                        } else {
-                            r_icache_inval_rsp = false;
-                            r_icache_fsm = ICACHE_CC_CLEANUP;
-                        }
+                    }
+
+                    bool val = CACHE_MISS_BUF_RSP_VAL(i,0);
+
+                    PRINTF("    * <ICACHE> val                  : %d\n",val);
+
+                    if (val)
+                    {
+                        PRINTF("    * <ICACHE> r_icache_inval_rsp   : %d\n",(int) r_icache_inval_rsp  );
+                        PRINTF("    * <ICACHE> r_vci_rsp_ins_error  : %d\n",(int) r_vci_rsp_ins_error );
+                        PRINTF("    * <ICACHE> r_icache_cleanup_req : %d\n",(int) r_icache_cleanup_req);
+
+                        // if (not r_icache_inval_rsp )
+                        // {
+                            // Miss read response and no invalidation
+                            if ( r_vci_rsp_ins_error ) {
+                                r_icache_fsm = ICACHE_ERROR;
+                            } else {
+#if not CC_XCACHE_WRAPPER_SELECT_VICTIM
+                                if (not r_icache_cleanup_req.read())
+#endif
+                                {
+                                    r_icache_update_addr = 0;
+                                    r_icache_fsm         = ICACHE_MISS_UPDT;
+                                }
+                            }
+                        // }
+                        // else
+                        // {
+                        //     r_icache_inval_rsp = false;
+                            
+                        //     // Miss read response and invalidation
+                        //     if ( r_vci_rsp_ins_error )
+                        //         r_icache_fsm = ICACHE_ERROR;
+                        //     else
+                        //         r_icache_fsm = ICACHE_CC_CLEANUP;
+                        // }
                     }
                     break;
@@ -778,6 +1050,10 @@
                         r_icache_fsm_save = r_icache_fsm.read();
                         break;
-                    } 
-                    if ( !r_icache_unc_req ) {
+                    }
+
+                    bool ok = CACHE_MISS_BUF_RSP_VAL(i,0);
+
+                    if (ok)
+                    {
                         if ( r_vci_rsp_ins_error ) {
                             r_icache_fsm = ICACHE_ERROR;
@@ -803,31 +1079,76 @@
             case ICACHE_MISS_UPDT: 
                 {
-                    if ( r_tgt_icache_req ) {   // external request
-                        r_icache_fsm = ICACHE_CC_CHECK;
-                        r_icache_fsm_save = r_icache_fsm.read();
-                        break;
-                    } 
-                    if(!r_icache_cleanup_req.read() && !r_icache_inval_rsp){
-                        vci_addr_t ad   = 0;
-                        ad              = (vci_addr_t) r_icache_addr_save.read();
-                        data_t*   buf   = r_icache_miss_buf;
-                        vci_addr_t victim_index = 0;
-                        m_cpt_icache_dir_write++;
-                        m_cpt_icache_data_write++;
-                        if ( ireq.valid ) m_cost_ins_miss_frz++;
-
-                        r_icache_cleanup_req  = r_icache.update(ad, buf, &victim_index);
-                        r_icache_cleanup_line = (addr_40) victim_index;
-
-                        r_icache_fsm        = ICACHE_IDLE;
-                        break;
-                    }
-                    if(r_icache_inval_rsp){
-                        if ( ireq.valid ) m_cost_ins_miss_frz++;
-                        r_icache_inval_rsp  = false;
-                        r_icache_fsm = ICACHE_CC_CLEANUP;
-                        break;
-                    }
-                    if ( ireq.valid ) m_cost_ins_miss_frz++;
+                    size_t     word = r_icache_update_addr.read();
+                    vci_addr_t addr = (vci_addr_t) r_icache_addr_save.read();
+                    size_t     way  = 0;
+                    size_t     set  = 0;
+
+                    // need invalid rsp, don't select a victim
+                    if (not r_icache_inval_rsp )
+                    {
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+                        way = r_icache_miss_way.read();
+                        set = r_icache_miss_set.read();
+#else
+
+                        // First word : select an victim !
+                        if (word == 0)
+                        {
+                            vci_addr_t victim;
+                        
+                            // r_icache_cleanup_req is false because is the transition condition to go in ICACHE_MISS_UPDT state
+                            r_icache_cleanup_req  = r_icache.victim_select(addr, &victim, &way, &set );
+                            r_icache.victim_update_tag(addr, way, set);
+                        
+                            r_icache_cleanup_line = (addr_40) victim;
+                            r_icache_miss_way     = way;
+                            r_icache_miss_set     = set;
+                        }
+                        else
+                        {
+                            way = r_icache_miss_way.read();
+                            set = r_icache_miss_set.read();
+                        }
+#endif
+                    }
+                    bool val = CACHE_MISS_BUF_RSP_VAL(i,word);
+
+                    if (val)
+                    {
+                        PRINTF("    * <ICACHE> rsp_val            : %d/%d\n",(int)r_icache_update_addr,m_icache_words);
+                        PRINTF("    * <ICACHE> r_icache_inval_rsp : %d\n",(int)r_icache_inval_rsp);
+                        PRINTF("    * <ICACHE> ins : %x\n",(int)CACHE_MISS_BUF_RSP_DATA(i,word));
+
+                        // m_cpt_icache_dir_write++;
+                        // m_cpt_icache_data_write++;
+                        // if ( ireq.valid ) m_cost_ins_miss_frz++;
+
+                        // if need invalid rsp, don't modify the cache, but pop the buf_rsp
+                        if (not r_icache_inval_rsp )
+                            r_icache.write(way, set, word, CACHE_MISS_BUF_RSP_DATA(i,word));
+                        CACHE_MISS_BUF_RSP_POP(i);
+
+                        r_icache_update_addr = ++word;
+                            
+                        // if last word, finish the update
+                        if (word >= m_icache_words)
+                        {
+                            // Last word : if previous invalid_rsp, can cleanup, else update the TAG
+                            if (r_icache_inval_rsp)
+                            {
+                                r_icache_inval_rsp  = false;
+                                r_icache_fsm = ICACHE_CC_CLEANUP;
+                            }
+                            else
+                            {
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+                                r_icache.victim_update_tag(addr, way, set);
+#endif
+                                r_icache_fsm = ICACHE_IDLE;
+                            }
+                        }
+                    }
+
+                    break;
                 }
                 ////////////////////
@@ -842,7 +1163,7 @@
                     }
                     // cleanup
-                    if(!r_icache_cleanup_req){
+                    if(not r_icache_cleanup_req){
                         r_icache_cleanup_req = true;
-                        r_icache_cleanup_line = r_icache_addr_save.read() >> (uint32_log2(m_icache_words) + 2);   
+                        r_icache_cleanup_line = r_icache_addr_save.read() >> m_icache_words_shift;
                         r_icache_fsm = ICACHE_IDLE;
                     }
@@ -853,10 +1174,10 @@
                 {
 
-                    m_cpt_icache_dir_read += m_icache_ways;
+                    m_cpt_icache_dir_read  += m_icache_ways;
                     m_cpt_icache_data_read += m_icache_ways;
-                    addr_40  ad           = r_tgt_addr;
+                    addr_40 ad = r_tgt_addr;
                     data_t  icache_rdata = 0;
 
-                    if(( ( r_icache_fsm_save == ICACHE_MISS_WAIT ) || ( r_icache_fsm_save == ICACHE_MISS_UPDT ) ) && 
+                    if((r_icache_fsm_save == ICACHE_MISS_WAIT) and 
                             ( (r_icache_addr_save.read() & ~((m_icache_words<<2)-1)) == (ad & ~((m_icache_words<<2)-1)))) {
                         r_icache_inval_rsp = true;
@@ -870,5 +1191,35 @@
                     } else {
                         bool    icache_hit   = r_icache.read(ad, &icache_rdata);
-                        if ( icache_hit && r_tgt_update ) {
+                        if ( icache_hit and r_tgt_update ) 
+                        {
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+                            uint32_t word  = r_cache_word;
+                            data_t   mask  = vci_param::be2mask(r_tgt_be[word]);
+                            data_t   rdata = 0;
+
+                            r_icache.read(ad+word*4,&rdata);
+                            r_tgt_buf[word] = (mask & r_tgt_buf[word]) | (~mask & rdata);
+                            
+                            word ++;
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+                            for (; word<m_icache_words; ++word)
+                                if (r_tgt_be[word] != 0)
+                                    break;
+#endif
+
+                            if (word==m_icache_words)
+                            {
+                                r_icache_fsm = ICACHE_CC_UPDT;
+
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+                                for (word=0; word<m_icache_words; ++word)
+                                    if (r_tgt_be[word] != 0)
+                                        break;
+#else
+                                word = 0;
+#endif
+                            }
+                            r_cache_word = word;
+#else //CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
                             r_icache_fsm = ICACHE_CC_UPDT;
                             // complete the line buffer in case of update
@@ -879,5 +1230,6 @@
                                 r_tgt_buf[i] = (mask & r_tgt_buf[i]) | (~mask & rdata);
                             }
-                        } else if ( icache_hit && !r_tgt_update ) {
+#endif //CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+                        } else if ( icache_hit and not r_tgt_update ) {
                             r_icache_fsm = ICACHE_CC_INVAL;
                         } else { // instruction not found (can happen)
@@ -908,7 +1260,30 @@
             case ICACHE_CC_UPDT:
                 {                       
+                    addr_40 ad = r_tgt_addr.read();
                     m_cpt_icache_dir_write++;
                     m_cpt_icache_data_write++;
-                    addr_40    ad  = r_tgt_addr.read();
+
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+                    uint32_t word  = r_cache_word;
+
+                    if(r_tgt_be[word])
+                        r_icache.write(ad+word*4, r_tgt_buf[word]);
+
+                    word ++;
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+                    for (; word<m_icache_words; ++word)
+                        if (r_tgt_be[word] != 0)
+                            break;
+#endif
+
+                    if (word==m_icache_words)
+                    {
+                        r_tgt_icache_req = false;
+                        r_tgt_icache_rsp = true;
+                        r_icache_fsm     = r_icache_fsm_save.read();
+                        word = 0;
+                    }
+                    r_cache_word = word;
+#else //CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
                     data_t* buf    = r_tgt_buf;
                     for(size_t i=0; i<m_icache_words;i++){
@@ -918,4 +1293,6 @@
                     r_tgt_icache_rsp = true;
                     r_icache_fsm     = r_icache_fsm_save.read();
+#endif //CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+
                     break;
                 }    
@@ -923,6 +1300,7 @@
         } // end switch r_icache_fsm
 
-#if DEBUG_CC_XCACHE_WRAPPER
-        std::cout << " Instruction Response: " << irsp << std::endl;
+#if CC_XCACHE_WRAPPER_DEBUG
+        if (m_cpt_total_cycles>=CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN)
+            std::cout << "    * Instruction Response : " << irsp << std::endl;
 #endif
 
@@ -940,5 +1318,4 @@
         // - r_dcache_miss_req set
         // - r_dcache_unc_req set
-        // - r_dcache_write_req set
         // - r_dcache_cleanup_req set
         // - r_vci_rsp_data_error reset
@@ -984,49 +1361,11 @@
         ///////////////////////////////////////////////////////////////////////////////////
 
-#if DEBUG_CC_XCACHE_WRAPPER
-        std::cout << " Data Request: " << dreq << std::endl;
-#endif
-
-        //if( (m_cpt_total_cycles % 10000) ==0 ) std::cout << std::dec << "Proc " << m_srcid << " Data Request: " << dreq << std::endl;
+#if CC_XCACHE_WRAPPER_DEBUG
+        if (m_cpt_total_cycles>=CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN)
+            std::cout << "    * Data        Request  : " << dreq << std::endl;
+#endif
 
         switch ( r_dcache_fsm ) {
 
-            /////////////////////
-            case DCACHE_WRITE_REQ:
-                { 
-                    if ( r_tgt_dcache_req ) {   // external request
-                        r_dcache_fsm = DCACHE_CC_CHECK;
-                        r_dcache_fsm_save = r_dcache_fsm;
-                        break;
-                    }
-                    // try to post the write request in the write buffer
-                    if ( !r_dcache_write_req ) {    // no previous write transaction     
-                        if ( r_wbuf.wok(r_dcache_addr_save) ) {   // write request in the same cache line
-                            r_wbuf.write(r_dcache_addr_save, r_dcache_be_save, r_dcache_wdata_save);
-                            // close the write packet if uncached
-                            if ( !r_dcache_cached_save ){
-                                r_dcache_write_req = true ;
-                            }
-                        } else {    
-                            // close the write packet if write request not in the same cache line
-                            r_dcache_write_req = true;  
-                            if(!m_srcid_rw) {
-                            }
-                            m_cost_write_frz++;
-                            break;  // posting request not possible : stay in DCACHE_WRITEREQ state
-                        }
-                    } else {    //  previous write transaction not completed
-                        m_cost_write_frz++;
-                        break;  // posting request not possible : stay in DCACHE_WRITEREQ state  
-                    }
-
-                    // close the write packet if the next processor request is not a write 
-                    if ( !dreq.valid || (dreq.type != iss_t::DATA_WRITE) ) {
-                        r_dcache_write_req = true ;
-                    }
-
-                    // The next state and the processor request parameters are computed 
-                    // as in the DCACHE_IDLE state (see below ...)
-                }
                 /////////////////
             case DCACHE_IDLE:
@@ -1038,97 +1377,184 @@
                     } 
 
-                    if ( dreq.valid ) {              
-                        bool        dcache_hit     = false;
-                        data_t      dcache_rdata   = 0;
-                        bool        dcache_cached;
+                    if ( dreq.valid ) {
+                        PRINTF("    * <DCACHE> Have dreq\n");
+
+                        data_t      dcache_rdata       = 0;
+                        // dcache_cached and dcache_hit don't used with dreq.type == {DATA_SC, XTN_READ, XTN_WRITE}
+                        bool        dcache_cached      = m_cacheability_table[(vci_addr_t)dreq.addr];
+                        bool        dcache_hit         = r_dcache.read((vci_addr_t) dreq.addr, &dcache_rdata);
+                        bool        dcache_cleanup_hit = r_dcache_cleanup_req and (((addr_40)dreq.addr >> (addr_40)m_dcache_words_shift) == r_dcache_cleanup_line.read());
+
+                        PRINTF("    * <DCACHE> hit %d - cached %d - cleanup_hit %d\n",dcache_hit, dcache_cached, dcache_cleanup_hit);
+                        
                         m_cpt_dcache_data_read += m_dcache_ways;
-                        m_cpt_dcache_dir_read += m_dcache_ways;
-
-                        // dcache_cached evaluation
-                        switch (dreq.type) {
-                            case iss_t::DATA_SC:
-                            case iss_t::XTN_READ:
-                            case iss_t::XTN_WRITE:
-                                dcache_cached = false;
-                                break;
-                            default:
-                                dcache_cached = m_cacheability_table[(vci_addr_t)dreq.addr];
-                        }
-
-                        // dcache_hit & dcache_rdata evaluation
-                        if ( dcache_cached ) {
-                            dcache_hit = r_dcache.read((vci_addr_t) dreq.addr, &dcache_rdata);
-                        } else {
-                            dcache_hit = false;
-                        }
+                        m_cpt_dcache_dir_read  += m_dcache_ways;
 
                         switch( dreq.type ) {
                             case iss_t::DATA_READ:
                             case iss_t::DATA_LL:
-                                m_cpt_read++;
-                                if ( dcache_hit ) {
-                                    r_dcache_fsm = DCACHE_IDLE;
-                                    drsp.valid = true;
-                                    drsp.rdata = dcache_rdata;
-                                    if(dreq.type == iss_t::DATA_LL){
-                                        r_dcache_ll_valid = true;
-                                        r_dcache_ll_data = dcache_rdata;
-                                        r_dcache_ll_addr = (vci_addr_t) dreq.addr;
+                                {
+                                    m_cpt_data_read++; // new dcache read
+
+                                    if (dcache_hit) // no special test for uncached read, because it's always miss
+                                        {
+                                            // address is in the cache : return the word
+                                            r_dcache_fsm = DCACHE_IDLE;
+                                            drsp.valid   = true;
+                                            drsp.rdata   = dcache_rdata; // return read data (cf dcache_hit)
+                                            
+                                            // if the request is a Load Linked instruction, save request information
+                                            if(dreq.type == iss_t::DATA_LL)
+                                                {
+                                                    PRINTF("    * <DCACHE> ll_valid = true\n");
+
+                                                    r_dcache_ll_valid = true;
+                                                    r_dcache_ll_data = dcache_rdata;
+                                                    r_dcache_ll_addr = (vci_addr_t) dreq.addr;
 #ifdef COHERENCE_DEBUG
-                                        std::cout << "Value returned for LL at address : " << std::hex << dreq.addr << " data : " << std::dec << dcache_rdata<< std::endl;
-                                        r_dcache.read((vci_addr_t) dreq.addr, &dcache_rdata);
-                                        std::cout << "Value stored at this  address : " << std::hex << dreq.addr << " data : " << std::dec << dcache_rdata<< std::endl;
-#endif
-                                    }
-                                } else {
-                                    if ( dcache_cached ) {
-                                        m_cpt_data_miss++;
-                                        m_cost_data_miss_frz++;
-                                        r_dcache_miss_req = true;
-                                        r_dcache_fsm = DCACHE_MISS_WAIT;
-                                    } else {
-                                        m_cpt_unc_read++;
-                                        m_cost_unc_read_frz++;
-                                        r_dcache_unc_req = true;
-                                        r_dcache_fsm = DCACHE_UNC_WAIT;
-                                    }
+                                                    std::cout << "Value returned for LL at address : " << std::hex << dreq.addr << " data : " << std::dec << dcache_rdata<< std::endl;
+                                                    r_dcache.read((vci_addr_t) dreq.addr, &dcache_rdata);
+                                                    std::cout << "Value stored at this  address : " << std::hex << dreq.addr << " data : " << std::dec << dcache_rdata<< std::endl;
+#endif
+                                                }
+                                        }
+                                    else
+                                        {
+                                            if (not dcache_cleanup_hit)
+                                            {
+                                                CACHE_MISS_BUF_REQ_INIT(d);
+                                                
+                                                // Miss : send signal at the CMD_FSM (via r_dcache_miss_req or r_dcache_unc_req)
+                                                if ( dcache_cached ) {
+                                                    m_cpt_data_read_miss++;
+                                                    m_cost_data_miss_frz++;
+                                                    r_dcache_miss_req = true;
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+                                                    r_dcache_fsm = DCACHE_MISS_VICTIM;
+#else
+                                                    r_dcache_fsm = DCACHE_MISS_WAIT;
+#endif
+                                                    
+                                                } else {
+                                                    if (not r_dcache_previous_unc.read()) // strongly order to the uncached access
+                                                    {
+                                                        r_dcache_previous_unc = true;
+                                                        
+                                                        m_cpt_data_read_uncached++;
+                                                        m_cost_unc_read_frz++;
+                                                        r_dcache_unc_req = true;
+                                                        r_dcache_fsm = DCACHE_UNC_WAIT;
+                                                    }
+                                                }
+                                            }
+                                        }
                                 }
                                 break;
                             case iss_t::DATA_SC:
                             {
-                                m_cpt_unc_read++;
-                                m_cost_unc_read_frz++;
-                                if(r_dcache_ll_valid.read() && (r_dcache_ll_addr.read() == (vci_addr_t)dreq.addr)){
-                                    r_dcache_sc_req = true;
-                                    r_dcache_fsm = DCACHE_SC_WAIT;
-                                } else {
-                                    drsp.valid = true;
-                                    drsp.rdata = 1; // SC rsp NOK
-                                    r_dcache_ll_valid = false;
+                                PRINTF("    * <DCACHE> DATA_SC - ll_valid = %d\n",r_dcache_ll_valid.read());
+
+                                if (not r_dcache_previous_unc.read() and not dcache_cleanup_hit) // strongly order to the uncached access
+                                {
+                                    //m_cpt_data_read_unc++; // instruction must read the memory in uncached mode
+                                    m_cost_unc_read_frz++;
+                                    
+                                    // if previous load linked (with the same address), make a transaction
+                                    // else, keep in IDLE state and return 1 (no OK)
+                                    if(r_dcache_ll_valid.read() and (r_dcache_ll_addr.read() == (vci_addr_t)dreq.addr)){
+                                        PRINTF("    * <DCACHE> have previous load linked\n");
+                                        
+                                        r_dcache_previous_unc = true;
+
+                                        r_dcache_sc_req   = true;
+
+                                        CACHE_MISS_BUF_REQ_INIT(d);
+
+                                        r_dcache_fsm = DCACHE_SC_WAIT;
+                                    } else {
+                                        PRINTF("    * <DCACHE> don't have previous load linked\n");
+                                        
+                                        drsp.valid = true;
+                                        drsp.rdata = 1; // SC rsp NOK
+                                        r_dcache_ll_valid = false;
+                                    }
                                 }
+
                                 break;
                             }
                             case iss_t::XTN_READ:
                             case iss_t::XTN_WRITE:
-                                    // only DCACHE INVALIDATE request are supported
-                                    if ( dreq.addr/4 == iss_t::XTN_DCACHE_INVAL ){
-                                        r_dcache_fsm = DCACHE_INVAL;
-                                    } else {
-                                        r_dcache_fsm = DCACHE_IDLE;
-                                    }
-                                    drsp.valid = true;
+                                {
+                                    bool drsp_valid = false;
+                                    // only DCACHE INVALIDATE and SYNC request are supported
+                                    switch (dreq.addr>>2)
+                                        {
+                                        case iss_t::XTN_DCACHE_INVAL : 
+                                            {
+                                                drsp_valid = true;
+                                                r_dcache_fsm = DCACHE_INVAL;
+                                                break;
+                                            }
+                                        case iss_t::XTN_SYNC :
+                                            {
+                                                // Test if write buffer is already empty
+                                                //  * gain : 1 cycle
+                                                //  * cost : can be on the critical path
+                                                if (r_wbuf.empty())
+                                                    {
+                                                        drsp_valid = true;
+                                                        r_dcache_fsm = DCACHE_IDLE;
+                                                    }
+                                                else
+                                                    {
+                                                        drsp_valid = false;
+                                                        r_dcache_fsm = DCACHE_SYNC;
+                                                    }
+                                                break;
+                                            }
+                                        default :
+                                            {
+                                                // std::cout << "Warning in VCI_CC_XCACHE_WRAPPER " << name() << std::endl;
+                                                // std::cout << "Unsupported  external access : " << (dreq.addr>>2) << std::endl;
+
+                                                r_dcache_fsm = DCACHE_IDLE;
+                                            }
+                                        }//end switch (dreq.addr>>2)
+
+                                    drsp.valid = drsp_valid;
                                     drsp.rdata = 0;
                                     break;
+                                }
                             case iss_t::DATA_WRITE:
-                                    m_cpt_write++;
-                                    if ( dcache_hit && dcache_cached ) {
-                                        r_dcache_fsm = DCACHE_WRITE_UPDT;
-                                        m_cpt_write_cached++;
-                                    } else {
-                                        r_dcache_fsm = DCACHE_WRITE_REQ;
+
+                                if (dcache_cached or not r_dcache_previous_unc.read()) // strongly order to the uncached access
+                                {
+                                    bool drsp_valid;
+
+                                    drsp_valid = r_wbuf.write((addr_40) dreq.addr, dreq.be, dreq.wdata, dcache_cached);
+
+                                    if (drsp_valid)
+                                    {
+                                        m_cpt_data_write++;
+                                        
+                                        if (not dcache_cached)
+                                        {
+                                            r_dcache_previous_unc = true;
+                                            m_cpt_data_write_uncached++;
+                                        }
+                                        else if (not dcache_hit)
+                                            m_cpt_data_write_miss++;
+                                        
+                                        if ( dcache_hit) {
+                                            r_dcache_fsm = DCACHE_WRITE_UPDT;
+                                        } else {
+                                            r_dcache_fsm = DCACHE_IDLE;
+                                        }
                                     }
-                                    drsp.valid = true;
+
+                                    drsp.valid = drsp_valid;
                                     drsp.rdata = 0;
-                                    break;
+                                }
+                                break;
                         } // end switch dreq.type
 
@@ -1139,15 +1565,9 @@
                         r_dcache_rdata_save     = dcache_rdata;
                         r_dcache_cached_save    = dcache_cached;
-
+                        
                     } else {    // end if dreq.valid
                         r_dcache_fsm = DCACHE_IDLE;
                     }
-                    // processor request are not accepted in the WRITE_REQUEST state
-                    // when the write buffer is not writeable
-                    if ( (r_dcache_fsm == DCACHE_WRITE_REQ) &&
-                            (r_dcache_write_req || !r_wbuf.wok(r_dcache_addr_save)) ) {
-                        drsp.valid = false;
-                        drsp.rdata = 0;
-                    }
+                    
                     break;
                 }
@@ -1160,7 +1580,31 @@
                     vci_addr_t ad = r_dcache_addr_save.read();
                     r_dcache.write(ad, wdata);
-                    r_dcache_fsm = DCACHE_WRITE_REQ;
+
+                    r_dcache_fsm = DCACHE_IDLE;
+
                     break;
                 }
+                //////////////////////
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+            case DCACHE_MISS_VICTIM:
+                {
+                    if (not r_dcache_cleanup_req.read())
+                     {
+                         size_t     way;
+                         size_t     set;
+                         vci_addr_t addr = (vci_addr_t) r_dcache_addr_save.read();
+                         vci_addr_t victim;
+                         
+                         r_dcache_cleanup_req  = r_dcache.victim_select(addr, &victim, &way, &set );
+                         r_dcache_cleanup_line = (addr_40) victim;
+                         r_dcache_miss_way     = way;
+                         r_dcache_miss_set     = set;
+                         
+                         r_dcache_fsm = DCACHE_MISS_WAIT;
+                     }
+                    
+                    break;
+                }
+#endif
                 //////////////////////
             case DCACHE_MISS_WAIT:
@@ -1173,21 +1617,38 @@
                         break;
                     }
-                    if ( !r_dcache_miss_req && !r_dcache_inval_rsp ) { // Miss read response and no invalidation
-                        if ( r_vci_rsp_data_error ) {
+
+                    bool val = CACHE_MISS_BUF_RSP_VAL(d,0);
+                    if (val)
+                    {
+                        // if (not r_dcache_inval_rsp )
+                        //  {
+
+                        // Miss read response and no invalidation
+                        if ( r_vci_rsp_data_error )
+                        {
                             r_dcache_fsm = DCACHE_ERROR;
-                        } else {
-                            r_dcache_fsm = DCACHE_MISS_UPDT;
+                        } 
+                        else 
+                        {
+#if not CC_XCACHE_WRAPPER_SELECT_VICTIM
+                            if (not r_dcache_cleanup_req.read())
+#endif
+                            {
+                                r_dcache_update_addr = 0;
+                                r_dcache_fsm         = DCACHE_MISS_UPDT;
+                            }
                         }
-                        break;
-                    }
-                    if ( !r_dcache_miss_req && r_dcache_inval_rsp ) { // Miss read response and invalidation
-                        if ( r_vci_rsp_data_error ) {
-                            r_dcache_inval_rsp  = false;
-                            r_dcache_fsm = DCACHE_ERROR;
-                        } else {
-                            r_dcache_inval_rsp  = false;
-                            r_dcache_fsm = DCACHE_CC_CLEANUP;
-                        }
-                        break;
+                        //  }
+                        // else
+                        // {
+                        //     r_dcache_inval_rsp  = false;
+
+                        //     // Miss read response and invalidation
+                        //     if ( r_vci_rsp_data_error ) {
+                        //         r_dcache_fsm = DCACHE_ERROR;
+                        //     } else {
+                        //         r_dcache_fsm = DCACHE_CC_CLEANUP;
+                        //     }
+                        // }
                     }
                     break;
@@ -1195,35 +1656,73 @@
                 //////////////////////
             case DCACHE_MISS_UPDT:
-
-                {
-                        if ( r_tgt_dcache_req.read() ) {   // external request
-                        r_dcache_fsm = DCACHE_CC_CHECK;
-                        r_dcache_fsm_save = r_dcache_fsm;
-                        break;
-                    }
-                    if( !r_dcache_cleanup_req.read() && !r_dcache_inval_rsp ){
-                        vci_addr_t  ad  = 0;
-                        ad = (vci_addr_t) r_dcache_addr_save.read();
-                        data_t* buf = new data_t[m_dcache_words];
-                        for(size_t i=0; i<m_dcache_words; i++) {
-                            buf[i] = r_dcache_miss_buf[i];
+                {
+                    size_t     word = r_dcache_update_addr.read();
+                    vci_addr_t addr = (vci_addr_t) r_dcache_addr_save.read();
+                    size_t     way  = 0;
+                    size_t     set  = 0;
+                    
+                    // need invalid rsp, don't select a victim
+                    if (not r_dcache_inval_rsp )
+                    {
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+                        way = r_dcache_miss_way.read();
+                        set = r_dcache_miss_set.read();
+#else
+                        // First word : select an victim !
+                        if (word == 0)
+                        {
+                            vci_addr_t victim;
+                        
+                            // r_dcache_cleanup_req is false (condition to enter in DCACHE_MISS_UPDT
+                            r_dcache_cleanup_req  = r_dcache.victim_select(addr, &victim, &way, &set );
+                            r_dcache.victim_update_tag(addr, way, set);
+                            r_dcache_cleanup_line = (addr_40) victim;
+
+                            r_dcache_miss_way     = way;
+                            r_dcache_miss_set     = set;
                         }
-                        vci_addr_t  victim_index = 0;
-                        if ( dreq.valid ) m_cost_data_miss_frz++;
-                        m_cpt_dcache_data_write++;
-                        m_cpt_dcache_dir_write++;
-
-                        r_dcache_cleanup_req = r_dcache.update(ad, buf, &victim_index);
-                        r_dcache_cleanup_line = (addr_40) victim_index;
-
-                        r_dcache_fsm = DCACHE_IDLE;
-                        delete [] buf;
-                        break;
-                    }
-                    if( r_dcache_inval_rsp ){
-                        r_dcache_inval_rsp  = false;
-                        r_dcache_fsm = DCACHE_CC_CLEANUP;
-                        break;
-                    }
+                        else
+                        {
+                            way = r_dcache_miss_way.read();
+                            set = r_dcache_miss_set.read();
+                        }
+#endif
+                    }
+
+                    bool val = CACHE_MISS_BUF_RSP_VAL(d,word);
+                    if (val)
+                    {
+                        // m_cpt_dcache_dir_write++;
+                        // if ( ireq.valid ) m_cost_data_miss_frz++;
+
+                        // if need invalid rsp, don't modify the cache, but pop the buf_rsp
+                        if (not r_dcache_inval_rsp )
+                        {
+                            r_dcache.write(way, set, word, CACHE_MISS_BUF_RSP_DATA(d,word));
+                            m_cpt_dcache_data_write++;
+                        }
+
+                        CACHE_MISS_BUF_RSP_POP(d);
+                        r_dcache_update_addr = ++word;
+                            
+                        // if last word, finish the update
+                        if (word >= m_dcache_words)
+                        {
+                            // Last word : if previous invalid_rsp, can cleanup, else update the TAG
+                            if (r_dcache_inval_rsp)
+                            {
+                                r_dcache_inval_rsp  = false;
+                                r_dcache_fsm = DCACHE_CC_CLEANUP;
+                            }
+                            else
+                            {
+#if CC_XCACHE_WRAPPER_SELECT_VICTIM
+                                r_dcache.victim_update_tag(addr, way, set);
+#endif
+                                r_dcache_fsm = DCACHE_IDLE;
+                            }
+                        }
+                    }
+                
                     break;
                 }
@@ -1237,16 +1736,24 @@
                         break;
                     } 
-                    if ( !r_dcache_unc_req ) {
+
+                    bool ok = CACHE_MISS_BUF_RSP_VAL(d,0);
+
+                    if (ok) {
                         if ( r_vci_rsp_data_error ) {
                             r_dcache_fsm = DCACHE_ERROR;
                         } else {
+                            data_t rdata = CACHE_MISS_BUF_RSP_DATA(d,0);
+                            CACHE_MISS_BUF_RSP_POP(d);
+
                             if(dreq.type == iss_t::DATA_LL){
+                                PRINTF("    * <DCACHE> ll_valid = true\n");
+
                                 r_dcache_ll_valid = true;
-                                r_dcache_ll_data = r_dcache_miss_buf[0];
+                                r_dcache_ll_data = rdata;
                                 r_dcache_ll_addr = (vci_addr_t) dreq.addr;
                             }
                             r_dcache_fsm = DCACHE_IDLE;
                             drsp.valid = true;
-                            drsp.rdata = r_dcache_miss_buf[0];
+                            drsp.rdata = rdata;
                         }
                     }
@@ -1262,5 +1769,8 @@
                         break;
                     } 
-                    if ( !r_dcache_sc_req ) {
+
+                    bool ok = CACHE_MISS_BUF_RSP_VAL(d,0);
+
+                    if (ok) {
                         if ( r_vci_rsp_data_error ) {
                             r_dcache_fsm = DCACHE_ERROR;
@@ -1268,5 +1778,6 @@
                             r_dcache_fsm = DCACHE_IDLE;
                             drsp.valid = true;
-                            drsp.rdata = r_dcache_miss_buf[0];
+                            drsp.rdata = CACHE_MISS_BUF_RSP_DATA(d,0);
+                            CACHE_MISS_BUF_RSP_POP(d);
                             r_dcache_ll_valid = false;
                         }
@@ -1292,12 +1803,27 @@
                         break;
                     }
-                    if( !r_dcache_cleanup_req.read() ){
+                    if( not r_dcache_cleanup_req.read() ){
                         m_cpt_dcache_dir_read += m_dcache_ways;
                         vci_addr_t  ad  = r_dcache_addr_save.read();
                         r_dcache_cleanup_req = r_dcache.inval(ad);
-                        r_dcache_cleanup_line = r_dcache_addr_save.read() >> (uint32_log2(m_dcache_words)+2);
+                        r_dcache_cleanup_line = r_dcache_addr_save.read() >> m_dcache_words_shift;
 
                         r_dcache_fsm = DCACHE_IDLE;
                     }
+                    break;
+                }
+            case DCACHE_SYNC :
+                {
+                    if ( r_tgt_dcache_req ) {   // external request
+                        r_dcache_fsm = DCACHE_CC_CHECK;
+                        r_dcache_fsm_save = r_dcache_fsm;
+                        break;
+                    } 
+
+                    if (r_wbuf.empty())
+                        {
+                            drsp.valid = true; // end, can accept the sync request
+                            r_dcache_fsm = DCACHE_IDLE;
+                        }
                     break;
                 }
@@ -1305,11 +1831,8 @@
             case DCACHE_CC_CHECK:   // read directory in case of invalidate or update request
                 {
-
-                    m_cpt_dcache_dir_read += m_dcache_ways;
-                    m_cpt_dcache_data_read += m_dcache_ways;
-                    addr_40  ad           = r_tgt_addr;
+                    addr_40  ad          = r_tgt_addr;
                     data_t  dcache_rdata = 0;
 
-                    if(( ( r_dcache_fsm_save == DCACHE_MISS_WAIT ) || ( r_dcache_fsm_save == DCACHE_MISS_UPDT ) ) && 
+                    if((r_dcache_fsm_save == DCACHE_MISS_WAIT) and 
                             ( (r_dcache_addr_save.read() & ~((m_dcache_words<<2)-1)) == (ad & ~((m_dcache_words<<2)-1)))) {
                         r_dcache_inval_rsp = true;
@@ -1323,8 +1846,42 @@
                     } else {
                         bool    dcache_hit   = r_dcache.read(ad, &dcache_rdata);
+
+                        m_cpt_dcache_data_read += m_dcache_ways;
+                        m_cpt_dcache_dir_read += m_dcache_ways;
+
 #ifdef COHERENCE_DEBUG
                         std::cout << "PROC " << m_srcid_rw << " DCACHE_CC_CHECK, hit ? : " << dcache_hit << std::endl;
 #endif
-                        if ( dcache_hit && r_tgt_update ) {
+                        if ( dcache_hit and r_tgt_update ) 
+                        {
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+                            uint32_t word  = r_cache_word;
+                            data_t   mask  = vci_param::be2mask(r_tgt_be[word]);
+                            data_t   rdata = 0;
+
+                            r_dcache.read(ad+word*4,&rdata);
+                            
+                            r_tgt_buf[word] = (mask & r_tgt_buf[word]) | (~mask & rdata);
+
+                            word ++;
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+                            for (; word<m_dcache_words; ++word)
+                                if (r_tgt_be[word] != 0)
+                                    break;
+#endif
+
+                            if (word==m_dcache_words)
+                            {
+                                r_dcache_fsm = DCACHE_CC_UPDT;
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+                                for (word=0; word<m_dcache_words; ++word)
+                                    if (r_tgt_be[word] != 0)
+                                        break;
+#else
+                                word = 0;
+#endif
+                            }
+                            r_cache_word = word;
+#else //CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
                             // complete the line buffer in case of update
                             for(size_t i=0; i<m_dcache_words; i++){
@@ -1335,5 +1892,6 @@
                             }
                             r_dcache_fsm = DCACHE_CC_UPDT;
-                        } else if ( dcache_hit && !r_tgt_update ) {
+#endif //CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+                        } else if ( dcache_hit and not r_tgt_update ) {
                             r_dcache_fsm = DCACHE_CC_INVAL;
                         } else {
@@ -1352,20 +1910,51 @@
             case DCACHE_CC_UPDT:    // update directory and data cache        
                 {
+                    addr_40 ad = r_tgt_addr;
+
                     m_cpt_dcache_dir_write++;
                     m_cpt_dcache_data_write++;
-                    addr_40  ad      = r_tgt_addr;
-                    data_t* buf     = r_tgt_buf;
-#ifdef COHERENCE_DEBUG
+
+# ifdef COHERENCE_DEBUG
                     std::cout << "PROC " << m_srcid_rw << " DCACHE_CC_UPDT, update : " << std::endl;
-#endif
+# endif
+
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+                    uint32_t word  = r_cache_word;
+                    
+                    if(r_tgt_be[word])
+                        r_dcache.write(ad+word*4, r_tgt_buf[word]);
+# ifdef COHERENCE_DEBUG
+                    std::cout << " address " << std::hex << ad+word*4 << " data " << std::dec << r_tgt_buf[word] << std::endl;
+                    data_t rdata = 0xAAAAAAAA;
+                    r_dcache.read(ad+word*4,&rdata);
+                    std::cout << "data written " << rdata << std::endl; 
+# endif
+
+                    word ++;
+#if CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE_OPT
+                    for (; word<m_dcache_words; ++word)
+                        if (r_tgt_be[word] != 0)
+                            break;
+#endif
+                    
+                    if (word==m_dcache_words)
+                    {
+                        r_tgt_dcache_req = false;
+                        r_tgt_dcache_rsp = true;
+                        r_dcache_fsm = r_dcache_fsm_save;
+                        word = 0;
+                    }
+                    r_cache_word = word;
+#else //CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
+                    data_t* buf = r_tgt_buf;
                     for(size_t i=0; i<m_dcache_words; i++){
                         if(r_tgt_be[i]) {
                             r_dcache.write( ad + i*4, buf[i]);
-#ifdef COHERENCE_DEBUG
+# ifdef COHERENCE_DEBUG
                             std::cout << " address " << std::hex << ad+i*4 << " data " << std::dec << buf[i] << std::endl;
                             data_t rdata = 0xAAAAAAAA;
                             r_dcache.read(ad + i*4,&rdata);
                             std::cout << "data written " << rdata << std::endl; 
-#endif
+# endif //CC_XCACHE_WRAPPER_CC_UPDATE_MULTI_CYCLE
                         }
                     }
@@ -1373,4 +1962,5 @@
                     r_tgt_dcache_rsp = true;
                     r_dcache_fsm = r_dcache_fsm_save;
+#endif
                     break;
                 }
@@ -1396,7 +1986,7 @@
                     }        
                     // cleanup
-                    if(!r_dcache_cleanup_req){
+                    if(not r_dcache_cleanup_req){
                         r_dcache_cleanup_req = true;
-                        r_dcache_cleanup_line = r_dcache_addr_save.read() >> (uint32_log2(m_dcache_words) + 2);
+                        r_dcache_cleanup_line = r_dcache_addr_save.read() >> m_dcache_words_shift;
                         r_dcache_fsm = DCACHE_IDLE;
                     }
@@ -1405,7 +1995,22 @@
 
         } // end switch r_dcache_fsm
-
-#if DEBUG_CC_XCACHE_WRAPPER
-        std::cout << " Data Response: " << drsp << std::endl;
+        
+        ////////// write buffer state update  /////////////
+        // The update() method must be called at each cycle to update the internal state.
+        // All pending write requests must be locked in case of SYNC
+        bool wbuf_flush=(r_dcache_fsm == DCACHE_SYNC);
+#if   (CC_XCACHE_WRAPPER_WBUF_UPDATE_SCHEME==1)
+        r_wbuf.update_multi_scan      (wbuf_flush);
+#elif (CC_XCACHE_WRAPPER_WBUF_UPDATE_SCHEME==2)
+        r_wbuf.update_round_robin_scan(wbuf_flush);
+#elif (CC_XCACHE_WRAPPER_WBUF_UPDATE_SCHEME==3)
+        r_wbuf.update_one_scan        (wbuf_flush);
+#else
+        r_wbuf.update                 (wbuf_flush);
+#endif
+
+#if CC_XCACHE_WRAPPER_DEBUG
+        if (m_cpt_total_cycles>=CC_XCACHE_WRAPPER_DEBUG_CYCLE_MIN)
+            std::cout << "    * Data        Response : " << drsp << std::endl;
 #endif
 
@@ -1418,6 +2023,137 @@
         }
 
-        if ( (ireq.valid && !irsp.valid) || (dreq.valid && !drsp.valid) ) m_cpt_frz_cycles++;
-
+        if ( (ireq.valid and not irsp.valid) or 
+             (dreq.valid and not drsp.valid))
+        {
+            m_cpt_frz_cycles++;
+#if CC_XCACHE_WRAPPER_STOP_SIMULATION
+            m_stop_simulation_nb_frz_cycles ++;
+            
+            if (m_stop_simulation and (m_stop_simulation_nb_frz_cycles >= m_stop_simulation_nb_frz_cycles_max))
+            {
+                std::cout << std::dec << "CC_XCACHE_WRAPPER \"" << name() << "\" : cycle " << m_cpt_total_cycles << ", the cpu is frozen since " << m_stop_simulation_nb_frz_cycles << " cycles." << std::endl;
+                ASSERT(false,"CPU : anormal activity"); // exit
+            }
+        }
+        else
+        {
+            m_stop_simulation_nb_frz_cycles = 0; // reinit counter
+#endif //CC_XCACHE_WRAPPER_STOP_SIMULATION
+        }
+
+
+#if CC_XCACHE_WRAPPER_DEBUG_DCACHE_TRANSACTION
+        if (dreq.valid and drsp.valid)
+        {
+            log_dcache_transaction_file 
+                << "[" << m_cpt_total_cycles << "]"
+                << std::hex
+                << " @ "     << std::setw(8) << (uint32_t)dreq.addr
+                << " be "    << std::setw(1) << (uint32_t)dreq.be
+                << " W "     << std::setw(8) << (uint32_t)dreq.wdata
+                << " R "     << std::setw(8) << (uint32_t)drsp.rdata
+                << " error "            << (uint32_t)drsp.error
+                << std::dec
+                << " "  << type_str(dreq.type);
+
+            if ((dreq.type == iss_t::XTN_READ) or 
+                (dreq.type == iss_t::XTN_WRITE))
+                //log_dcache_transaction_file << xtn_str(dreq.addr>>2);
+                switch (dreq.addr>>2)
+                {
+                case iss_t::XTN_DCACHE_INVAL : log_dcache_transaction_file << " INVAL"; break;
+                case iss_t::XTN_SYNC         : log_dcache_transaction_file << " SYNC"; break;
+                default                      : log_dcache_transaction_file << " invalid"; break;
+                }                                                                            
+
+            log_dcache_transaction_file << std::endl;
+
+            // printf("[%d] @ %.8x be %.1x W %.8x R %.8x error %d - %s"
+            //        ,(uint32_t)m_cpt_total_cycles
+            //        ,(uint32_t)dreq.addr
+            //        ,(uint32_t)dreq.be
+            //        ,(uint32_t)dreq.wdata
+            //        ,(uint32_t)drsp.rdata
+            //        ,(uint32_t)drsp.error
+            //        ,type_str(dreq.type));
+            // if ((dreq.type == iss_t::XTN_READ) or 
+            //     (dreq.type == iss_t::XTN_WRITE))
+            //     //     printf(" %s",xtn_str(dreq.addr>>2));
+            //     switch (dreq.addr>>2)
+            //     {
+            //     case iss_t::XTN_DCACHE_INVAL : printf(" INVAL"); break;
+            //     case iss_t::XTN_SYNC         : printf(" SYNC"); break;
+            //     default                      : printf(" invalid"); break;
+            //     }                                                                            
+            // printf("\n");
+        }
+#endif //CC_XCACHE_WRAPPER_DEBUG_DCACHE_TRANSACTION
+
+        ////////////////////////////////////////////////////////////////////////////
+        // This CLEANUP FSM controls the transmission of the cleanup transactions
+        // on the coherence network. It controls the following ressources:
+        // - r_cleanup_fsm
+        // - r_dcache_cleanup_req (reset)
+        // - r_icache_cleanup_req (reset)
+        // 
+        // This FSM handles cleanup requests from both the DCACHE FSM & ICACHE FSM
+        // - Instruction Cleanup  : r_icache_cleanup_req 
+        // - Data Cleanup         : r_dcache_cleanup_req 
+        // In case of simultaneous requests, the data request have highest priority.
+        // There is only one cleanup transaction at a given time (sequencial behavior)
+        // because the same FSM controls both command & response. 
+        // The the r_icache_cleanup_req & r_dcache_cleanup_req are reset only
+        // when the response packet is received.
+        // Error handling :
+        // As the coherence trafic is controled by hardware, errors are not reported
+        // to software : In case of errors, the simulation stops.
+        ////////////////////////////////////////////////////////////////////////////
+
+        switch (r_cleanup_fsm) {
+
+            case CLEANUP_IDLE:
+            {    
+                if ( p_vci_ini_c.cmdack )
+                {
+                    if      (r_dcache_cleanup_req) 	r_cleanup_fsm = CLEANUP_DCACHE;
+                    else if (r_icache_cleanup_req) 	r_cleanup_fsm = CLEANUP_ICACHE;
+                }
+                break;
+            }
+            case CLEANUP_DCACHE:
+            {
+                if ( p_vci_ini_c.rspval )
+                {
+                    PRINTF("      * <CLEANUP> rerror : %d (%d)\n",(uint32_t)p_vci_ini_c.rerror.read(),0x2 & ( (1 << vci_param::E) - 1));
+
+                    ASSERT(p_vci_ini_c.reop and (p_vci_ini_c.rtrdid.read() == TYPE_DATA_CLEANUP),
+                            "illegal response packet received for a cleanup transaction");
+                    ASSERT(p_vci_ini_c.rerror.read() == vci_param::ERR_NORMAL,
+                           "error signaled in a cleanup response" );
+                    
+                    r_cleanup_fsm = CLEANUP_IDLE;
+                    r_dcache_cleanup_req = false;
+                    // m_cpt_cc_cleanup_data++; TODO
+                }
+                break;
+            }
+            case CLEANUP_ICACHE:
+            {
+                if ( p_vci_ini_c.rspval )
+                {
+                    PRINTF("      * <CLEANUP> rerror : %d (%d)\n",(uint32_t)p_vci_ini_c.rerror.read(),0x2 & ( (1 << vci_param::E) - 1));
+
+                    ASSERT(p_vci_ini_c.reop and (p_vci_ini_c.rtrdid.read() == TYPE_INS_CLEANUP),
+                           "illegal response packet received for a cleanup transaction");
+                    ASSERT(p_vci_ini_c.rerror.read() == vci_param::ERR_NORMAL, 
+                           "error signaled in a cleanup response" );
+                    
+                    r_cleanup_fsm = CLEANUP_IDLE;
+                    r_icache_cleanup_req = false;
+                    // m_cpt_cc_cleanup_ins++; TODO
+                }
+                break;
+            }
+        } // end switch r_cleanup_fsm    
 
         ////////////////////////////////////////////////////////////////////////////
@@ -1427,14 +2163,18 @@
         // - r_vci_cmd_max
         // - r_vci_cmd_cpt
-        // - wbuf reset
+        // - wbuf (reset)
+        // - r_icache_miss_req (reset)
+        // - r_icache_unc_req (reset)
+        // - r_dcache_miss_req (reset)
+        // - r_dcache_sc_req (reset)
         //
         // This FSM handles requests from both the DCACHE FSM & the ICACHE FSM.
         // There is 7 request types, with the following priorities : 
-        // 1 - Instruction Miss     : r_icache_miss_req
-        // 2 - Data Write           : r_dcache_write_req
-        // 3 - Data Read Miss       : r_dcache_miss_req 
-        // 4 - Data Read Uncached   : r_dcache_unc_req 
-        // 5 - Instruction Cleanup  : r_icache_cleanup_req 
-        // 6 - Data Cleanup         : r_dcache_cleanup_req 
+        // 1 - Data Read Miss         : r_dcache_miss_req and miss in the write buffer
+        // 2 - Data Read Uncachable   : r_dcache_unc_req  and miss in the write buffer
+        // 3 - Instruction Miss       : r_icache_miss_req and miss in the write buffer
+        // 4 - Instruction Uncachable : r_icache_unc_req  and miss in the write buffer
+        // 5 - Data Write             : r_wbuf.rok()      
+        // 6 - Data Store Conditionnal: r_dcache_sc_req
         // There is at most one (CMD/RSP) VCI transaction, as both CMD_FSM 
         // and RSP_FSM exit simultaneously the IDLE state.
@@ -1447,40 +2187,95 @@
         //////////////////////////////////////////////////////////////////////////////
 
+        r_vci_cmd_dcache_prior = not r_vci_cmd_dcache_prior;
+
         switch (r_vci_cmd_fsm) {
 
             case CMD_IDLE:
-                if (r_vci_rsp_fsm != RSP_IDLE) break;
+                {
+                // if (r_vci_rsp_fsm != RSP_IDLE) break;
+
+                size_t	min;
+                size_t	max;
 
                 r_vci_cmd_cpt = 0;
-                if ( r_icache_cleanup_req ) { 
-                    r_vci_cmd_fsm = CMD_INS_CLEANUP; 
-                } else if ( r_dcache_cleanup_req ) { 
-                    r_vci_cmd_fsm = CMD_DATA_CLEANUP;
-                } else if ( r_icache_miss_req ) { 
+
+                // Requests :
+
+                // multi_write_buffer access is conditionnal with dcache_miss_req and icache_miss_req
+
+#if   (CC_XCACHE_WRAPPER_VCI_CMD_PRIORITY==1)
+                //  1) two access authorized
+                bool dcache_miss_req =  r_dcache_miss_req;
+                bool icache_miss_req =  r_icache_miss_req;
+#elif (CC_XCACHE_WRAPPER_VCI_CMD_PRIORITY==2)
+                //  2) one access with static priority (dcache prior)
+                bool dcache_miss_req = r_dcache_miss_req; // dcache prior
+                bool icache_miss_req = not dcache_miss_req and r_icache_miss_req;
+#elif (CC_XCACHE_WRAPPER_VCI_CMD_PRIORITY==3)
+                //  3) one access with static priority (icache prior)
+                bool icache_miss_req = r_icache_miss_req;
+                bool dcache_miss_req = not icache_miss_req and r_dcache_miss_req; // dcache prior
+#elif (CC_XCACHE_WRAPPER_VCI_CMD_PRIORITY==4)
+                //  4) one access with round robin priority
+                bool dcache_miss_req = ((r_dcache_miss_req and not r_icache_miss_req) or // only dcache
+                                        (r_dcache_miss_req and r_vci_cmd_dcache_prior)); // dcache prior
+                bool icache_miss_req = not dcache_miss_req and r_icache_miss_req;
+#else
+#error "Invalid value to CC_XCACHE_WRAPPER_VCI_CMD_PRIORITY"
+#endif
+                // 1 - Data Read
+                if (dcache_miss_req and r_wbuf.miss(r_dcache_addr_save))
+                { 
+                    r_vci_cmd_fsm = CMD_DATA_MISS;
+                    r_dcache_miss_req = false;
+                    m_cpt_dmiss_transaction++; 
+                } 
+
+                // 2 - Data Read Uncachable
+                else if ( r_dcache_unc_req )
+                { 
+                    r_vci_cmd_fsm = CMD_DATA_UNC;
+                    r_dcache_unc_req = false;
+                 // m_cpt_data_unc_transaction++; 
+                }
+
+                // 3 - Instruction Miss
+                else if (icache_miss_req and r_wbuf.miss(r_icache_addr_save))
+                { 
                     r_vci_cmd_fsm = CMD_INS_MISS; 
+                    r_icache_miss_req = false;
                     m_cpt_imiss_transaction++;
-                } else if ( r_icache_unc_req ) { 
+                } 
+
+                // 4 - Instruction Uncachable
+                else if ( r_icache_unc_req )
+                { 
                     r_vci_cmd_fsm = CMD_INS_UNC; 
-                    m_cpt_imiss_transaction++;
-                } else if ( r_dcache_write_req ) { 
+                    r_icache_unc_req = false;
+                 // m_cpt_ins_unc_transaction++;
+                }
+
+                // 5 - Data Write
+                else if ( r_wbuf.rok(&min, &max) ) 
+                { 
                     r_vci_cmd_fsm = CMD_DATA_WRITE;
-                    r_vci_cmd_cpt = r_wbuf.getMin();
-                    r_vci_cmd_min = r_wbuf.getMin();
-                    r_vci_cmd_max = r_wbuf.getMax(); 
-                    m_cpt_write_transaction++; 
-                    m_length_write_transaction += (r_wbuf.getMax() - r_wbuf.getMin() + 1); 
-                } else if ( r_dcache_miss_req ) { 
-                    r_vci_cmd_fsm = CMD_DATA_MISS;
-                    m_cpt_dmiss_transaction++; 
-                } else if ( r_dcache_unc_req ) { 
-                    r_vci_cmd_fsm = CMD_DATA_UNC;
-                    m_cpt_unc_transaction++; 
-                } else if ( r_dcache_sc_req ) { 
+                    r_vci_cmd_cpt = min;
+                    r_vci_cmd_min = min;
+                    r_vci_cmd_max = max;
+                    m_cpt_data_write_transaction++; 
+                    m_length_write_transaction += (max-min+1); 
+                } 
+
+                // 6 - Data Store Conditionnal
+                else if ( r_dcache_sc_req ) 
+                { 
                     r_vci_cmd_fsm = CMD_DATA_SC;
                     r_vci_cmd_max = 1; 
                     m_cpt_unc_transaction++; 
-                }
-                break;
-
+                    r_dcache_sc_req = false;
+                }
+
+                break;
+                }
             case CMD_DATA_WRITE:
                 if ( p_vci_ini_rw.cmdack.read() ) {
@@ -1488,5 +2283,5 @@
                     if (r_vci_cmd_cpt == r_vci_cmd_max) {
                         r_vci_cmd_fsm = CMD_IDLE ;
-                        r_wbuf.reset() ;
+                        r_wbuf.sent() ;
                     }
                 }
@@ -1509,10 +2304,4 @@
                 }
                 break;
-            case CMD_INS_CLEANUP:
-            case CMD_DATA_CLEANUP:
-                if ( p_vci_ini_c.cmdack.read() ) {
-                    r_vci_cmd_fsm = CMD_IDLE;
-                }
-                break;
 
         } // end  switch r_vci_cmd_fsm
@@ -1523,9 +2312,4 @@
         // - r_icache_miss_buf[m_icache_words]
         // - r_dcache_miss_buf[m_dcache_words]
-        // - r_icache_miss_req reset
-        // - r_icache_unc_req reset
-        // - r_dcache_miss_req reset
-        // - r_icache_cleanup_req reset
-        // - r_dcache_cleanup_req reset
         // - r_vci_rsp_data_error set
         // - r_vci_rsp_ins_error set
@@ -1552,120 +2336,153 @@
 
             case RSP_IDLE:
-                if(p_vci_ini_rw.rspval.read()||
-                        p_vci_ini_c.rspval.read())
-                {
-                    std::cout << "CC_XCache " << m_srcid_rw << " Unexpected response" << std::endl;
-                }
-                assert( ! p_vci_ini_rw.rspval.read() && ! p_vci_ini_c.rspval.read() && "Unexpected response" );
-                if (r_vci_cmd_fsm != CMD_IDLE) break;
-
-                r_vci_rsp_cpt = 0;
-                if      ( r_icache_cleanup_req )    r_vci_rsp_fsm = RSP_INS_CLEANUP;
-                else if ( r_dcache_cleanup_req )    r_vci_rsp_fsm = RSP_DATA_CLEANUP;
-                else if ( r_icache_miss_req )       r_vci_rsp_fsm = RSP_INS_MISS;
-                else if ( r_icache_unc_req )        r_vci_rsp_fsm = RSP_INS_UNC;
-                else if ( r_dcache_write_req )      r_vci_rsp_fsm = RSP_DATA_WRITE;
-                else if ( r_dcache_miss_req )       r_vci_rsp_fsm = RSP_DATA_MISS;
-                else if ( r_dcache_unc_req )        r_vci_rsp_fsm = RSP_DATA_UNC;
-                else if ( r_dcache_sc_req )         r_vci_rsp_fsm = RSP_DATA_SC;
+
+                if( p_vci_ini_rw.rspval.read() )
+                {
+                    PRINTF("      * <RSP> have rsp - trdid : %x\n",(uint32_t)p_vci_ini_rw.rtrdid.read());
+
+                    r_vci_rsp_cpt = 0;
+
+                    if ((p_vci_ini_rw.rtrdid.read()>>(vci_param::T-1)) != 0 )
+                        r_vci_rsp_fsm = RSP_DATA_WRITE;
+                    else
+                    {
+                        switch (p_vci_ini_rw.rtrdid.read())
+                        {
+                        case TYPE_INS_MISS     : r_vci_rsp_fsm = RSP_INS_MISS;     break;
+                        case TYPE_INS_UNC      : r_vci_rsp_fsm = RSP_INS_UNC;      break;
+                        case TYPE_DATA_MISS    : r_vci_rsp_fsm = RSP_DATA_MISS;    break;
+                        case TYPE_DATA_UNC     : r_vci_rsp_fsm = RSP_DATA_UNC;     break;
+                        case TYPE_DATA_SC      : r_vci_rsp_fsm = RSP_DATA_SC;      break;
+                        default : 
+                            {
+                                ASSERT(false, "Unexpected response");
+                            }
+                        }
+                    }
+                }
                 break;
 
             case RSP_INS_MISS:
+
                 m_cost_imiss_transaction++;
-                if ( ! p_vci_ini_rw.rspval.read() )
-                    break;
-                assert( (r_vci_rsp_cpt < m_icache_words) &&
-                        "The VCI response packet for instruction miss is too long" );
-                r_vci_rsp_cpt = r_vci_rsp_cpt + 1;
-                r_icache_miss_buf[r_vci_rsp_cpt] = (data_t)p_vci_ini_rw.rdata.read();
-
-                if ( p_vci_ini_rw.reop.read() ) {
-                    assert( ((r_vci_rsp_cpt == m_icache_words - 1) ||
-                             p_vci_ini_rw.rerror.read() ||
-                             (r_vci_rsp_ins_error.read()&0x1))&&
-                            "The VCI response packet for instruction miss is too short");
-                    r_icache_miss_req = false;
+                PRINTF("      * <RSP> rspval/ack : %d - %d\n",(uint32_t)p_vci_ini_rw.rspval.read(), (uint32_t)r_vci_rsp_ack);
+
+                if (p_vci_ini_rw.rspval.read() and r_vci_rsp_ack)
+                {
+                    PRINTF("      * <RSP> have rsp - r_vci_rsp_cpt : %d/%d\n",(uint32_t)r_vci_rsp_cpt.read(),(uint32_t)m_icache_words);
+                    PRINTF("      * <RSP> ins : %x\n",(int)p_vci_ini_rw.rdata.read());
+
+                    ASSERT( (r_vci_rsp_cpt < m_icache_words),
+                            "The VCI response packet for instruction miss is too long" );
+                    r_vci_rsp_cpt = r_vci_rsp_cpt + 1;
+                    CACHE_MISS_BUF_RSP_PUSH(i,r_vci_rsp_cpt,(data_t)p_vci_ini_rw.rdata.read());
+                    if ( p_vci_ini_rw.reop.read() ) 
+                    {
+                        PRINTF("      * <RSP> have reop\n");
+
+                        ASSERT( ((r_vci_rsp_cpt == m_icache_words - 1) or
+                                 p_vci_ini_rw.rerror.read() or
+                                 (r_vci_rsp_ins_error.read()&0x1)),
+                                "The VCI response packet for instruction miss is too short");
+                        r_vci_rsp_cpt    = 0;
+                        r_vci_rsp_fsm    = RSP_IDLE;
+
+                    }
+                    if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_ins_error = true;
+                }
+                break;
+
+            case RSP_INS_UNC:
+
+                m_cost_imiss_transaction++;
+                if (p_vci_ini_rw.rspval.read() and r_vci_rsp_ack)
+                {
+                    ASSERT(p_vci_ini_rw.reop.read(),
+                           "illegal VCI response packet for uncached instruction");
+
+                    CACHE_MISS_BUF_RSP_PUSH(i,0,(data_t)p_vci_ini_rw.rdata.read());
+
                     r_vci_rsp_fsm = RSP_IDLE;
-                }
-                if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_ins_error = true;
-                break;
-
-            case RSP_INS_UNC:
-                m_cost_imiss_transaction++;
-                if ( ! p_vci_ini_rw.rspval.read() )
-                    break;
-                assert(p_vci_ini_rw.reop.read() &&
-                        "illegal VCI response packet for uncached instruction");
-                r_icache_miss_buf[0] = (data_t)p_vci_ini_rw.rdata.read();
-                r_vci_rsp_fsm = RSP_IDLE;
-                r_icache_unc_req = false;
-                if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_ins_error = true;
+
+                    if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_ins_error = true;
+                }
                 break;
 
             case RSP_DATA_MISS:
+
                 m_cost_dmiss_transaction++;
-                if ( ! p_vci_ini_rw.rspval.read() )
-                    break;
-                assert(r_vci_rsp_cpt != m_dcache_words &&
-                        "illegal VCI response packet for data read miss");
-                r_vci_rsp_cpt = r_vci_rsp_cpt + 1;
-                r_dcache_miss_buf[r_vci_rsp_cpt] = (data_t)p_vci_ini_rw.rdata.read();
-                if ( p_vci_ini_rw.reop.read() ) {
-                    assert( ((r_vci_rsp_cpt == m_dcache_words - 1) 
-                             || (p_vci_ini_rw.rerror.read()&0x1)
-                             || r_vci_rsp_data_error.read()) &&
-                            "illegal VCI response packet for data read miss");
-                    r_dcache_miss_req = false;
+                if (p_vci_ini_rw.rspval.read() and r_vci_rsp_ack)
+                {
+                    PRINTF("      * <RSP> have rspval - error : %d\n",(int)p_vci_ini_rw.rerror.read());
+
+                    ASSERT(r_vci_rsp_cpt < m_dcache_words,
+                           "illegal VCI response packet for data read miss");
+                    r_vci_rsp_cpt = r_vci_rsp_cpt + 1;
+
+                    CACHE_MISS_BUF_RSP_PUSH(d,r_vci_rsp_cpt,(data_t)p_vci_ini_rw.rdata.read());
+
+                    if ( p_vci_ini_rw.reop.read() ) {
+                        ASSERT( ((r_vci_rsp_cpt == m_dcache_words - 1) 
+                                 or (p_vci_ini_rw.rerror.read()&0x1)
+                                 or r_vci_rsp_data_error.read()),
+                                "illegal VCI response packet for data read miss");
+                        r_vci_rsp_cpt     = 0;
+                        r_vci_rsp_fsm     = RSP_IDLE;
+                    }
+                    if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_data_error = true;
+                }
+                break;
+
+            case RSP_DATA_WRITE:
+
+                m_cost_write_transaction++;
+                if (p_vci_ini_rw.rspval.read())
+                {
+                    PRINTF("      * <RSP> have rspval - error : %d\n",(int)p_vci_ini_rw.rerror.read());
+
+                    ASSERT(p_vci_ini_rw.reop.read(),
+                           "A VCI response packet must contain one flit for a write transaction");
                     r_vci_rsp_fsm = RSP_IDLE;
-                }
-                if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_data_error = true;
-                break;
-
-            case RSP_DATA_WRITE:
-                m_cost_write_transaction++;
-                if ( ! p_vci_ini_rw.rspval.read() )
-                    break;
-                if ( p_vci_ini_rw.reop.read() ) {
-                    r_vci_rsp_fsm = RSP_IDLE;
-                    r_dcache_write_req = false;
-                }
-                if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) m_iss.setWriteBerr();
+                    bool cached = r_wbuf.completed(p_vci_ini_rw.rtrdid.read() - (1<<(vci_param::T-1)) );
+
+                    PRINTF("      * <RSP> cached : %d\n",cached);
+
+                    if (not cached)
+                        r_dcache_previous_unc = false;
+
+                    if ((p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL) m_iss.setWriteBerr();
+                }
                 break;
 
             case RSP_DATA_UNC:
                 m_cost_unc_transaction++;
-                if ( ! p_vci_ini_rw.rspval.read() )
-                    break;
-                assert(p_vci_ini_rw.reop.read() &&
-                        "illegal VCI response packet for data read uncached");
-                r_dcache_miss_buf[0] = (data_t)p_vci_ini_rw.rdata.read();
-                r_vci_rsp_fsm = RSP_IDLE;
-                r_dcache_unc_req = false;
-                if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_data_error = true;
+                if (p_vci_ini_rw.rspval.read() and r_vci_rsp_ack)
+                {
+                    ASSERT(p_vci_ini_rw.reop.read(),
+                           "illegal VCI response packet for data read uncached");
+
+                    CACHE_MISS_BUF_RSP_PUSH(d,0,(data_t)p_vci_ini_rw.rdata.read());
+
+                    r_vci_rsp_fsm = RSP_IDLE;
+                    r_dcache_previous_unc = false;
+
+                    if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_data_error = true;
+                }
                 break;
 
             case RSP_DATA_SC:
                 m_cost_unc_transaction++;
-                if ( ! p_vci_ini_rw.rspval.read() )
-                    break;
-                assert(p_vci_ini_rw.reop.read() &&
-                        "illegal VCI response packet for data SC");
-                r_dcache_miss_buf[0] = (data_t)p_vci_ini_rw.rdata.read();
-                r_vci_rsp_fsm = RSP_IDLE;
-                r_dcache_sc_req = false;
-                if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_data_error = true;
-                break;
-
-            case RSP_INS_CLEANUP:
-            case RSP_DATA_CLEANUP:
-                if ( ! p_vci_ini_c.rspval.read() )
-                    break;
-                assert( p_vci_ini_c.reop.read() &&
-                        "illegal VCI response packet for icache cleanup");
-                assert( ((p_vci_ini_c.rerror.read()&0x1) == vci_param::ERR_NORMAL) &&
-                        "error in response packet for icache cleanup");
-                if ( r_vci_rsp_fsm == RSP_INS_CLEANUP ) r_icache_cleanup_req = false;
-                else                                    r_dcache_cleanup_req = false;
-                r_vci_rsp_fsm = RSP_IDLE;
+                if (p_vci_ini_rw.rspval.read() and r_vci_rsp_ack)
+                {
+                    ASSERT(p_vci_ini_rw.reop.read(),
+                           "illegal VCI response packet for data SC");
+
+                    CACHE_MISS_BUF_RSP_PUSH(d,0,(data_t)p_vci_ini_rw.rdata.read());
+
+                    r_vci_rsp_fsm = RSP_IDLE;
+                    r_dcache_previous_unc = false;
+
+                    if ( (p_vci_ini_rw.rerror.read()&0x1) != vci_param::ERR_NORMAL ) r_vci_rsp_data_error = true;
+                }
                 break;
 
@@ -1678,8 +2495,73 @@
     //////////////////////////////////////////////////////////////////////////////////
     {
+
         // VCI initiator response
-
-        p_vci_ini_rw.rspack = true;
-        p_vci_ini_c.rspack = true;
+        switch ( r_cleanup_fsm.read() ) {
+
+            case CLEANUP_IDLE:
+                p_vci_ini_c.rspack  = false;
+                p_vci_ini_c.cmdval  = r_icache_cleanup_req || r_dcache_cleanup_req;
+                if ( r_dcache_cleanup_req )
+                {
+                    p_vci_ini_c.address =  r_dcache_cleanup_line.read() * (m_dcache_words << 2);
+                    p_vci_ini_c.trdid   = TYPE_DATA_CLEANUP;
+                }
+                else
+                {
+                    p_vci_ini_c.address =  r_icache_cleanup_line.read() * (m_icache_words << 2); 
+                    p_vci_ini_c.trdid   = TYPE_INS_CLEANUP;
+                }
+                p_vci_ini_c.wdata  = 0;
+                p_vci_ini_c.be     = 0xF;
+                p_vci_ini_c.plen   = 4;
+                p_vci_ini_c.cmd    = vci_param::CMD_WRITE;
+                p_vci_ini_c.pktid  = 0;
+                p_vci_ini_c.srcid  = m_srcid_c;
+                p_vci_ini_c.cons   = false;
+                p_vci_ini_c.wrap   = false;
+                p_vci_ini_c.contig = false;
+                p_vci_ini_c.clen   = 0;
+                p_vci_ini_c.cfixed = false;
+                p_vci_ini_c.eop    = true;
+                break;
+
+           case CLEANUP_DCACHE:
+                p_vci_ini_c.rspack  = true;
+                p_vci_ini_c.cmdval  = false;
+                p_vci_ini_c.address = 0;
+                p_vci_ini_c.wdata  = 0;
+                p_vci_ini_c.be     = 0;
+                p_vci_ini_c.plen   = 0;
+                p_vci_ini_c.cmd    = vci_param::CMD_WRITE;
+                p_vci_ini_c.trdid  = 0; 
+                p_vci_ini_c.pktid  = 0;
+                p_vci_ini_c.srcid  = 0;
+                p_vci_ini_c.cons   = false;
+                p_vci_ini_c.wrap   = false;
+                p_vci_ini_c.contig = false;
+                p_vci_ini_c.clen   = 0;
+                p_vci_ini_c.cfixed = false;
+                p_vci_ini_c.eop = false;
+                break;
+
+           case CLEANUP_ICACHE:
+                p_vci_ini_c.rspack  = true;
+                p_vci_ini_c.cmdval  = false;
+                p_vci_ini_c.address = 0;
+                p_vci_ini_c.wdata  = 0;
+                p_vci_ini_c.be     = 0;
+                p_vci_ini_c.plen   = 0;
+                p_vci_ini_c.cmd    = vci_param::CMD_WRITE;
+                p_vci_ini_c.trdid  = 0; 
+                p_vci_ini_c.pktid  = 0;
+                p_vci_ini_c.srcid  = 0;
+                p_vci_ini_c.cons   = false;
+                p_vci_ini_c.wrap   = false;
+                p_vci_ini_c.contig = false;
+                p_vci_ini_c.clen   = 0;
+                p_vci_ini_c.cfixed = false;
+                p_vci_ini_c.eop = false;
+                break;
+           } // end switch r_cleanup_fsm
 
         // VCI initiator command
@@ -1704,20 +2586,4 @@
                 p_vci_ini_rw.eop     = false;
 
-                p_vci_ini_c.cmdval  = false;
-                p_vci_ini_c.address = 0;
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 0;
-                p_vci_ini_c.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_c.trdid  = 0;
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = 0;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = false;
-
                 break;
 
@@ -1737,8 +2603,8 @@
                         break;
                     default:
-                        assert("this should not happen");
+                        ASSERT(false,"this should not happen");
                 }
                 p_vci_ini_rw.plen = 4;
-                p_vci_ini_rw.trdid  = 0;   // data cache uncached read
+                p_vci_ini_rw.trdid  = TYPE_DATA_UNC;   // data cache uncached read
                 p_vci_ini_rw.pktid  = 0;
                 p_vci_ini_rw.srcid  = m_srcid_rw;
@@ -1750,20 +2616,4 @@
                 p_vci_ini_rw.eop    = true;
 
-                p_vci_ini_c.cmdval  = false;
-                p_vci_ini_c.address = 0;
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 0;
-                p_vci_ini_c.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_c.trdid  = 0;
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = 0;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = false;
-
                 break;
 
@@ -1772,5 +2622,5 @@
                 p_vci_ini_rw.address = (addr_40) r_dcache_addr_save.read() & ~0x3;
                 if(r_vci_cmd_max.read() == 3){
-                    assert(false && "Not handled yet");
+                    ASSERT(false, "Not handled yet");
                 } else { // r_vci_cmd_cpt == 1
                     switch(r_vci_cmd_cpt.read()){
@@ -1786,5 +2636,5 @@
                 p_vci_ini_rw.cmd    = vci_param::CMD_STORE_COND;
                 p_vci_ini_rw.plen   = 4*(r_vci_cmd_max.read()+1);
-                p_vci_ini_rw.trdid  = 0;   // data cache uncached read
+                p_vci_ini_rw.trdid  = TYPE_DATA_SC;   // data cache uncached read
                 p_vci_ini_rw.pktid  = 0;
                 p_vci_ini_rw.srcid  = m_srcid_rw;
@@ -1796,20 +2646,4 @@
                 p_vci_ini_rw.eop    = (r_vci_cmd_cpt.read() == r_vci_cmd_max.read());
 
-                p_vci_ini_c.cmdval  = false;
-                p_vci_ini_c.address = 0;
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 0;
-                p_vci_ini_c.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_c.trdid  = 0;
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = 0;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = false;
-
                 break;
 
@@ -1821,5 +2655,5 @@
                 p_vci_ini_rw.plen    = (r_vci_cmd_max - r_vci_cmd_min + 1)<<2;
                 p_vci_ini_rw.cmd     = vci_param::CMD_WRITE;
-                p_vci_ini_rw.trdid   = 0;  // data cache write
+                p_vci_ini_rw.trdid   = r_wbuf.getIndex() + (1<<(vci_param::T-1));
                 p_vci_ini_rw.pktid   = 0;
                 p_vci_ini_rw.srcid   = m_srcid_rw;
@@ -1831,20 +2665,4 @@
                 p_vci_ini_rw.eop     = (r_vci_cmd_cpt == r_vci_cmd_max);
 
-                p_vci_ini_c.cmdval  = false;
-                p_vci_ini_c.address = 0;
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 0;
-                p_vci_ini_c.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_c.trdid  = 0;
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = 0;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = false;
-
                 break;
 
@@ -1855,5 +2673,5 @@
                 p_vci_ini_rw.plen   = m_dcache_words << 2;
                 p_vci_ini_rw.cmd    = vci_param::CMD_READ;
-                p_vci_ini_rw.trdid  = 1;   // data cache cached read
+                p_vci_ini_rw.trdid  = TYPE_DATA_MISS;   // data cache cached read
                 p_vci_ini_rw.pktid  = 0;
                 p_vci_ini_rw.srcid  = m_srcid_rw;
@@ -1865,20 +2683,4 @@
                 p_vci_ini_rw.eop = true;
 
-                p_vci_ini_c.cmdval  = false;
-                p_vci_ini_c.address = 0;
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 0;
-                p_vci_ini_c.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_c.trdid  = 0;
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = 0;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = false;
-
                 break;
 
@@ -1889,5 +2691,5 @@
                 p_vci_ini_rw.plen   = m_icache_words << 2;
                 p_vci_ini_rw.cmd    = vci_param::CMD_READ;
-                p_vci_ini_rw.trdid  = 3;   // ins cache cached read
+                p_vci_ini_rw.trdid  = TYPE_INS_MISS;   // ins cache cached read
                 p_vci_ini_rw.pktid  = 0;
                 p_vci_ini_rw.srcid  = m_srcid_rw;
@@ -1899,20 +2701,4 @@
                 p_vci_ini_rw.eop = true;
 
-                p_vci_ini_c.cmdval  = false;
-                p_vci_ini_c.address = 0;
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 0;
-                p_vci_ini_c.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_c.trdid  = 0;
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = 0;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = false;
-
                 break;
 
@@ -1923,5 +2709,5 @@
                 p_vci_ini_rw.plen   = 4;
                 p_vci_ini_rw.cmd    = vci_param::CMD_READ;
-                p_vci_ini_rw.trdid  = 2;   // ins cache uncached read
+                p_vci_ini_rw.trdid  = TYPE_INS_UNC;   // ins cache uncached read
                 p_vci_ini_rw.pktid  = 0;
                 p_vci_ini_rw.srcid  = m_srcid_rw;
@@ -1933,96 +2719,23 @@
                 p_vci_ini_rw.eop = true;
 
-                p_vci_ini_c.cmdval  = false;
-                p_vci_ini_c.address = 0;
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 0;
-                p_vci_ini_c.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_c.trdid  = 0;
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = 0;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = false;
-
-
-                break;
-
-            case CMD_INS_CLEANUP:
-                p_vci_ini_rw.cmdval = false;
-                p_vci_ini_rw.address = 0;
-                p_vci_ini_rw.wdata  = 0;
-                p_vci_ini_rw.be     = 0;
-                p_vci_ini_rw.plen   = 0;
-                p_vci_ini_rw.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_rw.trdid  = 0;
-                p_vci_ini_rw.pktid  = 0;
-                p_vci_ini_rw.srcid  = 0;
-                p_vci_ini_rw.cons   = false;
-                p_vci_ini_rw.wrap   = false;
-                p_vci_ini_rw.contig = false;
-                p_vci_ini_rw.clen   = 0;
-                p_vci_ini_rw.cfixed = false;
-                p_vci_ini_rw.eop    = false;
-
-                p_vci_ini_c.cmdval  = true;
-                p_vci_ini_c.address = r_icache_cleanup_line.read() * (m_icache_words<<2);
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 4;
-                p_vci_ini_c.cmd    = vci_param::CMD_WRITE;
-                p_vci_ini_c.trdid  = 1; // cleanup instruction
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = m_srcid_c;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = true;
-
-                break;
-
-
-            case CMD_DATA_CLEANUP:
-                p_vci_ini_rw.cmdval = false;
-                p_vci_ini_rw.address = 0;
-                p_vci_ini_rw.wdata  = 0;
-                p_vci_ini_rw.be     = 0;
-                p_vci_ini_rw.plen   = 0;
-                p_vci_ini_rw.cmd    = vci_param::CMD_NOP;
-                p_vci_ini_rw.trdid  = 0;
-                p_vci_ini_rw.pktid  = 0;
-                p_vci_ini_rw.srcid  = 0;
-                p_vci_ini_rw.cons   = false;
-                p_vci_ini_rw.wrap   = false;
-                p_vci_ini_rw.contig = false;
-                p_vci_ini_rw.clen   = 0;
-                p_vci_ini_rw.cfixed = false;
-                p_vci_ini_rw.eop    = false;
-
-                p_vci_ini_c.cmdval  = true;
-                p_vci_ini_c.address = r_dcache_cleanup_line.read() * (m_dcache_words<<2);
-                p_vci_ini_c.wdata  = 0;
-                p_vci_ini_c.be     = 0;
-                p_vci_ini_c.plen   = 4;
-                p_vci_ini_c.cmd    = vci_param::CMD_WRITE;
-                p_vci_ini_c.trdid  = 0; // cleanup data
-                p_vci_ini_c.pktid  = 0;
-                p_vci_ini_c.srcid  = m_srcid_c;
-                p_vci_ini_c.cons   = false;
-                p_vci_ini_c.wrap   = false;
-                p_vci_ini_c.contig = false;
-                p_vci_ini_c.clen   = 0;
-                p_vci_ini_c.cfixed = false;
-                p_vci_ini_c.eop = true;
-
                 break;
 
         } // end switch r_vci_cmd_fsm
 
+        bool ack;
+
+        switch (r_vci_rsp_fsm.read() ) {
+        case RSP_IDLE       : ack = false; break;
+        case RSP_DATA_WRITE : ack = true; break;
+        case RSP_INS_MISS   :
+        case RSP_INS_UNC    : ack = CACHE_MISS_BUF_RSP_ACK(i); break;
+        case RSP_DATA_MISS  :
+        case RSP_DATA_UNC   :
+        case RSP_DATA_SC    : ack = CACHE_MISS_BUF_RSP_ACK(d); break;
+        } // end switch r_vci_cmd_fsm
+
+        r_vci_rsp_ack       = ack;
+        p_vci_ini_rw.rspack = ack;
+        
         // VCI_TGT
 
@@ -2038,5 +2751,5 @@
             case TGT_RSP_BROADCAST:
                 p_vci_tgt.cmdack  = false;
-                p_vci_tgt.rspval  = !r_tgt_icache_req.read() && !r_tgt_dcache_req.read() && ( r_tgt_icache_rsp | r_tgt_dcache_rsp );
+                p_vci_tgt.rspval  = not r_tgt_icache_req.read() and not r_tgt_dcache_req.read() and ( r_tgt_icache_rsp | r_tgt_dcache_rsp );
                 p_vci_tgt.rsrcid  = r_tgt_srcid.read();
                 p_vci_tgt.rpktid  = r_tgt_pktid.read();
@@ -2049,5 +2762,5 @@
             case TGT_RSP_ICACHE:
                 p_vci_tgt.cmdack  = false;
-                p_vci_tgt.rspval  = !r_tgt_icache_req.read() && r_tgt_icache_rsp.read();
+                p_vci_tgt.rspval  = not r_tgt_icache_req.read() and r_tgt_icache_rsp.read();
                 p_vci_tgt.rsrcid  = r_tgt_srcid.read();
                 p_vci_tgt.rpktid  = r_tgt_pktid.read();
@@ -2060,5 +2773,5 @@
             case TGT_RSP_DCACHE:
                 p_vci_tgt.cmdack  = false;
-                p_vci_tgt.rspval  = !r_tgt_dcache_req.read() && r_tgt_dcache_rsp.read();
+                p_vci_tgt.rspval  = not r_tgt_dcache_req.read() and r_tgt_dcache_rsp.read();
                 p_vci_tgt.rsrcid  = r_tgt_srcid.read();
                 p_vci_tgt.rpktid  = r_tgt_pktid.read();
@@ -2079,4 +2792,26 @@
     } // end genMoore()
 
+    //////////////////////////////////////////////////////////////////////////////////
+    tmpl(void)::stop_simulation (uint32_t nb_frz_cycles)
+    //////////////////////////////////////////////////////////////////////////////////
+    {
+#if CC_XCACHE_WRAPPER_STOP_SIMULATION
+        if (nb_frz_cycles == 0)
+            {
+                PRINTF("CC_XCACHE_WRAPPER \"%s\" : don't stop the simulation.\n",name().c_str());
+                m_stop_simulation = false;
+            }
+        else
+            {
+                PRINTF("CC_XCACHE_WRAPPER \"%s\" : stop the simulation after %d cycles.\n",name().c_str(),nb_frz_cycles);
+                m_stop_simulation = true;
+                m_stop_simulation_nb_frz_cycles_max = nb_frz_cycles;
+            }
+#else
+        std::cout << "CC_XCACHE_WRAPPER \"" << name() << "\" : flag CC_XCACHE_WRAPPER_STOP_SIMULATION is unset, you can't use stop_simulation." << std::endl;
+#endif // CC_XCACHE_WRAPPER_STOP_SIMULATION
+        
+    }
+
 }} // end namespace
 
@@ -2089,6 +2824,2 @@
 
 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
-
-
-
-
Index: /trunk/modules/vci_mem_cache_v4/caba/source/src/vci_mem_cache_v4.cpp
===================================================================
--- /trunk/modules/vci_mem_cache_v4/caba/source/src/vci_mem_cache_v4.cpp	(revision 133)
+++ /trunk/modules/vci_mem_cache_v4/caba/source/src/vci_mem_cache_v4.cpp	(revision 134)
@@ -33,7 +33,14 @@
 //#define DDEBUG // Directory debug
 //#define LOCK_DEBUG // Lock debug
-//#define DEBUG_VCI_MEM_CACHE 1
-#define DEBUG_START_CYCLE 8750000
+#define DEBUG_VCI_MEM_CACHE 0
+#define DEBUG_START_CYCLE   200000
 #define RANDOMIZE_SC
+
+#if DEBUG_VCI_MEM_CACHE
+# define PRINTF(msg...) do { if (m_cpt_cycles > DEBUG_START_CYCLE) printf(msg); } while (0); 
+#else
+# define PRINTF(msg...)
+#endif
+
 namespace soclib { namespace caba {
 
@@ -641,4 +648,7 @@
         {
           if ( p_vci_tgt.cmdval ) {
+
+              PRINTF("  * <TGT> Request from %d at address %llx\n",(uint32_t)p_vci_tgt.srcid.read(),(uint64_t)p_vci_tgt.address.read());
+
             assert( (p_vci_tgt.srcid.read() < m_initiators) && 
             "VCI_MEM_CACHE error in direct request : received SRCID is larger than the number of initiators");
@@ -653,5 +663,4 @@
               }
             }
-
 
             if ( !reached ) 
@@ -666,5 +675,6 @@
               r_tgt_cmd_fsm = TGT_CMD_READ;
             } 
-            else if (( p_vci_tgt.cmd.read() == vci_param::CMD_WRITE ) && ( p_vci_tgt.trdid.read() == 0x0 ))
+            // else if (( p_vci_tgt.cmd.read() == vci_param::CMD_WRITE ) && ( p_vci_tgt.trdid.read() == 0x0 ))
+            else if ( p_vci_tgt.cmd.read() == vci_param::CMD_WRITE )
             {  
               r_tgt_cmd_fsm = TGT_CMD_WRITE;
@@ -838,4 +848,6 @@
     ////////////////////////////////////////////////////////////////////////////////////
 
+    PRINTF("  * TOP : Request from %d at address %llx\n",(uint32_t)m_cmd_read_srcid_fifo.read(),(uint64_t)m_cmd_read_addr_fifo.read());
+
     switch ( r_read_fsm.read() ) {
 
@@ -844,4 +856,6 @@
         {
           if (m_cmd_read_addr_fifo.rok()) {
+            PRINTF("  * <READ> Request from %d at address %llx\n",(uint32_t)m_cmd_read_srcid_fifo.read(),(uint64_t)m_cmd_read_addr_fifo.read());
+
             m_cpt_read++;
             r_read_fsm = READ_DIR_LOCK;
@@ -2591,5 +2605,5 @@
             hit_inval = m_update_tab.search_inval(r_cleanup_nline.read(),index);
             if(!hit_inval) {
-#ifdef DEBUG_VCI_MEM_CACHE
+#if DEBUG_VCI_MEM_CACHE
 if(m_cpt_cycles > DEBUG_START_CYCLE)
               std::cout << "MEM_CACHE WARNING: cleanup with no corresponding entry at address : " << std::hex << (r_cleanup_nline.read()*4*m_words) << std::dec << std::endl;
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/Makefile
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/Makefile	(revision 133)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/Makefile	(revision 134)
@@ -1,6 +1,9 @@
-ARCH=mips32el
-SIMULATION_ARGS=100000
-SOCLIB?=$(shell soclib-cc --getpath)
-SOCLIB_CC_ADD_ARGS= -t systemcass
+#NO_SOFT		=  1
+ARCH			=  mips32el
+#SIMULATION_ARGS	=  100000
+#SOCLIB_CC_ADD_ARGS	= "-DCC_XCACHE_WRAPPER_DEBUG=1"
+SOCLIB			?= $(shell soclib-cc --getpath)
 export SOCLIB
+SOCLIB_TTY		= FILES;
+export SOCLIB_TTY
 include $(SOCLIB)/soclib/platform/topcells/all.mk
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/configuration/default.cfg
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/configuration/default.cfg	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/configuration/default.cfg	(revision 134)
@@ -0,0 +1,5 @@
+4
+4 64 16
+4 64 16
+8 8 16
+16 256 16 4096
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/configuration/gen_config.sh
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/configuration/gen_config.sh	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/configuration/gen_config.sh	(revision 134)
@@ -0,0 +1,78 @@
+#!/bin/bash
+
+#               archi1  archi2  archi3  archi4
+archi_name=(    "00512" "16384" "01024" "02048");
+iways=(         "1"     "4"     "16"    "4"    );
+isets=(         "8"     "64"    "1"     "8"    );
+iwords=(        "16"    "16"    "16"    "16"   );
+dways=(         "1"     "4"     "16"    "4"    );
+dsets=(         "8"     "64"    "1"     "8"    );
+dwords=(        "16"    "16"    "16"    "16"   );
+memc_nways=(    "4"     "16"    "8"     "2"    );
+memc_nsets=(    "4"     "256"   "64"    "32"   );
+memc_words=(    "16"    "16"    "16"    "16"   );
+memc_heap_size=("4096"  "4096"  "4096"  "4096" );
+
+nb_proc=( "1" "15" "+1" "4");
+wnwords=( "1" "16" "*2" "8");
+wnlines=( "1" "8"  "*2" "8");
+wtimeout=("1" "1024" "*4" "16");
+
+archi_default="1";
+
+function gen_file ()
+{
+        filename=$(printf "x%.2d-xcache_%s-wbuf_%.2d_%.2d_%.4d.cfg" ${1} ${archi_name[${2}]} ${3} ${4} ${5});
+
+        echo ${filename};
+
+        echo "${1}" > ${filename};
+        echo "${iways[${2}]} ${isets[${2}]} ${iwords[${2}]}" >> ${filename};
+        echo "${dways[${2}]} ${dsets[${2}]} ${dwords[${2}]}" >> ${filename};
+        echo "${3} ${4} ${5}" >> ${filename};
+        echo "${memc_nways[${2}]} ${memc_nsets[${2}]} ${memc_words[${2}]} ${memc_heap_size[${2}]}" >> ${filename};
+}
+
+function gen_default ()
+{
+        filename="default.cfg";
+        archi=${1};
+
+        echo ${filename};
+
+        echo "${nb_proc[3]}" > ${filename};
+        echo "${iways[${archi}]} ${isets[${archi}]} ${iwords[${archi}]}" >> ${filename};
+        echo "${dways[${archi}]} ${dsets[${archi}]} ${dwords[${archi}]}" >> ${filename};
+        echo "${wnwords[3]} ${wnlines[3]} ${wtimeout[3]}" >> ${filename};
+        echo "${memc_nways[${archi}]} ${memc_nsets[${archi}]} ${memc_words[${archi}]} ${memc_heap_size[${archi}]}" >> ${filename};
+}
+
+gen_default ${archi_default};
+
+nb_archi=${#iways[*]};
+
+num_archi=0;
+while test ${num_archi} -lt ${nb_archi}; do
+    num_proc=${nb_proc[0]};
+    while test ${num_proc} -le ${nb_proc[1]}; do
+        num_words=${wnwords[0]};
+        while test ${num_words} -le ${wnwords[1]}; do
+            num_lines=${wnlines[0]};
+            while test ${num_lines} -le ${wnlines[1]}; do
+                num_timeout=${wtimeout[0]};
+                while test ${num_timeout} -le ${wtimeout[1]}; do
+
+                    gen_file ${num_proc} ${num_archi} ${num_words} ${num_lines} ${num_timeout};
+
+                    num_timeout=$((${num_timeout} ${wtimeout[2]}));
+                done;
+                num_lines=$((${num_lines} ${wnlines[2]}));
+            done;
+            num_words=$((${num_words} ${wnwords[2]}));
+        done;
+        num_proc=$((${num_proc} ${nb_proc[2]}));
+    done;
+    num_archi=$((${num_archi}+1));
+done;
+
+
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/platform_desc
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/platform_desc	(revision 133)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/platform_desc	(revision 134)
@@ -4,8 +4,8 @@
 
 todo = Platform('caba', 'top.cpp',
-				uses = [
+	uses = [
 	Uses('caba:vci_cc_xcache_wrapper_v4', iss_t = 'common:gdb_iss', gdb_iss_t = 'common:mips32el'),
 	Uses('caba:vci_simple_ram'),
-  Uses('caba:vci_logger'),
+        Uses('caba:vci_simhelper'),
 	Uses('caba:vci_multi_tty'),
 	Uses('caba:vci_vgmn'),
@@ -15,4 +15,5 @@
 	Uses('caba:vci_mem_cache_v4'),
 	Uses('common:elf_file_loader'),
+        Uses('caba:vci_xicu'),
 	],
 	cell_size = 4,
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/segmentation.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/segmentation.h	(revision 133)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/segmentation.h	(revision 134)
@@ -19,6 +19,4 @@
 //      base address required by MIPS processor
 /////////////////////////////////////////////////////////////////
-#define MMU
-
 #define	RESET_BASE	0xBFC00000
 #define	RESET_SIZE	0x00010000
@@ -29,4 +27,5 @@
 #define	TEXT_BASE	0x00400000
 #define	TEXT_SIZE	0x00050000
+
 /////////////////////////////////////////////////////////////////
 //	global data segment (initialised)
@@ -34,16 +33,6 @@
 
 #define MC_M_BASE	0x10000000
-#define MC_M_SIZE	0x00100000
+#define MC_M_SIZE	0x000F0000
 
-/////////////////////////////////////////////////////////////////
-//	page table (initialised)
-/////////////////////////////////////////////////////////////////
-#define PTD_ADDR	0x40400000
-#define PTE_ADDR	0x40402000
-#define IPTE_ADDR	0x40403000
-#define	TAB_SIZE	0x00010000
-
-#define V_TTY_BASE 	0x00800000
-#define	V_TIMER_BASE	0x00C00000	// timer virtual address
 //////////////////////////////////////////////////////////
 //	System devices
@@ -53,30 +42,22 @@
 #define	TTY_SIZE	0x00000100
 
-#define	TIMER_BASE	0xD0200000
-#define	TIMER_SIZE	0x00000100
+#define	XICU_BASE	0xD0200000
+#define	XICU_SIZE	0x00000100
 
-#define	LOCKS_BASE	0xE0200000
-#define	LOCKS_SIZE	0x00000100
+#define	SIMHELPER_BASE  0xF0200000
+#define	SIMHELPER_SIZE	0x00000100
 
-#define C_PROC0_BASE	0x01200000
-#define C_PROC0_SIZE	0x00000010
-
-#define C_PROC1_BASE	0x02200000
-#define C_PROC1_SIZE	0x00000010
-
-#define C_PROC2_BASE	0x03200000
-#define C_PROC2_SIZE	0x00000010
-
-#define C_PROC3_BASE	0x04200000
-#define C_PROC3_SIZE	0x00000010
-
-#define C_MC_M_BASE	0x00200000
-#define C_MC_M_SIZE	0x00000008
-
-#define XRAM_BASE	0xB0200000
-#define XRAM_SIZE	0x00000008
+#define C_PROC_BASE	0x01200000
+#define C_PROC_SIZE	0x00000010
+#define C_PROC_SPAN     0x01000000
 
 #define MC_R_BASE	0x20200000
 #define MC_R_SIZE	0x00000008
 
-#define CLEANUP_OFFSET  0x20200000
+//#define C_MC_M_BASE	0x00200000
+//#define C_MC_M_SIZE	0x00000008
+
+//#define XRAM_BASE	0xB0200000
+//#define XRAM_SIZE	0x00000008
+
+//#define CLEANUP_OFFSET  0x20200000
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/Makefile
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/Makefile	(revision 133)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/Makefile	(revision 134)
@@ -1,4 +1,14 @@
-ADD_OBJS= stdio.o stdlib.o exception.o system.o
-SOCLIB?=$(shell soclib-cc --getpath)
+ADD_OBJS	= 	stdio.o stdlib.o exception.o system.o \
+			$(patsubst %.c,%.o,$(wildcard *.c)) \
+			$(patsubst common/%.c,common/%.o,$(wildcard common/*.c)) \
+			$(patsubst irq/%.c,irq/%.o,$(wildcard irq/*.c)) \
+			$(patsubst benchmark/%.c,benchmark/%.o,$(wildcard benchmark/*.c)) \
+			$(patsubst matrix_multiplication/%.c,matrix_multiplication/%.o,$(wildcard matrix_multiplication/*.c)) \
+			$(patsubst sort/%.c,sort/%.o,$(wildcard sort/*.c)) \
+			$(patsubst dhrystone/%.c,dhrystone/%.o,$(wildcard dhrystone/*.c))
+
+ADD_CFLAGS	=
+SOCLIB		?=	$(shell soclib-cc --getpath)
+
 export SOCLIB
 include $(SOCLIB)/soclib/platform/topcells/soft.mk
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark.c	(revision 134)
@@ -0,0 +1,61 @@
+#include "benchmark.h"
+#include "system.h"
+#include "stdio.h"
+#include "../common/common.h"
+
+void benchmark (void)
+{
+  /* if(procnum() != 0) */
+  /*   EXIT(0); */
+
+  int result = 0;
+  int cycle_begin = cycle_begin = cpu_cycles();
+
+  switch (procnum())
+    {
+    default :
+      {
+#if BENCHMARK_MATRIX_MULTIPLICATION_MT
+        int result_mm_mt = benchmark_matrix_multiplication_mt();
+        result += result_mm_mt;
+#endif
+#if BENCHMARK_DHRYSTONE
+        int result_dhrystone = benchmark_dhrystone();
+        result += result_dhrystone;
+#endif
+#if BENCHMARK_SORT
+        int result_sort = benchmark_sort();
+        result += result_sort;
+#endif
+#if BENCHMARK_MATRIX_MULTIPLICATION_ST
+        int result_mm_st = benchmark_matrix_multiplication_st();
+        result += result_mm_st;
+#endif
+
+        printf("\n");
+        printf("--------------------------------\n");
+        printf( "Partial results :\n");
+#if BENCHMARK_MATRIX_MULTIPLICATION_MT
+        printf(" * MM MT           : %d\n",result_mm_mt);
+#endif
+#if BENCHMARK_DHRYSTONE
+        printf(" * DHRYSTONE       : %d\n",result_dhrystone);
+#endif
+#if BENCHMARK_SORT
+        printf(" * SORT            : %d\n",result_sort);
+#endif
+#if BENCHMARK_MATRIX_MULTIPLICATION_ST
+        printf(" * MM ST           : %d\n",result_mm_st);
+#endif 
+        printf("--------------------------------\n");
+       break;
+      }
+    }
+
+  printf("\n");
+  printf("================================\n");
+  printf( "Results :\n");
+  printf( " * Score           : %d\n", result);
+  printf( " * Total CPU Cycle : %d\n", cpu_cycles()-cycle_begin);
+  printf("================================\n");
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark.h	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark.h	(revision 134)
@@ -0,0 +1,12 @@
+#ifndef benchmark_h
+#define benchmark_h
+
+#include "../define.h"
+
+void benchmark                         (void);
+int  benchmark_sort                    (void);
+int  benchmark_dhrystone               (void);
+int  benchmark_matrix_multiplication_st(void);
+int  benchmark_matrix_multiplication_mt(void);
+
+#endif //benchmark_h
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_dhrystone.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_dhrystone.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_dhrystone.c	(revision 134)
@@ -0,0 +1,31 @@
+#include "benchmark.h"
+#include "system.h"
+#include "stdlib.h"
+#include "stdio.h"
+#include "../dhrystone/dhry21.h"
+
+static uint32_t nb_thread;
+
+int _benchmark_dhrystone (unsigned int nb_runs)
+{
+  printf("\n");
+  printf("================================\n");
+  printf("Benchmark Dhrystone\n");
+  printf("================================\n");
+  printf("\n");
+
+  int result = 0;
+  
+  if (atomic_inc(&nb_thread) == 1)
+    {
+      result = dhry21(nb_runs);
+    }
+  else
+    {
+      printf("The dhrystone benchmark is not multi threaded.\n");
+    }
+    
+  return result;
+}
+
+int benchmark_dhrystone (void) { return _benchmark_dhrystone(DHRYSTONE_NB_RUNS); }
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_matrix_multiplication.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_matrix_multiplication.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_matrix_multiplication.c	(revision 134)
@@ -0,0 +1,258 @@
+#include "benchmark.h"
+#include "system.h"
+#include "stdlib.h"
+#include "stdio.h"
+#include "stdint.h"
+#include "../matrix_multiplication/matrix_multiplication.h"
+#include "../common/common.h"
+
+static uint32_t matrix_lock;
+
+void benchmark_matrix_malloc (int ** matrix_a,
+                              int ** matrix_b,
+                              int ** matrix_d,
+                              int    size)
+{
+  int i;
+  
+  for (i=0; i<size; ++i)
+    {
+      matrix_a[i] = (int*) malloc(size*sizeof(int));
+      matrix_b[i] = (int*) malloc(size*sizeof(int));
+      matrix_d[i] = (int*) malloc(size*sizeof(int));
+    }
+}
+
+void benchmark_matrix_free (int ** matrix_a,
+                            int ** matrix_b,
+                            int ** matrix_d,
+                            int    size)
+{
+  int i;
+  
+  for (i=0; i<size; ++i)
+    {
+      free(matrix_a[i]);
+      free(matrix_b[i]);
+      free(matrix_d[i]);
+    }
+}
+
+void benchmark_matrix_init (int ** matrix_a,
+                            int ** matrix_b,
+                            int    size)
+{
+  int i,j,x;
+
+  x = 0;
+  for (i=0; i<size; ++i)
+    for (j=0; j<size; ++j)
+      {
+        matrix_a [i][j] = x;
+        matrix_b [j][i] = x;
+        x++;
+      }
+}
+
+void benchmark_matrix_validation (int ** matrix_d,
+                                  int    size)
+{
+  int i,j,x;
+  int error = 0;
+
+  for (i=0; (i<size)&&(error==0); ++i)
+    for (j=0; (j<size)&&(error==0); ++j)
+      {
+        int val = 0;
+        for (x=0; x<size; ++x)
+          val += (i*size+x)*(j*size+x);
+        
+        if (matrix_d[i][j] != val)
+          {
+            error = 1;
+            printf("KO !!! (matrix_d[%d][%d] = %d (!= %d))\n",i,j,matrix_d[i][j],val);
+          }
+      }
+
+  if (error == 0)
+    printf("OK\n");
+}
+
+int _benchmark_matrix_multiplication_st (unsigned int size)
+{
+  printf("\n");
+  printf("================================\n");
+  printf("Benchmark Matrix Multiplication (ST)\n");
+  printf("================================\n");
+  printf("\n");
+
+  printf(" * Size : %d\n",size);
+  
+  int cycle_begin, result;
+
+  result = 0;
+
+  printf(" * Malloc...\n");
+
+  lock_lock(&matrix_lock);
+
+  int ** matrix_local_a = (int**) malloc(size*sizeof(int*));
+  int ** matrix_local_b = (int**) malloc(size*sizeof(int*));
+  int ** matrix_local_d = (int**) malloc(size*sizeof(int*));
+
+  benchmark_matrix_malloc (matrix_local_a,
+                           matrix_local_b,
+                           matrix_local_d,
+                           size);
+  lock_unlock(&matrix_lock);
+  
+  printf(" * Init...\n");
+
+  benchmark_matrix_init (matrix_local_a,
+                         matrix_local_b,
+                         size);
+  
+  /* matrix_multiplication_print(matrix_local_a, size); */
+  /* matrix_multiplication_print(matrix_local_b, size); */
+ 
+  printf(" * Matrix multiplication (size : %d)... \n",size);
+
+  cycle_begin = cpu_cycles();
+  matrix_multiplication_st(matrix_local_a,
+                           matrix_local_b,
+                           matrix_local_d,
+                           size);
+  result += cpu_cycles()-cycle_begin;
+
+  /* matrix_multiplication_print(matrix_local_d, size); */
+  
+  printf(" * Verification... ");
+  
+  benchmark_matrix_validation (matrix_local_d, size);
+  
+  printf(" * Free...\n");
+  
+  benchmark_matrix_free (matrix_local_a,
+                         matrix_local_b,
+                         matrix_local_d,
+                         size);
+  
+  free(matrix_local_a);
+  free(matrix_local_b);
+  free(matrix_local_d);
+
+  return result;
+}
+
+static int ** matrix_global_a;
+static int ** matrix_global_b;
+static int ** matrix_global_d;
+
+static int matrix_nb_thread_start;
+static int matrix_nb_thread_stop;
+static int matrix_end;
+
+int _benchmark_matrix_multiplication_mt (int size, int lock_by_line)
+{
+  printf("\n");
+  printf("================================\n");
+  printf("Benchmark Matrix Multiplication (MT)\n");
+  printf("================================\n");
+  printf("\n");
+  
+  printf(" * Size         : %d\n",size);
+  printf(" * Lock by line : %d\n",lock_by_line);
+  
+  int cycle_begin, result;
+
+  result = 0;
+
+  lock_lock(&matrix_lock);
+
+  if (matrix_end != 0)
+    {
+      printf("Benchmark is already finished\n");
+
+      lock_unlock(&matrix_lock);
+      
+      return 0;
+    }
+      
+  printf(" * Start number %d\n",matrix_nb_thread_start);
+  
+  // first thread
+  if (matrix_nb_thread_start==0)
+    {
+      printf(" * Malloc...\n");
+
+      matrix_global_a = (int**) malloc(size*sizeof(int*));
+      matrix_global_b = (int**) malloc(size*sizeof(int*));
+      matrix_global_d = (int**) malloc(size*sizeof(int*));
+
+      benchmark_matrix_malloc (matrix_global_a,
+                               matrix_global_b,
+                               matrix_global_d,
+                               size);
+           
+      printf(" * Init...\n");
+
+      benchmark_matrix_init (matrix_global_a,
+                             matrix_global_b,
+                             size);
+    }
+
+  matrix_nb_thread_start ++;
+
+  lock_unlock(&matrix_lock);
+  
+  /* matrix_multiplication_print(matrix_global_a, size); */
+  /* matrix_multiplication_print(matrix_global_b, size); */
+ 
+  printf(" * Matrix multiplication (size : %d)... \n",size);
+
+  cycle_begin = cpu_cycles();
+  matrix_multiplication_mt(matrix_global_a,
+                           matrix_global_b,
+                           matrix_global_d,
+                           size,
+                           lock_by_line);
+  result += cpu_cycles()-cycle_begin;
+
+  /* matrix_multiplication_print(matrix_global_d, size); */
+
+  lock_lock(&matrix_lock);
+
+  printf(" * Stop number %d\n",matrix_nb_thread_stop);
+  
+  matrix_nb_thread_stop ++;
+    
+  // first thread
+  if (matrix_nb_thread_stop == matrix_nb_thread_start)
+    {
+      printf(" * Verification... ");
+
+      benchmark_matrix_validation (matrix_global_d, size);
+      
+      printf(" * Free...\n");
+   
+      benchmark_matrix_free (matrix_global_a,
+                             matrix_global_b,
+                             matrix_global_d,
+                             size);
+      
+      free(matrix_global_a);
+      free(matrix_global_b);
+      free(matrix_global_d);
+
+      matrix_end = 1;
+    }
+
+  lock_unlock(&matrix_lock);
+  
+  return result;
+}
+
+int benchmark_matrix_multiplication_st (void) { return _benchmark_matrix_multiplication_st (MATRIX_MULTIPLICATION_ST_SIZE);}
+int benchmark_matrix_multiplication_mt (void) { return _benchmark_matrix_multiplication_mt (MATRIX_MULTIPLICATION_MT_SIZE,MATRIX_MULTIPLICATION_MT_LOCK_BY_LINE);}
+
+
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_sort.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_sort.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/benchmark/benchmark_sort.c	(revision 134)
@@ -0,0 +1,84 @@
+#include "benchmark.h"
+#include "system.h"
+#include "stdlib.h"
+#include "stdio.h"
+#include "stdint.h"
+#include "../sort/sort.h"
+#include "../common/common.h"
+
+static uint32_t sort_lock;
+
+int _benchmark_sort (unsigned int size)
+{
+  printf("\n");
+  printf("================================\n");
+  printf("Benchmark Sort\n");
+  printf("================================\n");
+  printf("\n");
+
+  printf(" * Size : %d\n",size);
+
+  unsigned int* SortArray;
+  
+  int cycle_begin, result;
+
+  result = 0;
+  
+  int p=procnum();
+  
+  sort_t _sort_type;
+  const sort_t nb_sort_type = 4;
+  
+  for (_sort_type=0; _sort_type < nb_sort_type; _sort_type++)
+    {
+      sort_t sort_type = (_sort_type+p)%nb_sort_type;
+      
+      printf(" * Algo : %s\n",sort_str(sort_type));
+      
+      printf("   * Init...\n");
+      
+      lock_lock(&sort_lock);
+      SortArray = (unsigned int*) malloc(size*sizeof(unsigned int));
+      lock_unlock(&sort_lock);
+      
+      unsigned int seed = p;
+      int i;
+      for (i=0; i<size; ++i)
+        {
+          seed = seed * 1103515245 + 12345;
+          SortArray[i] = seed&0xff;
+        }
+      printf("   * Sort... \n");
+      
+      cycle_begin = cpu_cycles();
+      sort((unsigned int *) (SortArray), (unsigned int) size, sort_type);
+      int cycle_exec = cpu_cycles()-cycle_begin;
+      
+      printf("   * Executed in %d cycles\n",cycle_exec);
+      
+      result += cycle_exec;
+      
+      printf("   * Verification... ");
+      
+      for (i = 1; i < size; i++)
+        {
+          /* printf("%d ",SortArray[i-1]); */
+          
+          if (SortArray[i] < SortArray[i-1])
+            {
+              printf("KO !!!\n");
+              EXIT(1);
+            }
+        }
+      printf("OK\n");
+
+      free (SortArray);
+
+    }
+  
+  return result;
+}
+
+int benchmark_sort (void) { return _benchmark_sort(SORT_SIZE); }
+
+  
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/common/common.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/common/common.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/common/common.c	(revision 134)
@@ -0,0 +1,45 @@
+#include "common.h"
+#include "stdio.h"
+#include "system.h"
+#include "stdio.h"
+
+#ifdef SIMHELPER_BASE
+#include "soclib/simhelper.h"
+#endif
+
+static uint32_t lock;
+static uint32_t nb_thread;
+
+void system_start (void)
+{
+  lock_lock(&lock);
+  nb_thread ++;
+  lock_unlock(&lock);
+
+  printf("CPU %d\n",procnum());
+}
+
+void system_stop (char* file, int line, int x)
+{
+  printf("Exit(%d) in file \"%s\", line %d\n",x,file,line);
+
+  lock_lock(&lock);
+  uint32_t num_thread = --nb_thread;
+  lock_unlock(&lock);
+
+  // Last thread ?
+  if (num_thread == 0)
+    {
+#ifdef SIMHELPER_BASE
+      soclib_io_set
+        (base(SIMHELPER),
+         SIMHELPER_SC_STOP,
+         0);
+#else
+# warning "No simhelper, exit will do a trap and an infinite loop"
+#endif
+    }
+
+  while(1);
+}
+
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/common/common.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/common/common.h	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/common/common.h	(revision 134)
@@ -0,0 +1,9 @@
+#ifndef common_h
+#define common_h
+
+#define EXIT(x) system_stop(__FILE__,__LINE__,x)
+
+void system_start (void);
+void system_stop  (char* file, int line, int x);
+
+#endif // common_h
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/define.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/define.h	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/define.h	(revision 134)
@@ -0,0 +1,23 @@
+#ifndef define_h
+#define define_h
+
+// List of benchmark
+#define BENCHMARK_DHRYSTONE                   0
+#define BENCHMARK_SORT                        0
+#define BENCHMARK_MATRIX_MULTIPLICATION_ST    0
+#define BENCHMARK_MATRIX_MULTIPLICATION_MT    1
+
+#define VERBOSE_SORT                          0
+
+// Benchmark size
+#define DHRYSTONE_NB_RUNS                     5000
+#define SORT_SIZE                             850
+#define MATRIX_MULTIPLICATION_ST_SIZE         50
+#define MATRIX_MULTIPLICATION_MT_SIZE         75
+#define MATRIX_MULTIPLICATION_MT_LOCK_BY_LINE 1
+
+// Timer configuration
+#define TIMER_INTERRUPT                       0
+#define TIMER_INTERRUPT_PERIOD                100000
+
+#endif // define_h
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry.h	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry.h	(revision 134)
@@ -0,0 +1,414 @@
+/*
+ *************************************************************************
+ *
+ *                   "DHRYSTONE" Benchmark Program
+ *                   -----------------------------
+ *
+ *  Version:    C, Version 2.1
+ *
+ *  File:       dhry.h (part 1 of 3)
+ *
+ *  Date:       May 25, 1988
+ *
+ *  Author:     Reinhold P. Weicker
+ *              Siemens Nixdorf Inf. Syst.
+ *              STM OS 32
+ *              Otto-Hahn-Ring 6
+ *              W-8000 Muenchen 83
+ *              Germany
+ *                      Phone:    [+49]-89-636-42436
+ *                                (8-17 Central European Time)
+ *                      UUCP:     weicker@ztivax.uucp@unido.uucp
+ *                      Internet: weicker@ztivax.siemens.com
+ *
+ *              Original Version (in Ada) published in
+ *              "Communications of the ACM" vol. 27., no. 10 (Oct. 1984),
+ *              pp. 1013 - 1030, together with the statistics
+ *              on which the distribution of statements etc. is based.
+ *
+ *              In this C version, the following C library functions are
+ *              used:
+ *              - strcpy, strcmp (inside the measurement loop)
+ *              - printf, scanf (outside the measurement loop)
+ *
+ *  Collection of Results:
+ *              Reinhold Weicker (address see above) and
+ *              
+ *              Rick Richardson
+ *              PC Research. Inc.
+ *              94 Apple Orchard Drive
+ *              Tinton Falls, NJ 07724
+ *                      Phone:  (201) 834-1378 (9-17 EST)
+ *                      UUCP:   ...!uunet!pcrat!rick
+ *
+ *      Please send results to Rick Richardson and/or Reinhold Weicker.
+ *      Complete information should be given on hardware and software
+ *      used. Hardware information includes: Machine type, CPU, type and
+ *      size of caches; for microprocessors: clock frequency, memory speed
+ *      (number of wait states). Software information includes: Compiler
+ *      (and runtime library) manufacturer and version, compilation
+ *      switches, OS version. The Operating System version may give an
+ *      indication about the compiler; Dhrystone itself performs no OS
+ *      calls in the measurement loop.
+ *
+ *      The complete output generated by the program should be mailed
+ *      such that at least some checks for correctness can be made.
+ *
+ *************************************************************************
+ *
+ *  History:    This version C/2.1 has been made for two reasons:
+ *
+ *              1) There is an obvious need for a common C version of
+ *              Dhrystone, since C is at present the most popular system
+ *              programming language for the class of processors
+ *              (microcomputers, minicomputers) where Dhrystone is used
+ *              most. There should be, as far as possible, only one C
+ *              version of Dhrystone such that results can be compared
+ *              without restrictions. In the past, the C versions
+ *              distributed by Rick Richardson (Version 1.1) and by
+ *              Reinhold Weicker had small (though not significant)
+ *              differences.
+ *
+ *              2) As far as it is possible without changes to the
+ *              Dhrystone statistics, optimizing compilers should be
+ *              prevented from removing significant statements.
+ *
+ *              This C version has been developed in cooperation with
+ *              Rick Richardson (Tinton Falls, NJ), it incorporates many
+ *              ideas from the "Version 1.1" distributed previously by
+ *              him over the UNIX network Usenet.
+ *              I also thank Chaim Benedelac (National Semiconductor),
+ *              David Ditzel (SUN), Earl Killian and John Mashey (MIPS),
+ *              Alan Smith and Rafael Saavedra-Barrera (UC at Berkeley)
+ *              for their help with comments on earlier versions of the
+ *              benchmark.
+ *
+ *  Changes:    In the initialization part, this version follows mostly
+ *              Rick Richardson's version distributed via Usenet, not the
+ *              version distributed earlier via floppy disk by Reinhold
+ *              Weicker. As a concession to older compilers, names have
+ *              been made unique within the first 8 characters. Inside the
+ *              measurement loop, this version follows the version
+ *              previously distributed by Reinhold Weicker.
+ *
+ *              At several places in the benchmark, code has been added,
+ *              but within the measurement loop only in branches that
+ *              are not executed. The intention is that optimizing
+ *              compilers should be prevented from moving code out of the
+ *              measurement loop, or from removing code altogether. Since
+ *              the statements that are executed within the measurement
+ *              loop have NOT been changed, the numbers defining the
+ *              "Dhrystone distribution" (distribution of statements,
+ *              operand types and locality) still hold. Except for
+ *              sophisticated optimizing compilers, execution times for
+ *              this version should be the same as for previous versions.
+ *
+ *              Since it has proven difficult to subtract the time for the
+ *              measurement loop overhead in a correct way, the loop check
+ *              has been made a part of the benchmark. This does have
+ *              an impact - though a very minor one - on the distribution
+ *              statistics which have been updated for this version.
+ *
+ *              All changes within the measurement loop are described
+ *              and discussed in the companion paper "Rationale for
+ *              Dhrystone version 2".
+ *
+ *              Because of the self-imposed limitation that the order and
+ *              distribution of the executed statements should not be
+ *              changed, there are still cases where optimizing compilers
+ *              may not generate code for some statements. To a certain
+ *              degree, this is unavoidable for small synthetic
+ *              benchmarks. Users of the benchmark are advised to check
+ *              code listings whether code is generated for all statements
+ *              of Dhrystone.
+ *
+ *              Version 2.1 is identical to version 2.0 distributed via
+ *              the UNIX network Usenet in March 1988 except that it
+ *              corrects some minor deficiencies that were found by users
+ *              of version 2.0. The only change within the measurement
+ *              loop is that a non-executed "else" part was added to the
+ *              "if" statement in Func_3, and a non-executed "else" part
+ *              removed from Proc_3.
+ *
+ *************************************************************************
+ *
+ * Defines:     The following "Defines" are possible:
+ *              -DROPT         (default: Not defined)
+ *                      As an approximation to what an average C
+ *                      programmer might do, the "register" storage class
+ *                      is applied (if enabled by -DROPT)
+ *                      - for local variables, if they are used
+ *                        (dynamically) five or more times
+ *                      - for parameters if they are used (dynamically)
+ *                        six or more times
+ *                      Note that an optimal "register" strategy is
+ *                      compiler-dependent, and that "register"
+ *                      declarations do not necessarily lead to faster
+ *                      execution.
+ *              -DNOSTRUCTASSIGN        (default: Not defined)
+ *                      Define if the C compiler does not support
+ *                      assignment of structures.
+ *              -DNOENUMS               (default: Not defined)
+ *                      Define if the C compiler does not support
+ *                      enumeration types.
+ *
+ *************************************************************************
+ *
+ *  Compilation model and measurement (IMPORTANT):
+ *
+ *  This C version of Dhrystone consists of three files:
+ *  - dhry.h (this file, containing global definitions and comments)
+ *  - dhry_1.c (containing the code corresponding to Ada package Pack_1)
+ *  - dhry_2.c (containing the code corresponding to Ada package Pack_2)
+ *
+ *  The following "ground rules" apply for measurements:
+ *  - Separate compilation
+ *  - No procedure merging
+ *  - Otherwise, compiler optimizations are allowed but should be
+ *    indicated
+ *  - Default results are those without register declarations
+ *  See the companion paper "Rationale for Dhrystone Version 2" for a more
+ *  detailed discussion of these ground rules.
+ *
+ *  For 16-Bit processors (e.g. 80186, 80286), times for all compilation
+ *  models ("small", "medium", "large" etc.) should be given if possible,
+ *  together with a definition of these models for the compiler system
+ *  used.
+ *
+ *************************************************************************
+ *
+ *  Dhrystone (C version) statistics:
+ *
+ *  [Comment from the first distribution, updated for version 2.
+ *   Note that because of language differences, the numbers are slightly
+ *   different from the Ada version.]
+ *
+ *  The following program contains statements of a high level programming
+ *  language (here: C) in a distribution considered representative:
+ *
+ *    assignments                  52 (51.0 %)
+ *    control statements           33 (32.4 %)
+ *    procedure, function calls    17 (16.7 %)
+ *
+ *  103 statements are dynamically executed. The program is balanced with
+ *  respect to the three aspects:
+ *
+ *    - statement type
+ *    - operand type
+ *    - operand locality
+ *         operand global, local, parameter, or constant.
+ *
+ *  The combination of these three aspects is balanced only approximately.
+ *
+ *  1. Statement Type:
+ *  -----------------             number
+ *
+ *     V1 = V2                     9
+ *       (incl. V1 = F(..)
+ *     V = Constant               12
+ *     Assignment,                 7
+ *       with array element
+ *     Assignment,                 6
+ *       with record component
+ *                                --
+ *                                34       34
+ *
+ *     X = Y +|-|"&&"|"|" Z        5
+ *     X = Y +|-|"==" Constant     6
+ *     X = X +|- 1                 3
+ *     X = Y *|/ Z                 2
+ *     X = Expression,             1
+ *           two operators
+ *     X = Expression,             1
+ *           three operators
+ *                                --
+ *                                18       18
+ *
+ *     if ....                    14
+ *       with "else"      7
+ *       without "else"   7
+ *           executed        3
+ *           not executed    4
+ *     for ...                     7  |  counted every time
+ *     while ...                   4  |  the loop condition
+ *     do ... while                1  |  is evaluated
+ *     switch ...                  1
+ *     break                       1
+ *     declaration with            1
+ *       initialization
+ *                                --
+ *                                34       34
+ *
+ *     P (...)  procedure call    11
+ *       user procedure      10
+ *       library procedure    1
+ *     X = F (...)
+ *             function  call      6
+ *       user function        5
+ *       library function     1
+ *                                --
+ *                                17       17
+ *                                        ---
+ *                                        103
+ *
+ *    The average number of parameters in procedure or function calls
+ *    is 1.82 (not counting the function values as implicit parameters).
+ *
+ *
+ *  2. Operators
+ *  ------------
+ *                          number    approximate
+ *                                    percentage
+ *
+ *    Arithmetic             32          50.8
+ *
+ *       +                     21          33.3
+ *       -                      7          11.1
+ *       *                      3           4.8
+ *       / (int div)            1           1.6
+ *
+ *    Comparison             27           42.8
+ *
+ *       ==                     9           14.3
+ *       /=                     4            6.3
+ *       >                      1            1.6
+ *       <                      3            4.8
+ *       >=                     1            1.6
+ *       <=                     9           14.3
+ *
+ *    Logic                   4            6.3
+ *
+ *       && (AND-THEN)          1            1.6
+ *       |  (OR)                1            1.6
+ *       !  (NOT)               2            3.2
+ * 
+ *                           --          -----
+ *                           63          100.1
+ *
+ *
+ *  3. Operand Type (counted once per operand reference):
+ *  ---------------
+ *                          number    approximate
+ *                                    percentage
+ *
+ *     Integer               175        72.3 %
+ *     Character              45        18.6 %
+ *     Pointer                12         5.0 %
+ *     String30                6         2.5 %
+ *     Array                   2         0.8 %
+ *     Record                  2         0.8 %
+ *                           ---       -------
+ *                           242       100.0 %
+ *
+ *  When there is an access path leading to the final operand (e.g. a
+ *  record component), only the final data type on the access path is
+ *  counted.
+ *
+ *
+ *  4. Operand Locality:
+ *  -------------------
+ *                                number    approximate
+ *                                          percentage
+ *
+ *     local variable              114        47.1 %
+ *     global variable              22         9.1 %
+ *     parameter                    45        18.6 %
+ *        value                        23         9.5 %
+ *        reference                    22         9.1 %
+ *     function result               6         2.5 %
+ *     constant                     55        22.7 %
+ *                                 ---       -------
+ *                                 242       100.0 %
+ *
+ *
+ *  The program does not compute anything meaningful, but it is
+ *  syntactically and semantically correct. All variables have a value
+ *  assigned to them before they are used as a source operand.
+ *
+ *  There has been no explicit effort to account for the effects of a
+ *  cache, or to balance the use of long or short displacements for code
+ *  or data.
+ *
+ *************************************************************************
+ */
+
+#ifndef DHRY_H
+#define DHRY_H
+
+/* Compiler and system dependent definitions: */
+
+#define VERBOSE
+//#define HAVE_DOUBLE
+//#define GENERATE_RESULT_FILE
+
+#ifdef HAVE_DOUBLE
+# define DOUBLE float
+# define Mic_secs_Per_Second     1000000.0
+#else
+# define DOUBLE unsigned int
+# define Mic_secs_Per_Second     1000000
+#endif
+
+DOUBLE dtime ();
+
+                /* Berkeley UNIX C returns process times in seconds/HZ */
+
+#ifdef  NOSTRUCTASSIGN
+#define structassign(d, s)      memcpy(&(d), &(s), sizeof(d))
+#else
+#define structassign(d, s)      d = s
+#endif
+
+#ifdef  NOENUM
+#define Ident_1 0
+#define Ident_2 1
+#define Ident_3 2
+#define Ident_4 3
+#define Ident_5 4
+  typedef int   Enumeration;
+#else
+  typedef       enum    {Ident_1, Ident_2, Ident_3, Ident_4, Ident_5}
+                Enumeration;
+#endif
+        /* for boolean and enumeration types in Ada, Pascal */
+
+/* General definitions: */
+
+#include <stdio.h>
+                /* for strcpy, strcmp */
+
+#define Null 0 
+                /* Value of a Null pointer */
+#define true  1
+#define false 0
+
+typedef int     One_Thirty;
+typedef int     One_Fifty;
+typedef char    Capital_Letter;
+typedef int     Boolean;
+typedef char    Str_30 [31];
+typedef int     Arr_1_Dim [50];
+typedef int     Arr_2_Dim [50] [50];
+
+typedef struct record 
+    {
+    struct record *Ptr_Comp;
+    Enumeration    Discr;
+    union {
+          struct {
+                  Enumeration Enum_Comp;
+                  int         Int_Comp;
+                  char        Str_Comp [31];
+                  } var_1;
+          struct {
+                  Enumeration E_Comp_2;
+                  char        Str_2_Comp [31];
+                  } var_2;
+          struct {
+                  char        Ch_1_Comp;
+                  char        Ch_2_Comp;
+                  } var_3;
+          } variant;
+      } Rec_Type, *Rec_Pointer;
+
+#endif //!DHRY_H
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21.h	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21.h	(revision 134)
@@ -0,0 +1,20 @@
+#ifndef DHRY21_H
+#define DHRY21_H
+
+#include "dhry.h"
+
+DOUBLE      dhry21 (unsigned int);
+
+void        Proc_1 (Rec_Pointer);
+void        Proc_2 (One_Fifty *);
+void        Proc_3 (Rec_Pointer *);
+void        Proc_4 ();
+void        Proc_5 ();
+void        Proc_6 (Enumeration, Enumeration*);
+void        Proc_7 (One_Fifty,One_Fifty,One_Fifty*);
+void        Proc_8 (Arr_1_Dim,Arr_2_Dim,int,int);
+Enumeration Func_1 (Capital_Letter,Capital_Letter);
+Boolean     Func_2 (Str_30,Str_30);
+Boolean     Func_3 (Enumeration);
+
+#endif
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21a.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21a.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21a.c	(revision 134)
@@ -0,0 +1,425 @@
+/*
+ *************************************************************************
+ *
+ *                   "DHRYSTONE" Benchmark Program
+ *                   -----------------------------
+ *
+ *  Version:    C, Version 2.1
+ *
+ *  File:       dhry_1.c (part 2 of 3)
+ *
+ *  Date:       May 25, 1988
+ *
+ *  Author:     Reinhold P. Weicker
+ *
+ *************************************************************************
+ */
+
+#include "dhry.h"
+#include "dhry21.h"
+
+#include <stdio.h>
+#ifdef GENERATE_RESULT_FILE
+#include <string.h>
+#endif
+#include <stdlib.h>
+
+/* Global Variables: */
+
+Rec_Pointer     Ptr_Glob,
+                Next_Ptr_Glob;
+int             Int_Glob;
+Boolean         Bool_Glob;
+char            Ch_1_Glob,
+                Ch_2_Glob;
+int             Arr_1_Glob [50];
+int             Arr_2_Glob [50] [50];
+
+char Reg_Define[] = "Register option selected.";
+
+//extern char     *malloc ();
+//Enumeration     Func_1 ();
+  /* 
+  forward declaration necessary since Enumeration may not simply be int
+  */
+
+#ifndef ROPT
+#define REG
+        /* REG becomes defined as empty */
+        /* i.e. no register variables   */
+#else
+#define REG register
+#endif
+
+
+/* variables for time measurement: */
+
+#define Too_Small_Time 2
+                /* Measurements should last at least 2 seconds */
+
+DOUBLE          Begin_Time,
+                End_Time,
+                User_Time;
+
+DOUBLE          Microseconds,
+                Dhrystones_Per_Second,
+                Vax_Mips;
+
+/* end of variables for time measurement */
+
+DOUBLE dhry21 (unsigned int NUMBER_OF_RUNS)
+/*****/
+
+  /* main program, corresponds to procedures        */
+  /* Main and Proc_0 in the Ada version             */
+{
+  DOUBLE   dtime();
+
+        One_Fifty       Int_1_Loc;
+  REG   One_Fifty       Int_2_Loc;
+        One_Fifty       Int_3_Loc;
+  REG   char            Ch_Index;
+        Enumeration     Enum_Loc;
+        Str_30          Str_1_Loc;
+        Str_30          Str_2_Loc;
+  REG   int             Run_Index;
+  REG   int             Number_Of_Runs;
+
+#ifdef GENERATE_RESULT_FILE
+        FILE            *Ap;
+
+  /* Initializations */
+
+  if ((Ap = fopen("dhry.res","a+")) == NULL)
+    {
+       printf("Can not open dhry.res\n\n");
+       EXIT(1);
+    }
+#endif
+
+  Next_Ptr_Glob = (Rec_Pointer) malloc (sizeof (Rec_Type));
+  Ptr_Glob      = (Rec_Pointer) malloc (sizeof (Rec_Type));
+
+  Ptr_Glob->Ptr_Comp                    = Next_Ptr_Glob;
+  Ptr_Glob->Discr                       = Ident_1;
+  Ptr_Glob->variant.var_1.Enum_Comp     = Ident_3;
+  Ptr_Glob->variant.var_1.Int_Comp      = 40;
+  strcpy (Ptr_Glob->variant.var_1.Str_Comp,
+          "DHRYSTONE PROGRAM, SOME STRING");
+  strcpy (Str_1_Loc, "DHRYSTONE PROGRAM, 1'ST STRING");
+
+  Arr_2_Glob [8][7] = 10;
+        /* Was missing in published program. Without this statement,    */
+        /* Arr_2_Glob [8][7] would have an undefined value.             */
+        /* Warning: With 16-Bit processors and Number_Of_Runs > 32000,  */
+        /* overflow may occur for this array element.                   */
+
+  printf ("\n");
+  printf ("Dhrystone Benchmark, Version 2.1 (Language: C)\n");
+  printf ("\n");
+  
+//  if (Reg)
+//  {
+//    printf ("Program compiled with 'register' attribute\n");
+//    printf ("\n");
+//  }
+//  else
+//  {
+//    printf ("Program compiled without 'register' attribute\n");
+//    printf ("\n");
+//  }
+
+//**********************************************************************
+//  printf ("Please give the number of runs through the benchmark: ");
+//  {
+//    int n;
+//    scanf ("%d", &n);
+//    Number_Of_Runs = n;
+//  }
+//  printf ("\n");
+//**********************************************************************
+
+  Number_Of_Runs = NUMBER_OF_RUNS;
+  
+  printf ("Execution starts, %d runs through Dhrystone\n",Number_Of_Runs);
+  
+  /***************/
+  /* Start timer */
+  /***************/
+ 
+  Begin_Time = dtime();
+
+  for (Run_Index = 1; Run_Index <= Number_Of_Runs; ++Run_Index)
+  {
+    Proc_5();
+    Proc_4();
+      /* Ch_1_Glob == 'A', Ch_2_Glob == 'B', Bool_Glob == true */
+    Int_1_Loc = 2;
+    Int_2_Loc = 3;
+    strcpy (Str_2_Loc, "DHRYSTONE PROGRAM, 2'ND STRING");
+    Enum_Loc = Ident_2;
+    Bool_Glob = ! Func_2 (Str_1_Loc, Str_2_Loc);
+      /* Bool_Glob == 1 */
+    while (Int_1_Loc < Int_2_Loc)  /* loop body executed once */
+    {
+      Int_3_Loc = 5 * Int_1_Loc - Int_2_Loc;
+        /* Int_3_Loc == 7 */
+      Proc_7 (Int_1_Loc, Int_2_Loc, &Int_3_Loc);
+        /* Int_3_Loc == 7 */
+      Int_1_Loc += 1;
+    } /* while */
+      /* Int_1_Loc == 3, Int_2_Loc == 3, Int_3_Loc == 7 */
+    Proc_8 (Arr_1_Glob, Arr_2_Glob, Int_1_Loc, Int_3_Loc);
+      /* Int_Glob == 5 */
+    Proc_1 (Ptr_Glob);
+    for (Ch_Index = 'A'; Ch_Index <= Ch_2_Glob; ++Ch_Index)
+                             /* loop body executed twice */
+    {
+      if (Enum_Loc == Func_1 (Ch_Index, 'C'))
+          /* then, not executed */
+        {
+        Proc_6 (Ident_1, &Enum_Loc);
+        strcpy (Str_2_Loc, "DHRYSTONE PROGRAM, 3'RD STRING");
+        Int_2_Loc = Run_Index;
+        Int_Glob = Run_Index;
+        }
+    }
+      /* Int_1_Loc == 3, Int_2_Loc == 3, Int_3_Loc == 7 */
+    Int_2_Loc = Int_2_Loc * Int_1_Loc;
+    Int_1_Loc = Int_2_Loc / Int_3_Loc;
+    Int_2_Loc = 7 * (Int_2_Loc - Int_3_Loc) - Int_1_Loc;
+      /* Int_1_Loc == 1, Int_2_Loc == 13, Int_3_Loc == 7 */
+    Proc_2 (&Int_1_Loc);
+      /* Int_1_Loc == 5 */
+
+  } /* loop "for Run_Index" */
+
+  /**************/
+  /* Stop timer */
+  /**************/
+
+  End_Time = dtime();
+
+  printf ("Execution ends\n");
+
+#ifdef VERBOSE
+  printf ("\n");
+  printf ("Final values of the variables used in the benchmark:\n");
+  printf ("\n");
+  printf ("Int_Glob:            %d\n", Int_Glob);
+  printf ("        should be:   %d\n", 5);
+  printf ("Bool_Glob:           %d\n", Bool_Glob);
+  printf ("        should be:   %d\n", 1);
+  printf ("Ch_1_Glob:           %c\n", Ch_1_Glob);
+  printf ("        should be:   %c\n", 'A');
+  printf ("Ch_2_Glob:           %c\n", Ch_2_Glob);
+  printf ("        should be:   %c\n", 'B');
+  printf ("Arr_1_Glob[8]:       %d\n", Arr_1_Glob[8]);
+  printf ("        should be:   %d\n", 7);
+  printf ("Arr_2_Glob[8][7]:    %d\n", Arr_2_Glob[8][7]);
+  printf ("        should be:   Number_Of_Runs + 10\n");
+  printf ("Ptr_Glob->\n");
+  printf ("  Ptr_Comp:          %d\n", (int) Ptr_Glob->Ptr_Comp);
+  printf ("        should be:   (implementation-dependent)\n");
+  printf ("  Discr:             %d\n", Ptr_Glob->Discr);
+  printf ("        should be:   %d\n", 0);
+  printf ("  Enum_Comp:         %d\n", Ptr_Glob->variant.var_1.Enum_Comp);
+  printf ("        should be:   %d\n", 2);
+  printf ("  Int_Comp:          %d\n", Ptr_Glob->variant.var_1.Int_Comp);
+  printf ("        should be:   %d\n", 17);
+  printf ("  Str_Comp:          %s\n", Ptr_Glob->variant.var_1.Str_Comp);
+  printf ("        should be:   DHRYSTONE PROGRAM, SOME STRING\n");
+  printf ("Next_Ptr_Glob->\n");
+  printf ("  Ptr_Comp:          %d\n", (int) Next_Ptr_Glob->Ptr_Comp);
+  printf ("        should be:   (implementation-dependent), same as above\n");
+  printf ("  Discr:             %d\n", Next_Ptr_Glob->Discr);
+  printf ("        should be:   %d\n", 0);
+  printf ("  Enum_Comp:         %d\n", Next_Ptr_Glob->variant.var_1.Enum_Comp);
+  printf ("        should be:   %d\n", 1);
+  printf ("  Int_Comp:          %d\n", Next_Ptr_Glob->variant.var_1.Int_Comp);
+  printf ("        should be:   %d\n", 18);
+  printf ("  Str_Comp:          %s\n", Next_Ptr_Glob->variant.var_1.Str_Comp);
+  printf ("        should be:   DHRYSTONE PROGRAM, SOME STRING\n");
+  printf ("Int_1_Loc:           %d\n", Int_1_Loc);
+  printf ("        should be:   %d\n", 5);
+  printf ("Int_2_Loc:           %d\n", Int_2_Loc);
+  printf ("        should be:   %d\n", 13);
+  printf ("Int_3_Loc:           %d\n", Int_3_Loc);
+  printf ("        should be:   %d\n", 7);
+  printf ("Enum_Loc:            %d\n", Enum_Loc);
+  printf ("        should be:   %d\n", 1);
+  printf ("Str_1_Loc:           %s\n", Str_1_Loc);
+  printf ("        should be:   DHRYSTONE PROGRAM, 1'ST STRING\n");
+  printf ("Str_2_Loc:           %s\n", Str_2_Loc);
+  printf ("        should be:   DHRYSTONE PROGRAM, 2'ND STRING\n");
+  printf ("\n");
+#endif
+
+  User_Time = End_Time - Begin_Time;
+
+//  if (User_Time < Too_Small_Time)
+//  {
+//#ifdef HAVE_DOUBLE
+//    printf ("Measured time too small to obtain meaningful results : %f\n",User_Time);
+//#else
+//    printf ("Measured time too small to obtain meaningful results : %d\n",User_Time);
+//#endif
+//    printf ("Please increase number of runs\n");
+//    printf ("\n");
+//  }
+//  else
+
+#ifdef HAVE_DOUBLE
+  Microseconds          = User_Time * Mic_secs_Per_Second / (DOUBLE) Number_Of_Runs;
+  Dhrystones_Per_Second = (DOUBLE) Number_Of_Runs / User_Time;
+  Vax_Mips              = Dhrystones_Per_Second / 1757.0;
+#else
+  Microseconds          = User_Time                       / (DOUBLE) Number_Of_Runs;
+#endif
+  
+#ifdef ROPT
+  printf ("Register option selected?  YES\n");
+#else
+  printf ("Register option selected?  NO\n");
+  strcpy(Reg_Define, "Register option not selected.");
+#endif
+  
+#ifdef HAVE_DOUBLE
+  printf ("Microseconds for one run through Dhrystone : %.1lf  \n",Microseconds);
+  printf ("Dhrystones per Second                      : %.1lf \n",Dhrystones_Per_Second);
+  printf ("VAX MIPS rating                            : %.3lf \n",Vax_Mips);
+#else
+  printf ("Begin_Time : %d\n",Begin_Time);
+  printf ("End_Time   : %d\n",End_Time  );
+  printf ("User_Time  : %d\n",User_Time );
+  printf ("Numbers of cycle for one run through Dhrystone : %d  \n",Microseconds);
+#endif
+  printf ("\n");
+  
+#ifdef GENERATE_RESULT_FILE
+  fprintf(Ap,"\n");
+  fprintf(Ap,"Dhrystone Benchmark, Version 2.1 (Language: C)\n");
+  fprintf(Ap,"%s\n",Reg_Define);
+  
+# ifdef HAVE_DOUBLE
+  fprintf(Ap,"Microseconds for one loop : %.1lf\n",Microseconds);
+  fprintf(Ap,"Dhrystones per second     : %.1lf\n",Dhrystones_Per_Second);
+  fprintf(Ap,"VAX MIPS rating           : %.3lf\n",Vax_Mips);
+# else
+  fprintf(Ap,"Numbers of cycle for one loop : %.1d\n",Microseconds);
+# endif
+  fclose(Ap);
+#endif
+  
+#ifdef HAVE_DOUBLE
+  return Vax_Mips;
+#else
+  return User_Time;
+#endif
+}
+
+void
+Proc_1 (Ptr_Val_Par)
+/******************/
+
+REG Rec_Pointer Ptr_Val_Par;
+    /* executed once */
+{
+  REG Rec_Pointer Next_Record = Ptr_Val_Par->Ptr_Comp;  
+                                        /* == Ptr_Glob_Next */
+  /* Local variable, initialized with Ptr_Val_Par->Ptr_Comp,    */
+  /* corresponds to "rename" in Ada, "with" in Pascal           */
+  
+  structassign (*Ptr_Val_Par->Ptr_Comp, *Ptr_Glob);
+  Ptr_Val_Par->variant.var_1.Int_Comp = 5;
+  Next_Record->variant.var_1.Int_Comp 
+        = Ptr_Val_Par->variant.var_1.Int_Comp;
+  Next_Record->Ptr_Comp = Ptr_Val_Par->Ptr_Comp;
+  Proc_3 (&Next_Record->Ptr_Comp);
+    /* Ptr_Val_Par->Ptr_Comp->Ptr_Comp 
+                        == Ptr_Glob->Ptr_Comp */
+  if (Next_Record->Discr == Ident_1)
+    /* then, executed */
+  {
+    Next_Record->variant.var_1.Int_Comp = 6;
+    Proc_6 (Ptr_Val_Par->variant.var_1.Enum_Comp, 
+           &Next_Record->variant.var_1.Enum_Comp);
+    Next_Record->Ptr_Comp = Ptr_Glob->Ptr_Comp;
+    Proc_7 (Next_Record->variant.var_1.Int_Comp, 10, 
+           &Next_Record->variant.var_1.Int_Comp);
+  }
+  else /* not executed */
+    structassign (*Ptr_Val_Par, *Ptr_Val_Par->Ptr_Comp);
+} /* Proc_1 */
+
+void
+Proc_2 (Int_Par_Ref)
+/******************/
+    /* executed once */
+    /* *Int_Par_Ref == 1, becomes 4 */
+
+One_Fifty   *Int_Par_Ref;
+{
+  One_Fifty  Int_Loc;
+  Enumeration   Enum_Loc;
+
+  Int_Loc = *Int_Par_Ref + 10;
+  do /* executed once */
+    if (Ch_1_Glob == 'A')
+      /* then, executed */
+    {
+      Int_Loc -= 1;
+      *Int_Par_Ref = Int_Loc - Int_Glob;
+      Enum_Loc = Ident_1;
+    } /* if */
+  while (Enum_Loc != Ident_1); /* true */
+} /* Proc_2 */
+
+void
+Proc_3 (Ptr_Ref_Par)
+/******************/
+    /* executed once */
+    /* Ptr_Ref_Par becomes Ptr_Glob */
+
+Rec_Pointer *Ptr_Ref_Par;
+
+{
+  if (Ptr_Glob != Null)
+    /* then, executed */
+    *Ptr_Ref_Par = Ptr_Glob->Ptr_Comp;
+  Proc_7 (10, Int_Glob, &Ptr_Glob->variant.var_1.Int_Comp);
+} /* Proc_3 */
+
+void
+Proc_4 () /* without parameters */
+/*******/
+    /* executed once */
+{
+  Boolean Bool_Loc;
+
+  Bool_Loc = Ch_1_Glob == 'A';
+  Bool_Glob = Bool_Loc | Bool_Glob;
+  Ch_2_Glob = 'B';
+} /* Proc_4 */
+
+void
+Proc_5 () /* without parameters */
+/*******/
+    /* executed once */
+{
+  Ch_1_Glob = 'A';
+  Bool_Glob = false;
+} /* Proc_5 */
+
+
+        /* Procedure for the assignment of structures,          */
+        /* if the C compiler doesn't support this feature       */
+#ifdef  NOSTRUCTASSIGN
+memcpy (d, s, l)
+register char   *d;
+register char   *s;
+register int    l;
+{
+        while (l--) *d++ = *s++;
+}
+#endif
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21b.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21b.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dhry21b.c	(revision 134)
@@ -0,0 +1,195 @@
+/*
+ *************************************************************************
+ *
+ *                   "DHRYSTONE" Benchmark Program
+ *                   -----------------------------
+ *
+ *  Version:    C, Version 2.1
+ *
+ *  File:       dhry_2.c (part 3 of 3)
+ *
+ *  Date:       May 25, 1988
+ *
+ *  Author:     Reinhold P. Weicker
+ *
+ *************************************************************************
+ */
+
+#include "dhry.h"
+#include "dhry21.h"
+//#include <string.h>
+
+#ifndef REG
+#define REG
+        /* REG becomes defined as empty */
+        /* i.e. no register variables   */
+#else
+#define REG register
+#endif
+
+int     Int_Glob;
+char    Ch_1_Glob;
+
+void
+Proc_6 (Enum_Val_Par, Enum_Ref_Par)
+/*********************************/
+    /* executed once */
+    /* Enum_Val_Par == Ident_3, Enum_Ref_Par becomes Ident_2 */
+
+Enumeration  Enum_Val_Par;
+Enumeration *Enum_Ref_Par;
+{
+  *Enum_Ref_Par = Enum_Val_Par;
+  if (! Func_3 (Enum_Val_Par))
+    /* then, not executed */
+    *Enum_Ref_Par = Ident_4;
+  switch (Enum_Val_Par)
+  {
+    case Ident_1: 
+      *Enum_Ref_Par = Ident_1;
+      break;
+    case Ident_2: 
+      if (Int_Glob > 100)
+        /* then */
+      *Enum_Ref_Par = Ident_1;
+      else *Enum_Ref_Par = Ident_4;
+      break;
+    case Ident_3: /* executed */
+      *Enum_Ref_Par = Ident_2;
+      break;
+    case Ident_4: break;
+    case Ident_5: 
+      *Enum_Ref_Par = Ident_3;
+      break;
+  } /* switch */
+} /* Proc_6 */
+
+void
+Proc_7 (Int_1_Par_Val, Int_2_Par_Val, Int_Par_Ref)
+/**********************************************/
+    /* executed three times                                      */
+    /* first call:      Int_1_Par_Val == 2, Int_2_Par_Val == 3,  */
+    /*                  Int_Par_Ref becomes 7                    */
+    /* second call:     Int_1_Par_Val == 10, Int_2_Par_Val == 5, */
+    /*                  Int_Par_Ref becomes 17                   */
+    /* third call:      Int_1_Par_Val == 6, Int_2_Par_Val == 10, */
+    /*                  Int_Par_Ref becomes 18                   */
+One_Fifty       Int_1_Par_Val;
+One_Fifty       Int_2_Par_Val;
+One_Fifty      *Int_Par_Ref;
+{
+  One_Fifty Int_Loc;
+
+  Int_Loc = Int_1_Par_Val + 2;
+  *Int_Par_Ref = Int_2_Par_Val + Int_Loc;
+} /* Proc_7 */
+
+void
+Proc_8 (Arr_1_Par_Ref, Arr_2_Par_Ref, Int_1_Par_Val, Int_2_Par_Val)
+/*********************************************************************/
+    /* executed once      */
+    /* Int_Par_Val_1 == 3 */
+    /* Int_Par_Val_2 == 7 */
+Arr_1_Dim       Arr_1_Par_Ref;
+Arr_2_Dim       Arr_2_Par_Ref;
+int             Int_1_Par_Val;
+int             Int_2_Par_Val;
+{
+  REG One_Fifty Int_Index;
+  REG One_Fifty Int_Loc;
+
+  Int_Loc = Int_1_Par_Val + 5;
+  Arr_1_Par_Ref [Int_Loc] = Int_2_Par_Val;
+  Arr_1_Par_Ref [Int_Loc+1] = Arr_1_Par_Ref [Int_Loc];
+  Arr_1_Par_Ref [Int_Loc+30] = Int_Loc;
+  for (Int_Index = Int_Loc; Int_Index <= Int_Loc+1; ++Int_Index)
+    Arr_2_Par_Ref [Int_Loc] [Int_Index] = Int_Loc;
+  Arr_2_Par_Ref [Int_Loc] [Int_Loc-1] += 1;
+  Arr_2_Par_Ref [Int_Loc+20] [Int_Loc] = Arr_1_Par_Ref [Int_Loc];
+  Int_Glob = 5;
+} /* Proc_8 */
+
+
+Enumeration Func_1 (Ch_1_Par_Val, Ch_2_Par_Val)
+/*************************************************/
+    /* executed three times                                         */
+    /* first call:      Ch_1_Par_Val == 'H', Ch_2_Par_Val == 'R'    */
+    /* second call:     Ch_1_Par_Val == 'A', Ch_2_Par_Val == 'C'    */
+    /* third call:      Ch_1_Par_Val == 'B', Ch_2_Par_Val == 'C'    */
+
+Capital_Letter   Ch_1_Par_Val;
+Capital_Letter   Ch_2_Par_Val;
+{
+  Capital_Letter        Ch_1_Loc;
+  Capital_Letter        Ch_2_Loc;
+
+  Ch_1_Loc = Ch_1_Par_Val;
+  Ch_2_Loc = Ch_1_Loc;
+  if (Ch_2_Loc != Ch_2_Par_Val)
+    /* then, executed */
+    return (Ident_1);
+  else  /* not executed */
+  {
+    Ch_1_Glob = Ch_1_Loc;
+    return (Ident_2);
+   }
+} /* Func_1 */
+
+
+Boolean Func_2 (Str_1_Par_Ref, Str_2_Par_Ref)
+/*************************************************/
+    /* executed once */
+    /* Str_1_Par_Ref == "DHRYSTONE PROGRAM, 1'ST STRING" */
+    /* Str_2_Par_Ref == "DHRYSTONE PROGRAM, 2'ND STRING" */
+
+Str_30  Str_1_Par_Ref;
+Str_30  Str_2_Par_Ref;
+{
+  REG One_Thirty        Int_Loc;
+      Capital_Letter    Ch_Loc ;
+
+  Int_Loc = 2;
+  while (Int_Loc <= 2) /* loop body executed once */
+    if (Func_1 (Str_1_Par_Ref[Int_Loc],
+                Str_2_Par_Ref[Int_Loc+1]) == Ident_1)
+      /* then, executed */
+    {
+      Ch_Loc = 'A';
+      Int_Loc += 1;
+    } /* if, while */
+  if (Ch_Loc >= 'W' && Ch_Loc < 'Z')
+    /* then, not executed */
+    Int_Loc = 7;
+  if (Ch_Loc == 'R')
+    /* then, not executed */
+    return (true);
+  else /* executed */
+  {
+    if (strcmp (Str_1_Par_Ref, Str_2_Par_Ref) > 0)
+      /* then, not executed */
+    {
+      Int_Loc += 7;
+      Int_Glob = Int_Loc;
+      return (true);
+    }
+    else /* executed */
+      return (false);
+  } /* if Ch_Loc */
+} /* Func_2 */
+
+
+Boolean Func_3 (Enum_Par_Val)
+/***************************/
+    /* executed once        */
+    /* Enum_Par_Val == Ident_3 */
+Enumeration Enum_Par_Val;
+{
+  Enumeration Enum_Loc;
+
+  Enum_Loc = Enum_Par_Val;
+  if (Enum_Loc == Ident_3)
+    /* then, executed */
+    return (true);
+  else /* not executed */
+    return (false);
+} /* Func_3 */
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dtime.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dtime.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/dhrystone/dtime.c	(revision 134)
@@ -0,0 +1,58 @@
+/*****************************************************/
+/* Various timer routines.                           */
+/* Al Aburto, aburto@nosc.mil, 18 Feb 1997           */
+/*                                                   */
+/* t = dtime() outputs the current time in seconds.  */
+/* Use CAUTION as some of these routines will mess   */
+/* up when timing across the hour mark!!!            */
+/*                                                   */
+/* For timing I use the 'user' time whenever         */
+/* possible. Using 'user+sys' time is a separate     */
+/* issue.                                            */
+/*                                                   */
+/* Example Usage:                                    */
+/* [timer options added here]                        */
+/* main()                                            */
+/* {                                                 */
+/* double starttime,benchtime,dtime();               */
+/*                                                   */
+/* starttime = dtime();                              */ 
+/* [routine to time]                                 */
+/* benchtime = dtime() - starttime;                  */
+/* }                                                 */
+/*                                                   */
+/* [timer code below added here]                     */
+/*****************************************************/
+
+/*********************************/
+/* Timer code.                   */
+/*********************************/
+
+#include "dhry.h"
+#include "system.h"
+
+/***************************************************/
+/*  dtime().                                       */
+/***************************************************/
+#ifdef HAVE_DOUBLE
+# ifndef MHZ
+# define MHZ (1000000.0)
+# endif //!MHZ
+
+# ifndef FRQ
+# define FRQ (1*MHZ)
+# endif //!FRQ
+#endif
+
+DOUBLE dtime()
+{
+  DOUBLE q;
+
+#ifdef HAVE_DOUBLE
+  q = (DOUBLE)(cpu_cycles())/(DOUBLE)FRQ;
+#else
+  q = (DOUBLE)(cpu_cycles());
+#endif
+
+  return (q);
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq.h	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq.h	(revision 134)
@@ -0,0 +1,7 @@
+#ifndef irq_h
+#define irq_h
+
+void irq_init   ();
+void irq_handler(int irq);
+
+#endif // irq_h
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq_handler.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq_handler.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq_handler.c	(revision 134)
@@ -0,0 +1,17 @@
+#include "irq.h"
+#include "system.h"
+#include "stdio.h"
+
+#include "../../segmentation.h"
+#include "soclib/xicu.h"
+
+void irq_handler (int irq)
+{
+  const int cpu = procnum();
+  
+  printf("Timer wrapped at cycle %d on cpu %d\n", cpu_cycles(), cpu);
+  /* printf("Timer wrapped  on cpu %d\n", cpu); */
+
+  soclib_io_get(base(XICU),
+        	XICU_REG(XICU_PTI_ACK, cpu));
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq_init.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq_init.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/irq/irq_init.c	(revision 134)
@@ -0,0 +1,27 @@
+#include "irq.h"
+#include "system.h"
+#include "stdio.h"
+#include "../define.h"
+#include "../../segmentation.h"
+#include "soclib/xicu.h"
+
+void irq_init ()
+{
+  int cpu=procnum();
+  
+  printf("irq_init : %d\n",cpu);
+  
+  set_irq_handler(irq_handler);
+  
+  soclib_io_set(base(XICU),
+                XICU_REG(XICU_PTI_PER, cpu),
+                TIMER_INTERRUPT_PERIOD);
+  
+  soclib_io_set(base(XICU),
+                XICU_REG(XICU_MSK_PTI, cpu),
+                1);
+
+  enable_hw_irq(0);
+  irq_enable();
+}
+
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/main.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/main.c	(revision 133)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/main.c	(revision 134)
@@ -1,961 +1,22 @@
 #include "system.h"
 #include "stdio.h"
-#include "stdlib.h"
-//#include "matrice.h"
 
-#include "../segmentation.h"
-
-#define NPROCS 4
-#define SIZE 500 
-#define SORT_TYPE 2
-
-volatile int nprocs=NPROCS;
-unsigned int gQSortNum0[16000] = {
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49, 92, 101, 58, 21, 184, 225, 6,
-  199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36, 141, 190, 
-  83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64,144, 137,
-  142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,192, 7, 62, 159, 20, 181,
-  182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8, 161,
-  58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77,
-  254, 19, 176, 183, 78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185,
-  254, 95, 172, 139, 246, 123, 104, 15, 42, 169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27,
-  186, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,78, 145, 132, 5, 90, 117,
-  152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,169,
-  68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227,
-  32, 153, 162, 193, 244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47,
-  60, 59, 26, 75, 40, 65, 230, 217, 44, 131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197,
-  168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91, 122, 213, 120, 223, 70, 7, 
-  52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126, 147,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  57, 126, 223, 44, 11, 138, 251, 232, 143, 86, 215, 60, 83, 30, 115, 48, 87, 46, 49, 164, 101, 198, 235, 72, 31,
-  6, 57, 12, 227, 110, 157, 96, 25, 34, 191, 140, 43, 22, 37, 136, 175, 182, 183, 220, 115, 66, 173, 144, 137, 114,
-  81, 68, 69, 102, 203, 168, 193, 102, 167, 172, 3, 14, 67, 64, 249, 62, 159, 20, 75, 74, 187, 216, 207, 22, 151,
-  124, 109, 162, 51, 16, 151, 18, 143, 28, 37, 250, 171, 8, 95, 58, 135, 76, 221, 82, 221, 224, 217, 158, 127, 76,
-  107, 170, 155, 200, 239, 138, 119, 228, 77, 2, 237, 176, 183, 178, 111, 132, 5, 166, 139, 104, 129, 218, 103, 20, 189,
-  78, 3, 128, 185, 2, 95, 172, 139, 10, 123, 104, 241, 214, 169, 188, 211, 98, 13, 80, 41, 82, 177, 220, 229, 186,
-  149, 200, 159, 134, 71, 116, 99, 18, 29, 224, 103, 162, 193, 12, 171, 150, 165, 248, 209, 202, 201, 92, 13, 62, 211,
-  16, 247, 14, 209, 60, 59, 26, 181, 40, 191, 230, 39, 44, 125, 114, 195, 64, 135, 190, 225, 148, 53, 202, 197, 168,
-  79, 106, 23, 4, 19, 34, 77, 144, 23, 146, 241, 156, 91, 122, 43, 136, 223, 70, 249, 52, 163, 46, 93, 96, 89,
-  30, 255, 52, 21, 214, 229, 72, 111, 10, 9, 156, 205, 126, 147, 48, 55, 50, 239, 252, 133, 38, 11, 232, 1, 166,
-  25, 108, 61, 206, 125, 0, 199, 126, 223, 44, 11, 118, 251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49,
-  92, 101, 58, 21, 184, 225, 6, 199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36,
-  141, 190, 83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64, 7, 62, 159, 236, 75,
-  182, 187, 40, 49, 234, 105, 124, 109, 162, 205, 16, 105, 238, 143, 28, 37, 6, 85, 248, 161, 58, 121, 180, 221, 174,
-  221, 32, 217, 98, 129, 76, 149, 170, 101, 200, 239, 118, 137, 28, 179, 254, 19, 80, 183, 178, 145, 124, 251, 166, 139,
-  152, 129, 38, 153, 20, 189, 78, 3, 128, 71, 254, 95, 84, 139, 10, 123, 152, 241, 214, 169, 68, 211, 98, 13, 80,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  225, 148, 53, 54, 197, 88, 79, 106, 233, 252, 19, 34, 77, 144, 233, 146, 241, 100, 91, 134, 43, 136, 33, 70, 249,
-  204, 163, 210, 163, 96, 89, 226, 1, 52, 235, 214, 27, 72, 111, 246, 247, 156, 51, 130, 109, 208, 55, 50, 17, 252,
-  123, 218, 245, 232, 255, 90, 231, 108, 195, 50, 125, 0, 199, 130, 223, 212, 11, 138, 251, 232, 143, 86, 215, 196, 83,
-  30, 141, 48, 87, 46, 207, 92, 155, 58, 235, 184, 31, 6, 199, 12, 29, 146, 157, 160, 231, 34, 191, 116, 213, 22,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227, 32, 153, 162, 193,
-  244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47, 60, 59, 26, 75, 40, 65, 230, 217, 44,
-  131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197, 168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91,
-  122, 213, 120, 223, 70, 7, 52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126,
-  147, 48, 55, 206, 239, 4, 133, 218, 245, 232, 255, 166, 231, 108, 195, 50, 131, 0, 57, 130, 223, 44, 245, 118, 251,
-  232, 113, 86, 215, 196, 83, 30, 141, 48, 87, 46, 207, 92, 155, 198, 235, 72, 31, 250, 57, 244, 29, 110, 99, 160,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  113, 228, 219, 
-250, 171, 8, 95, 58, 135, 180, 35, 82, 221, 224, 39, 98, 129, 180, 107, 86, 101, 200, 239, 118, 119,
-  228, 179, 2, 237, 80, 183, 78, 111, 124, 5, 90, 117, 104, 127, 38, 153, 20, 67, 178, 253, 128, 185, 254, 95, 172,
-  117, 10, 123, 152, 241, 42, 87, 188, 211, 98, 243, 80, 215, 82, 79, 36, 27, 186, 107, 200, 159, 122, 71, 140, 157,
-  238, 29, 224, 153, 94, 63, 244, 85, 106, 91, 248, 47, 54, 201, 164, 243, 62, 211, 240, 247, 242, 47, 196, 197, 230,
-  181, 216, 65, 26, 217, 44, 125, 114, 195, 192, 135, 190, 31, 148, 203, 202, 59, 88, 79, 150, 233, 252, 19, 34, 77,
-  144, 233, 146, 15, 100, 165, 122, 213, 136, 223, 70, 249, 204, 93, 46, 93, 96, 167, 30, 1, 204, 21, 42, 27, 72,
-
-  57, 126, 223, 44, 11, 138, 251, 232, 143, 86, 215, 60, 83, 30, 115, 48, 87, 46, 49, 164, 101, 198, 235, 72, 31,
-  6, 57, 12, 227, 110, 157, 96, 25, 34, 191, 140, 43, 22, 37, 136, 175, 182, 183, 220, 115, 66, 173, 144, 137, 114,
-  81, 68, 69, 102, 203, 168, 193, 102, 167, 172, 3, 14, 67, 64, 249, 62, 159, 20, 75, 74, 187, 216, 207, 22, 151,
-  124, 109, 162, 51, 16, 151, 18, 143, 28, 37, 250, 171, 8, 95, 58, 135, 76, 221, 82, 221, 224, 217, 158, 127, 76,
-  107, 170, 155, 200, 239, 138, 119, 228, 77, 2, 237, 176, 183, 178, 111, 132, 5, 166, 139, 104, 129, 218, 103, 20, 189,
-  78, 3, 128, 185, 2, 95, 172, 139, 10, 123, 104, 241, 214, 169, 188, 211, 98, 13, 80, 41, 82, 177, 220, 229, 186,
-  149, 200, 159, 134, 71, 116, 99, 18, 29, 224, 103, 162, 193, 12, 171, 150, 165, 248, 209, 202, 201, 92, 13, 62, 211,
-  16, 247, 14, 209, 60, 59, 26, 181, 40, 191, 230, 39, 44, 125, 114, 195, 64, 135, 190, 225, 148, 53, 202, 197, 168,
-  79, 106, 23, 4, 19, 34, 77, 144, 23, 146, 241, 156, 91, 122, 43, 136, 223, 70, 249, 52, 163, 46, 93, 96, 89,
-  30, 255, 52, 21, 214, 229, 72, 111, 10, 9, 156, 205, 126, 147, 48, 55, 50, 239, 252, 133, 38, 11, 232, 1, 166,
-  25, 108, 61, 206, 125, 0, 199, 126, 223, 44, 11, 118, 251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49,
-  92, 101, 58, 21, 184, 225, 6, 199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36,
-  141, 190, 83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64, 7, 62, 159, 236, 75,
-  182, 187, 40, 49, 234, 105, 124, 109, 162, 205, 16, 105, 238, 143, 28, 37, 6, 85, 248, 161, 58, 121, 180, 221, 174,
-  221, 32, 217, 98, 129, 76, 149, 170, 101, 200, 239, 118, 137, 28, 179, 254, 19, 80, 183, 178, 145, 124, 251, 166, 139,
-  152, 129, 38, 153, 20, 189, 78, 3, 128, 71, 254, 95, 84, 139, 10, 123, 152, 241, 214, 169, 68, 211, 98, 13, 80,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  225, 148, 53, 54, 197, 88, 79, 106, 233, 252, 19, 34, 77, 144, 233, 146, 241, 100, 91, 134, 43, 136, 33, 70, 249,
-  204, 163, 210, 163, 96, 89, 226, 1, 52, 235, 214, 27, 72, 111, 246, 247, 156, 51, 130, 109, 208, 55, 50, 17, 252,
-  123, 218, 245, 232, 255, 90, 231, 108, 195, 50, 125, 0, 199, 130, 223, 212, 11, 138, 251, 232, 143, 86, 215, 196, 83,
-  30, 141, 48, 87, 46, 207, 92, 155, 58, 235, 184, 31, 6, 199, 12, 29, 146, 157, 160, 231, 34, 191, 116, 213, 22,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227, 32, 153, 162, 193,
-  244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47, 60, 59, 26, 75, 40, 65, 230, 217, 44,
-  131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197, 168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91,
-  122, 213, 120, 223, 70, 7, 52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126,
-  147, 48, 55, 206, 239, 4, 133, 218, 245, 232, 255, 166, 231, 108, 195, 50, 131, 0, 57, 130, 223, 44, 245, 118, 251,
-  232, 113, 86, 215, 196, 83, 30, 141, 48, 87, 46, 207, 92, 155, 198, 235, 72, 31, 250, 57, 244, 29, 110, 99, 160,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  113, 228, 219, 
-250, 171, 8, 95, 58, 135, 180, 35, 82, 221, 224, 39, 98, 129, 180, 107, 86, 101, 200, 239, 118, 119,
-  228, 179, 2, 237, 80, 183, 78, 111, 124, 5, 90, 117, 104, 127, 38, 153, 20, 67, 178, 253, 128, 185, 254, 95, 172,
-  117, 10, 123, 152, 241, 42, 87, 188, 211, 98, 243, 80, 215, 82, 79, 36, 27, 186, 107, 200, 159, 122, 71, 140, 157,
-  238, 29, 224, 153, 94, 63, 244, 85, 106, 91, 248, 47, 54, 201, 164, 243, 62, 211, 240, 247, 242, 47, 196, 197, 230,
-  181, 216, 65, 26, 217, 44, 125, 114, 195, 192, 135, 190, 31, 148, 203, 202, 59, 88, 79, 150, 233, 252, 19, 34, 77,
-  144, 233, 146, 15, 100, 165, 122, 213, 136, 223, 70, 249, 204, 93, 46, 93, 96, 167, 30, 1, 204, 21, 42, 27, 72,
-
-  57, 126, 223, 44, 11, 138, 251, 232, 143, 86, 215, 60, 83, 30, 115, 48, 87, 46, 49, 164, 101, 198, 235, 72, 31,
-  6, 57, 12, 227, 110, 157, 96, 25, 34, 191, 140, 43, 22, 37, 136, 175, 182, 183, 220, 115, 66, 173, 144, 137, 114,
-  81, 68, 69, 102, 203, 168, 193, 102, 167, 172, 3, 14, 67, 64, 249, 62, 159, 20, 75, 74, 187, 216, 207, 22, 151,
-  124, 109, 162, 51, 16, 151, 18, 143, 28, 37, 250, 171, 8, 95, 58, 135, 76, 221, 82, 221, 224, 217, 158, 127, 76,
-  107, 170, 155, 200, 239, 138, 119, 228, 77, 2, 237, 176, 183, 178, 111, 132, 5, 166, 139, 104, 129, 218, 103, 20, 189,
-  78, 3, 128, 185, 2, 95, 172, 139, 10, 123, 104, 241, 214, 169, 188, 211, 98, 13, 80, 41, 82, 177, 220, 229, 186,
-  149, 200, 159, 134, 71, 116, 99, 18, 29, 224, 103, 162, 193, 12, 171, 150, 165, 248, 209, 202, 201, 92, 13, 62, 211,
-  16, 247, 14, 209, 60, 59, 26, 181, 40, 191, 230, 39, 44, 125, 114, 195, 64, 135, 190, 225, 148, 53, 202, 197, 168,
-  79, 106, 23, 4, 19, 34, 77, 144, 23, 146, 241, 156, 91, 122, 43, 136, 223, 70, 249, 52, 163, 46, 93, 96, 89,
-  30, 255, 52, 21, 214, 229, 72, 111, 10, 9, 156, 205, 126, 147, 48, 55, 50, 239, 252, 133, 38, 11, 232, 1, 166,
-  25, 108, 61, 206, 125, 0, 199, 126, 223, 44, 11, 118, 251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49,
-  92, 101, 58, 21, 184, 225, 6, 199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36,
-  141, 190, 83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64, 7, 62, 159, 236, 75,
-  182, 187, 40, 49, 234, 105, 124, 109, 162, 205, 16, 105, 238, 143, 28, 37, 6, 85, 248, 161, 58, 121, 180, 221, 174,
-  221, 32, 217, 98, 129, 76, 149, 170, 101, 200, 239, 118, 137, 28, 179, 254, 19, 80, 183, 178, 145, 124, 251, 166, 139,
-  152, 129, 38, 153, 20, 189, 78, 3, 128, 71, 254, 95, 84, 139, 10, 123, 152, 241, 214, 169, 68, 211, 98, 13, 80,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  225, 148, 53, 54, 197, 88, 79, 106, 233, 252, 19, 34, 77, 144, 233, 146, 241, 100, 91, 134, 43, 136, 33, 70, 249,
-  204, 163, 210, 163, 96, 89, 226, 1, 52, 235, 214, 27, 72, 111, 246, 247, 156, 51, 130, 109, 208, 55, 50, 17, 252,
-  123, 218, 245, 232, 255, 90, 231, 108, 195, 50, 125, 0, 199, 130, 223, 212, 11, 138, 251, 232, 143, 86, 215, 196, 83,
-  30, 141, 48, 87, 46, 207, 92, 155, 58, 235, 184, 31, 6, 199, 12, 29, 146, 157, 160, 231, 34, 191, 116, 213, 22,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227, 32, 153, 162, 193,
-  244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47, 60, 59, 26, 75, 40, 65, 230, 217, 44,
-  131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197, 168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91,
-  122, 213, 120, 223, 70, 7, 52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126,
-  147, 48, 55, 206, 239, 4, 133, 218, 245, 232, 255, 166, 231, 108, 195, 50, 131, 0, 57, 130, 223, 44, 245, 118, 251,
-  232, 113, 86, 215, 196, 83, 30, 141, 48, 87, 46, 207, 92, 155, 198, 235, 72, 31, 250, 57, 244, 29, 110, 99, 160,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  113, 228, 219, 
-250, 171, 8, 95, 58, 135, 180, 35, 82, 221, 224, 39, 98, 129, 180, 107, 86, 101, 200, 239, 118, 119,
-  228, 179, 2, 237, 80, 183, 78, 111, 124, 5, 90, 117, 104, 127, 38, 153, 20, 67, 178, 253, 128, 185, 254, 95, 172,
-  117, 10, 123, 152, 241, 42, 87, 188, 211, 98, 243, 80, 215, 82, 79, 36, 27, 186, 107, 200, 159, 122, 71, 140, 157,
-  238, 29, 224, 153, 94, 63, 244, 85, 106, 91, 248, 47, 54, 201, 164, 243, 62, 211, 240, 247, 242, 47, 196, 197, 230,
-  181, 216, 65, 26, 217, 44, 125, 114, 195, 192, 135, 190, 31, 148, 203, 202, 59, 88, 79, 150, 233, 252, 19, 34, 77,
-  144, 233, 146, 15, 100, 165, 122, 213, 136, 223, 70, 249, 204, 93, 46, 93, 96, 167, 30, 1, 204, 21, 42, 27, 72,
-
-  57, 126, 223, 44, 11, 138, 251, 232, 143, 86, 215, 60, 83, 30, 115, 48, 87, 46, 49, 164, 101, 198, 235, 72, 31,
-  6, 57, 12, 227, 110, 157, 96, 25, 34, 191, 140, 43, 22, 37, 136, 175, 182, 183, 220, 115, 66, 173, 144, 137, 114,
-  81, 68, 69, 102, 203, 168, 193, 102, 167, 172, 3, 14, 67, 64, 249, 62, 159, 20, 75, 74, 187, 216, 207, 22, 151,
-  124, 109, 162, 51, 16, 151, 18, 143, 28, 37, 250, 171, 8, 95, 58, 135, 76, 221, 82, 221, 224, 217, 158, 127, 76,
-  107, 170, 155, 200, 239, 138, 119, 228, 77, 2, 237, 176, 183, 178, 111, 132, 5, 166, 139, 104, 129, 218, 103, 20, 189,
-  78, 3, 128, 185, 2, 95, 172, 139, 10, 123, 104, 241, 214, 169, 188, 211, 98, 13, 80, 41, 82, 177, 220, 229, 186,
-  149, 200, 159, 134, 71, 116, 99, 18, 29, 224, 103, 162, 193, 12, 171, 150, 165, 248, 209, 202, 201, 92, 13, 62, 211,
-  16, 247, 14, 209, 60, 59, 26, 181, 40, 191, 230, 39, 44, 125, 114, 195, 64, 135, 190, 225, 148, 53, 202, 197, 168,
-  79, 106, 23, 4, 19, 34, 77, 144, 23, 146, 241, 156, 91, 122, 43, 136, 223, 70, 249, 52, 163, 46, 93, 96, 89,
-  30, 255, 52, 21, 214, 229, 72, 111, 10, 9, 156, 205, 126, 147, 48, 55, 50, 239, 252, 133, 38, 11, 232, 1, 166,
-  25, 108, 61, 206, 125, 0, 199, 126, 223, 44, 11, 118, 251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49,
-  92, 101, 58, 21, 184, 225, 6, 199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36,
-  141, 190, 83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64, 7, 62, 159, 236, 75,
-  182, 187, 40, 49, 234, 105, 124, 109, 162, 205, 16, 105, 238, 143, 28, 37, 6, 85, 248, 161, 58, 121, 180, 221, 174,
-  221, 32, 217, 98, 129, 76, 149, 170, 101, 200, 239, 118, 137, 28, 179, 254, 19, 80, 183, 178, 145, 124, 251, 166, 139,
-  152, 129, 38, 153, 20, 189, 78, 3, 128, 71, 254, 95, 84, 139, 10, 123, 152, 241, 214, 169, 68, 211, 98, 13, 80,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  225, 148, 53, 54, 197, 88, 79, 106, 233, 252, 19, 34, 77, 144, 233, 146, 241, 100, 91, 134, 43, 136, 33, 70, 249,
-  204, 163, 210, 163, 96, 89, 226, 1, 52, 235, 214, 27, 72, 111, 246, 247, 156, 51, 130, 109, 208, 55, 50, 17, 252,
-  123, 218, 245, 232, 255, 90, 231, 108, 195, 50, 125, 0, 199, 130, 223, 212, 11, 138, 251, 232, 143, 86, 215, 196, 83,
-  30, 141, 48, 87, 46, 207, 92, 155, 58, 235, 184, 31, 6, 199, 12, 29, 146, 157, 160, 231, 34, 191, 116, 213, 22,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227, 32, 153, 162, 193,
-  244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47, 60, 59, 26, 75, 40, 65, 230, 217, 44,
-  131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197, 168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91,
-  122, 213, 120, 223, 70, 7, 52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126,
-  147, 48, 55, 206, 239, 4, 133, 218, 245, 232, 255, 166, 231, 108, 195, 50, 131, 0, 57, 130, 223, 44, 245, 118, 251,
-  232, 113, 86, 215, 196, 83, 30, 141, 48, 87, 46, 207, 92, 155, 198, 235, 72, 31, 250, 57, 244, 29, 110, 99, 160,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  113, 228, 219, 
-250, 171, 8, 95, 58, 135, 180, 35, 82, 221, 224, 39, 98, 129, 180, 107, 86, 101, 200, 239, 118, 119,
-  228, 179, 2, 237, 80, 183, 78, 111, 124, 5, 90, 117, 104, 127, 38, 153, 20, 67, 178, 253, 128, 185, 254, 95, 172,
-  117, 10, 123, 152, 241, 42, 87, 188, 211, 98, 243, 80, 215, 82, 79, 36, 27, 186, 107, 200, 159, 122, 71, 140, 157,
-  238, 29, 224, 153, 94, 63, 244, 85, 106, 91, 248, 47, 54, 201, 164, 243, 62, 211, 240, 247, 242, 47, 196, 197, 230,
-  181, 216, 65, 26, 217, 44, 125, 114, 195, 192, 135, 190, 31, 148, 203, 202, 59, 88, 79, 150, 233, 252, 19, 34, 77,
-  144, 233, 146, 15, 100, 165, 122, 213, 136, 223, 70, 249, 204, 93, 46, 93, 96, 167, 30, 1, 204, 21, 42, 27, 72,
-
-  57, 126, 223, 44, 11, 138, 251, 232, 143, 86, 215, 60, 83, 30, 115, 48, 87, 46, 49, 164, 101, 198, 235, 72, 31,
-  6, 57, 12, 227, 110, 157, 96, 25, 34, 191, 140, 43, 22, 37, 136, 175, 182, 183, 220, 115, 66, 173, 144, 137, 114,
-  81, 68, 69, 102, 203, 168, 193, 102, 167, 172, 3, 14, 67, 64, 249, 62, 159, 20, 75, 74, 187, 216, 207, 22, 151,
-  124, 109, 162, 51, 16, 151, 18, 143, 28, 37, 250, 171, 8, 95, 58, 135, 76, 221, 82, 221, 224, 217, 158, 127, 76,
-  107, 170, 155, 200, 239, 138, 119, 228, 77, 2, 237, 176, 183, 178, 111, 132, 5, 166, 139, 104, 129, 218, 103, 20, 189,
-  78, 3, 128, 185, 2, 95, 172, 139, 10, 123, 104, 241, 214, 169, 188, 211, 98, 13, 80, 41, 82, 177, 220, 229, 186,
-  149, 200, 159, 134, 71, 116, 99, 18, 29, 224, 103, 162, 193, 12, 171, 150, 165, 248, 209, 202, 201, 92, 13, 62, 211,
-  16, 247, 14, 209, 60, 59, 26, 181, 40, 191, 230, 39, 44, 125, 114, 195, 64, 135, 190, 225, 148, 53, 202, 197, 168,
-  79, 106, 23, 4, 19, 34, 77, 144, 23, 146, 241, 156, 91, 122, 43, 136, 223, 70, 249, 52, 163, 46, 93, 96, 89,
-  30, 255, 52, 21, 214, 229, 72, 111, 10, 9, 156, 205, 126, 147, 48, 55, 50, 239, 252, 133, 38, 11, 232, 1, 166,
-  25, 108, 61, 206, 125, 0, 199, 126, 223, 44, 11, 118, 251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49,
-  92, 101, 58, 21, 184, 225, 6, 199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36,
-  141, 190, 83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64, 7, 62, 159, 236, 75,
-  182, 187, 40, 49, 234, 105, 124, 109, 162, 205, 16, 105, 238, 143, 28, 37, 6, 85, 248, 161, 58, 121, 180, 221, 174,
-  221, 32, 217, 98, 129, 76, 149, 170, 101, 200, 239, 118, 137, 28, 179, 254, 19, 80, 183, 178, 145, 124, 251, 166, 139,
-  152, 129, 38, 153, 20, 189, 78, 3, 128, 71, 254, 95, 84, 139, 10, 123, 152, 241, 214, 169, 68, 211, 98, 13, 80,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  225, 148, 53, 54, 197, 88, 79, 106, 233, 252, 19, 34, 77, 144, 233, 146, 241, 100, 91, 134, 43, 136, 33, 70, 249,
-  204, 163, 210, 163, 96, 89, 226, 1, 52, 235, 214, 27, 72, 111, 246, 247, 156, 51, 130, 109, 208, 55, 50, 17, 252,
-  123, 218, 245, 232, 255, 90, 231, 108, 195, 50, 125, 0, 199, 130, 223, 212, 11, 138, 251, 232, 143, 86, 215, 196, 83,
-  30, 141, 48, 87, 46, 207, 92, 155, 58, 235, 184, 31, 6, 199, 12, 29, 146, 157, 160, 231, 34, 191, 116, 213, 22,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227, 32, 153, 162, 193,
-  244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47, 60, 59, 26, 75, 40, 65, 230, 217, 44,
-  131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197, 168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91,
-  122, 213, 120, 223, 70, 7, 52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126,
-  147, 48, 55, 206, 239, 4, 133, 218, 245, 232, 255, 166, 231, 108, 195, 50, 131, 0, 57, 130, 223, 44, 245, 118, 251,
-  232, 113, 86, 215, 196, 83, 30, 141, 48, 87, 46, 207, 92, 155, 198, 235, 72, 31, 250, 57, 244, 29, 110, 99, 160,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  113, 228, 219, 
-250, 171, 8, 95, 58, 135, 180, 35, 82, 221, 224, 39, 98, 129, 180, 107, 86, 101, 200, 239, 118, 119,
-  228, 179, 2, 237, 80, 183, 78, 111, 124, 5, 90, 117, 104, 127, 38, 153, 20, 67, 178, 253, 128, 185, 254, 95, 172,
-  117, 10, 123, 152, 241, 42, 87, 188, 211, 98, 243, 80, 215, 82, 79, 36, 27, 186, 107, 200, 159, 122, 71, 140, 157,
-  238, 29, 224, 153, 94, 63, 244, 85, 106, 91, 248, 47, 54, 201, 164, 243, 62, 211, 240, 247, 242, 47, 196, 197, 230,
-  181, 216, 65, 26, 217, 44, 125, 114, 195, 192, 135, 190, 31, 148, 203, 202, 59, 88, 79, 150, 233, 252, 19, 34, 77,
-  144, 233, 146, 15, 100, 165, 122, 213, 136, 223, 70, 249, 204, 93, 46, 93, 96, 167, 30, 1, 204, 21, 42, 27, 72,
-
-  57, 126, 223, 44, 11, 138, 251, 232, 143, 86, 215, 60, 83, 30, 115, 48, 87, 46, 49, 164, 101, 198, 235, 72, 31,
-  6, 57, 12, 227, 110, 157, 96, 25, 34, 191, 140, 43, 22, 37, 136, 175, 182, 183, 220, 115, 66, 173, 144, 137, 114,
-  81, 68, 69, 102, 203, 168, 193, 102, 167, 172, 3, 14, 67, 64, 249, 62, 159, 20, 75, 74, 187, 216, 207, 22, 151,
-  124, 109, 162, 51, 16, 151, 18, 143, 28, 37, 250, 171, 8, 95, 58, 135, 76, 221, 82, 221, 224, 217, 158, 127, 76,
-  107, 170, 155, 200, 239, 138, 119, 228, 77, 2, 237, 176, 183, 178, 111, 132, 5, 166, 139, 104, 129, 218, 103, 20, 189,
-  78, 3, 128, 185, 2, 95, 172, 139, 10, 123, 104, 241, 214, 169, 188, 211, 98, 13, 80, 41, 82, 177, 220, 229, 186,
-  149, 200, 159, 134, 71, 116, 99, 18, 29, 224, 103, 162, 193, 12, 171, 150, 165, 248, 209, 202, 201, 92, 13, 62, 211,
-  16, 247, 14, 209, 60, 59, 26, 181, 40, 191, 230, 39, 44, 125, 114, 195, 64, 135, 190, 225, 148, 53, 202, 197, 168,
-  79, 106, 23, 4, 19, 34, 77, 144, 23, 146, 241, 156, 91, 122, 43, 136, 223, 70, 249, 52, 163, 46, 93, 96, 89,
-  30, 255, 52, 21, 214, 229, 72, 111, 10, 9, 156, 205, 126, 147, 48, 55, 50, 239, 252, 133, 38, 11, 232, 1, 166,
-  25, 108, 61, 206, 125, 0, 199, 126, 223, 44, 11, 118, 251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49,
-  92, 101, 58, 21, 184, 225, 6, 199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36,
-  141, 190, 83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64, 7, 62, 159, 236, 75,
-  182, 187, 40, 49, 234, 105, 124, 109, 162, 205, 16, 105, 238, 143, 28, 37, 6, 85, 248, 161, 58, 121, 180, 221, 174,
-  221, 32, 217, 98, 129, 76, 149, 170, 101, 200, 239, 118, 137, 28, 179, 254, 19, 80, 183, 178, 145, 124, 251, 166, 139,
-  152, 129, 38, 153, 20, 189, 78, 3, 128, 71, 254, 95, 84, 139, 10, 123, 152, 241, 214, 169, 68, 211, 98, 13, 80,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  225, 148, 53, 54, 197, 88, 79, 106, 233, 252, 19, 34, 77, 144, 233, 146, 241, 100, 91, 134, 43, 136, 33, 70, 249,
-  204, 163, 210, 163, 96, 89, 226, 1, 52, 235, 214, 27, 72, 111, 246, 247, 156, 51, 130, 109, 208, 55, 50, 17, 252,
-  123, 218, 245, 232, 255, 90, 231, 108, 195, 50, 125, 0, 199, 130, 223, 212, 11, 138, 251, 232, 143, 86, 215, 196, 83,
-  30, 141, 48, 87, 46, 207, 92, 155, 58, 235, 184, 31, 6, 199, 12, 29, 146, 157, 160, 231, 34, 191, 116, 213, 22,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227, 32, 153, 162, 193,
-  244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47, 60, 59, 26, 75, 40, 65, 230, 217, 44,
-  131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197, 168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91,
-  122, 213, 120, 223, 70, 7, 52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126,
-  147, 48, 55, 206, 239, 4, 133, 218, 245, 232, 255, 166, 231, 108, 195, 50, 131, 0, 57, 130, 223, 44, 245, 118, 251,
-  232, 113, 86, 215, 196, 83, 30, 141, 48, 87, 46, 207, 92, 155, 198, 235, 72, 31, 250, 57, 244, 29, 110, 99, 160,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  113, 228, 219, 
-250, 171, 8, 95, 58, 135, 180, 35, 82, 221, 224, 39, 98, 129, 180, 107, 86, 101, 200, 239, 118, 119,
-  228, 179, 2, 237, 80, 183, 78, 111, 124, 5, 90, 117, 104, 127, 38, 153, 20, 67, 178, 253, 128, 185, 254, 95, 172,
-  117, 10, 123, 152, 241, 42, 87, 188, 211, 98, 243, 80, 215, 82, 79, 36, 27, 186, 107, 200, 159, 122, 71, 140, 157,
-  238, 29, 224, 153, 94, 63, 244, 85, 106, 91, 248, 47, 54, 201, 164, 243, 62, 211, 240, 247, 242, 47, 196, 197, 230,
-  181, 216, 65, 26, 217, 44, 125, 114, 195, 192, 135, 190, 31, 148, 203, 202, 59, 88, 79, 150, 233, 252, 19, 34, 77,
-  144, 233, 146, 15, 100, 165, 122, 213, 136, 223, 70, 249, 204, 93, 46, 93, 96, 167, 30, 1, 204, 21, 42, 27, 72,
-
-  57, 126, 223, 44, 11, 138, 251, 232, 143, 86, 215, 60, 83, 30, 115, 48, 87, 46, 49, 164, 101, 198, 235, 72, 31,
-  6, 57, 12, 227, 110, 157, 96, 25, 34, 191, 140, 43, 22, 37, 136, 175, 182, 183, 220, 115, 66, 173, 144, 137, 114,
-  81, 68, 69, 102, 203, 168, 193, 102, 167, 172, 3, 14, 67, 64, 249, 62, 159, 20, 75, 74, 187, 216, 207, 22, 151,
-  124, 109, 162, 51, 16, 151, 18, 143, 28, 37, 250, 171, 8, 95, 58, 135, 76, 221, 82, 221, 224, 217, 158, 127, 76,
-  107, 170, 155, 200, 239, 138, 119, 228, 77, 2, 237, 176, 183, 178, 111, 132, 5, 166, 139, 104, 129, 218, 103, 20, 189,
-  78, 3, 128, 185, 2, 95, 172, 139, 10, 123, 104, 241, 214, 169, 188, 211, 98, 13, 80, 41, 82, 177, 220, 229, 186,
-  149, 200, 159, 134, 71, 116, 99, 18, 29, 224, 103, 162, 193, 12, 171, 150, 165, 248, 209, 202, 201, 92, 13, 62, 211,
-  16, 247, 14, 209, 60, 59, 26, 181, 40, 191, 230, 39, 44, 125, 114, 195, 64, 135, 190, 225, 148, 53, 202, 197, 168,
-  79, 106, 23, 4, 19, 34, 77, 144, 23, 146, 241, 156, 91, 122, 43, 136, 223, 70, 249, 52, 163, 46, 93, 96, 89,
-  30, 255, 52, 21, 214, 229, 72, 111, 10, 9, 156, 205, 126, 147, 48, 55, 50, 239, 252, 133, 38, 11, 232, 1, 166,
-  25, 108, 61, 206, 125, 0, 199, 126, 223, 44, 11, 118, 251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49,
-  92, 101, 58, 21, 184, 225, 6, 199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36,
-  141, 190, 83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64, 7, 62, 159, 236, 75,
-  182, 187, 40, 49, 234, 105, 124, 109, 162, 205, 16, 105, 238, 143, 28, 37, 6, 85, 248, 161, 58, 121, 180, 221, 174,
-  221, 32, 217, 98, 129, 76, 149, 170, 101, 200, 239, 118, 137, 28, 179, 254, 19, 80, 183, 178, 145, 124, 251, 166, 139,
-  152, 129, 38, 153, 20, 189, 78, 3, 128, 71, 254, 95, 84, 139, 10, 123, 152, 241, 214, 169, 68, 211, 98, 13, 80,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  225, 148, 53, 54, 197, 88, 79, 106, 233, 252, 19, 34, 77, 144, 233, 146, 241, 100, 91, 134, 43, 136, 33, 70, 249,
-  204, 163, 210, 163, 96, 89, 226, 1, 52, 235, 214, 27, 72, 111, 246, 247, 156, 51, 130, 109, 208, 55, 50, 17, 252,
-  123, 218, 245, 232, 255, 90, 231, 108, 195, 50, 125, 0, 199, 130, 223, 212, 11, 138, 251, 232, 143, 86, 215, 196, 83,
-  30, 141, 48, 87, 46, 207, 92, 155, 58, 235, 184, 31, 6, 199, 12, 29, 146, 157, 160, 231, 34, 191, 116, 213, 22,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227, 32, 153, 162, 193,
-  244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47, 60, 59, 26, 75, 40, 65, 230, 217, 44,
-  131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197, 168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91,
-  122, 213, 120, 223, 70, 7, 52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126,
-  147, 48, 55, 206, 239, 4, 133, 218, 245, 232, 255, 166, 231, 108, 195, 50, 131, 0, 57, 130, 223, 44, 245, 118, 251,
-  232, 113, 86, 215, 196, 83, 30, 141, 48, 87, 46, 207, 92, 155, 198, 235, 72, 31, 250, 57, 244, 29, 110, 99, 160,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  113, 228, 219, 
-250, 171, 8, 95, 58, 135, 180, 35, 82, 221, 224, 39, 98, 129, 180, 107, 86, 101, 200, 239, 118, 119,
-  228, 179, 2, 237, 80, 183, 78, 111, 124, 5, 90, 117, 104, 127, 38, 153, 20, 67, 178, 253, 128, 185, 254, 95, 172,
-  117, 10, 123, 152, 241, 42, 87, 188, 211, 98, 243, 80, 215, 82, 79, 36, 27, 186, 107, 200, 159, 122, 71, 140, 157,
-  238, 29, 224, 153, 94, 63, 244, 85, 106, 91, 248, 47, 54, 201, 164, 243, 62, 211, 240, 247, 242, 47, 196, 197, 230,
-  181, 216, 65, 26, 217, 44, 125, 114, 195, 192, 135, 190, 31, 148, 203, 202, 59, 88, 79, 150, 233, 252, 19, 34, 77,
-  144, 233, 146, 15, 100, 165, 122, 213, 136, 223, 70, 249, 204, 93, 46, 93, 96, 167, 30, 1, 204, 21, 42, 27, 72,
-
-  57, 126, 223, 44, 11, 138, 251, 232, 143, 86, 215, 60, 83, 30, 115, 48, 87, 46, 49, 164, 101, 198, 235, 72, 31,
-  6, 57, 12, 227, 110, 157, 96, 25, 34, 191, 140, 43, 22, 37, 136, 175, 182, 183, 220, 115, 66, 173, 144, 137, 114,
-  81, 68, 69, 102, 203, 168, 193, 102, 167, 172, 3, 14, 67, 64, 249, 62, 159, 20, 75, 74, 187, 216, 207, 22, 151,
-  124, 109, 162, 51, 16, 151, 18, 143, 28, 37, 250, 171, 8, 95, 58, 135, 76, 221, 82, 221, 224, 217, 158, 127, 76,
-  107, 170, 155, 200, 239, 138, 119, 228, 77, 2, 237, 176, 183, 178, 111, 132, 5, 166, 139, 104, 129, 218, 103, 20, 189,
-  78, 3, 128, 185, 2, 95, 172, 139, 10, 123, 104, 241, 214, 169, 188, 211, 98, 13, 80, 41, 82, 177, 220, 229, 186,
-  149, 200, 159, 134, 71, 116, 99, 18, 29, 224, 103, 162, 193, 12, 171, 150, 165, 248, 209, 202, 201, 92, 13, 62, 211,
-  16, 247, 14, 209, 60, 59, 26, 181, 40, 191, 230, 39, 44, 125, 114, 195, 64, 135, 190, 225, 148, 53, 202, 197, 168,
-  79, 106, 23, 4, 19, 34, 77, 144, 23, 146, 241, 156, 91, 122, 43, 136, 223, 70, 249, 52, 163, 46, 93, 96, 89,
-  30, 255, 52, 21, 214, 229, 72, 111, 10, 9, 156, 205, 126, 147, 48, 55, 50, 239, 252, 133, 38, 11, 232, 1, 166,
-  25, 108, 61, 206, 125, 0, 199, 126, 223, 44, 11, 118, 251, 24, 113, 170, 215, 60, 83, 30, 115, 48, 169, 210, 49,
-  92, 101, 58, 21, 184, 225, 6, 199, 244, 227, 146, 99, 96, 25, 222, 65, 140, 213, 22, 219, 136, 175, 182, 73, 36,
-  141, 190, 83, 112, 137, 114, 175, 188, 187, 102, 53, 168, 193, 154, 167, 172, 3, 242, 67, 64, 7, 62, 159, 236, 75,
-  182, 187, 40, 49, 234, 105, 124, 109, 162, 205, 16, 105, 238, 143, 28, 37, 6, 85, 248, 161, 58, 121, 180, 221, 174,
-  221, 32, 217, 98, 129, 76, 149, 170, 101, 200, 239, 118, 137, 28, 179, 254, 19, 80, 183, 178, 145, 124, 251, 166, 139,
-  152, 129, 38, 153, 20, 189, 78, 3, 128, 71, 254, 95, 84, 139, 10, 123, 152, 241, 214, 169, 68, 211, 98, 13, 80,
-  215, 82, 79, 36, 229, 70, 149, 56, 159, 134, 185, 140, 99, 18, 29, 224, 153, 94, 63, 244, 85, 150, 91, 248, 209,
-  202, 55, 92, 243, 194, 211, 240, 247, 242, 209, 196, 197, 26, 75, 40, 191, 26, 39, 44, 131, 142, 195, 64, 121, 190,
-  225, 148, 53, 54, 197, 88, 79, 106, 233, 252, 19, 34, 77, 144, 233, 146, 241, 100, 91, 134, 43, 136, 33, 70, 249,
-  204, 163, 210, 163, 96, 89, 226, 1, 52, 235, 214, 27, 72, 111, 246, 247, 156, 51, 130, 109, 208, 55, 50, 17, 252,
-  123, 218, 245, 232, 255, 90, 231, 108, 195, 50, 125, 0, 199, 130, 223, 212, 11, 138, 251, 232, 143, 86, 215, 196, 83,
-  30, 141, 48, 87, 46, 207, 92, 155, 58, 235, 184, 31, 6, 199, 12, 29, 146, 157, 160, 231, 34, 191, 116, 213, 22,
-  37, 136, 175, 74, 183, 36, 115, 66, 173, 144, 137, 142, 175, 188, 69, 102, 53, 168, 193, 102, 89, 172, 253, 242, 67,
-  192, 7, 62, 159, 20, 181, 182, 187, 216, 207, 22, 105, 132, 109, 162, 205, 16, 151, 18, 113, 228, 37, 6, 85, 8,
-  161, 58, 135, 76, 35, 174, 35, 224, 39, 158, 127, 180, 149, 86, 155, 200, 239, 118, 119, 28, 77, 254, 19, 176, 183,
-  78, 145, 132, 5, 90, 117, 152, 127, 218, 153, 20, 67, 178, 3, 128, 185, 254, 95, 172, 139, 246, 123, 104, 15, 42,
-  169, 68, 211, 98, 243, 80, 41, 174, 79, 36, 27, 186, 107, 56, 97, 134, 71, 116, 157, 238, 227, 32, 153, 162, 193,
-  244, 171, 150, 165, 248, 209, 54, 55, 164, 13, 194, 45, 16, 247, 242, 47, 60, 59, 26, 75, 40, 65, 230, 217, 44,
-  131, 142, 195, 192, 121, 190, 225, 108, 203, 202, 197, 168, 177, 150, 233, 252, 19, 34, 77, 144, 23, 110, 15, 100, 91,
-  122, 213, 120, 223, 70, 7, 52, 93, 46, 93, 160, 167, 226, 255, 204, 21, 42, 229, 72, 111, 246, 9, 100, 205, 126,
-  147, 48, 55, 206, 239, 4, 133, 218, 245, 232, 255, 166, 231, 108, 195, 50, 131, 0, 57, 130, 223, 44, 245, 118, 251,
-  232, 113, 86, 215, 196, 83, 30, 141, 48, 87, 46, 207, 92, 155, 198, 235, 72, 31, 250, 57, 244, 29, 110, 99, 160,
-  231, 34, 65, 116, 43, 22, 219, 136, 175, 74, 73, 220, 141, 190, 83, 112, 137, 142, 81, 68, 69, 154, 203, 88, 63,
-  154, 89, 172, 3, 242, 67, 192, 249, 62, 159, 20, 181, 74, 69, 216, 49, 22, 105, 132, 109, 162, 205, 16, 151, 18,
-  113, 228, 219, 
-250, 171, 8, 95, 58, 135, 180, 35, 82, 221, 224, 39, 98, 129, 180, 107, 86, 101, 200, 239, 118, 119,
-  228, 179, 2, 237, 80, 183, 78, 111, 124, 5, 90, 117, 104, 127, 38, 153, 20, 67, 178, 253, 128, 185, 254, 95, 172,
-  117, 10, 123, 152, 241, 42, 87, 188, 211, 98, 243, 80, 215, 82, 79, 36, 27, 186, 107, 200, 159, 122, 71, 140, 157,
-  238, 29, 224, 153, 94, 63, 244, 85, 106, 91, 248, 47, 54, 201, 164, 243, 62, 211, 240, 247, 242, 47, 196, 197, 230,
-  181, 216, 65, 26, 217, 44, 125, 114, 195, 192, 135, 190, 31, 148, 203, 202, 59, 88, 79, 150, 233, 252, 19, 34, 77,
-  144, 233, 146, 15, 100, 165, 122, 213, 136, 223, 70, 249, 204, 93, 46, 93, 96, 167, 30, 1, 204, 21, 42, 27, 72
-};
-
-
-
-unsigned int SortArr0[NPROCS*(SIZE+200)];
-//unsigned int SortArr0[4*4*SIZE];
-
-void SORT(unsigned int *base, unsigned int n, int type);
-void insertion_sort(unsigned int *base, unsigned int n); // type 2
-void selection_sort(unsigned int *base, unsigned int n); // type 1
-void bubble_sort(unsigned int *base, unsigned int n);    // type 3
-void shellSortPhase(unsigned int a[],unsigned int length, int gap);
-void shellSort(unsigned int *base, unsigned int n);     // type 0
+#include "define.h"
+#include "common/common.h"
+#include "benchmark/benchmark.h"
+#include "irq/irq.h"
 
 int main()
 {
-  register int p; 
+  system_start();
+  
+#if TIMER_INTERRUPT
+  irq_init();
+#endif
+  
+  benchmark();
+  
+  EXIT(0);
 
-  int beg_cycle, end_cycle;
-
-  beg_cycle = cpu_cycles();
-   
-  p=procnum();
-
-  puts("Hello from processor ");
-  putchar(p+'0');
-  putchar('\n');
-
-  int i;
-  int j;
-  unsigned int* SortArray;
-
-  if(p+1 <= nprocs)
-  {
-        i=1;
-  	puts("Memory copy \n");
-        SortArray = SortArr0 + p*(SIZE+200);
-	memcpy(SortArray, gQSortNum0 + p*SIZE,SIZE*4);
- 	puts("Sort... \n");
-        SORT((unsigned int *) (SortArray), (unsigned int) SIZE, SORT_TYPE);
-
-  	for (j = 1; j < SIZE; j++)
-    	{
-	  if (SortArray[j] < SortArray[j-1])
-		{
-	  		puts("ucbqsort: failed\n");
-			while(1);
-		}
-
-    	}
-
-  	puts("ucbqsort: success\n");
-        end_cycle = cpu_cycles();
-        printf( "nombre cycles cpu : %i\n", end_cycle-beg_cycle);
-  }
-
-  
-// puts("Display the sorted array : \n");
-// for(j = 0; j < SIZE; j++)
-// {
-//   puti(SortArray[j]);
-//   putchar('\n');
-// }
-
-//  printf( "------------------------------ \n");
-//  printf( "nombre cycles cpu : %i\n", end_cycle-beg_cycle);
-//  printf( "------------------------------ \n");
-
-
-  while(1);
+  return 1;
 }
-
-
-//---- insertion sort : non adapté pour tableaux de grande taille (> 100) --
-void insertion_sort(unsigned int *base, unsigned int n) 
-{
-    /* Spécifications externes : Tri du tableau base par insertion séquentielle */
-    int i,p,j;
-    int x;
-
-    puts("Insertion Sort\n");
-
-    for (i = 1; i < n; i++) 
-    {
-
-        putchar('-'); // added for debug
-
-        /* stockage de la valeur en i */
-        x = base[i]; 
- 
-        /* recherche du plus petit indice p inférieur à i tel que base[p] >= base[i] */
-        for(p = 0; base[p] < x; p++);
-        /* p pointe une valeur de base supérieure à celle en i */ 
- 
-        /* décalage avant des valeurs de base entre p et i */         
-        for (j = i-1; j >= p; j--) {
-            base[j+1] = base[j]; 
-        }   
- 
-        base[p] = x; /* insertion de la valeur stockée à la place vacante */
-
-        putchar('+'); // added for debug
-
-    }
-}
-
-//------ simple_sort -------------------------------
-void selection_sort(unsigned int *base, unsigned int n)
-{
-     int i, min, j , x;
-     puts("Selection Sort\n");
-
-     for(i = 0 ; i < n - 1 ; i++)
-     {
-
-         putchar('-'); // added for debug
-
-         min = i;
-
-         
-         for(j = i+1 ; j < n ; j++)
-         {
-        
-            if(base[j] < base[min])
-                  min = j;
-            
-         }
-
-         if(min != i)
-         {
-             x = base[i];
-             base[i] = base[min];
-             base[min] = x;
-         }
-
-         putchar('+'); // added for debug
-
-     }
-}
-//-------------------------------
-void bubble_sort(unsigned int *base, unsigned int n)
-{
-        int i   = 0; /* Indice de répétition du tri */
- 	int j   = 0; /* Variable de boucle */
- 	int tmp = 0; /* Variable de stockage temporaire */
-        int en_desordre = 1; /* Booléen marquant l'arrêt du tri si le tableau est ordonné */
-
-        puts("Bubble Sort\n");
-
-	/* Boucle de répétition du tri et le test qui arrête le tri dès que le tableau est ordonné */
-	for(i = 0 ; (i < n) && en_desordre; i++)
-	{
-                putchar('-'); // added for debug
-
-		/* Supposons le tableau ordonné */
-		en_desordre = 0;
-		/* Vérification des éléments des places j et j-1 */
-		for(j = 1 ; j < n - i ; j++)
-		{
-			/* Si les 2 éléments sont mal triés */
-			if(base[j] < base[j-1])
-			{
-				/* Inversion des 2 éléments */
- 				tmp = base[j-1];
- 				base[j-1] = base[j];
- 				base[j] = tmp;
- 
- 				/* Le tableau n'est toujours pas trié */
-				en_desordre = 1;
- 			}
-		}
-
-                putchar('+'); // added for debug
-	}
-
-}
-//------------------------------------------------------
-/*
- * Exécute un tri par insertion avec la séparation donnée
- * If gap == 1, on fait un tri ordinaire.
- * If gap >= length, on ne fait rien.
- */
-void shellSortPhase(unsigned int a[],unsigned int length, int gap) {
-    int i;
- 
-    puti(gap);
-    for (i = gap; i < length; ++i) {
-        unsigned int value = a[i];
-        int j;
-        for (j = i - gap; j >= 0 && a[j] > value; j -= gap) {
-	    putchar('+');
-            a[j + gap] = a[j];
-	    putchar('-');
-        }
-        a[j + gap] = value;
-    }
-}
- 
-void shellSort(unsigned int *base, unsigned int n) {
-    /*
-     * gaps[] doit approximer une Série géométrique.
-     * La sequence suivante est la meilleure connue en terme
-     * de nombre moyen de comparaisons. voir:
-     * http://www.research.att.com/~njas/sequences/A102549
-     */
-    static const int gaps[] = {
-        1, 4, 10, 23, 57, 132, 301, 701
-    };
-    int sizeIndex;
- 
-    puts("Shell Sort\n");
-    for (sizeIndex = sizeof(gaps)/sizeof(gaps[0]) - 1;
-               sizeIndex >= 0;
-               --sizeIndex)
-        shellSortPhase(base, n, gaps[sizeIndex]);
-}
-
-//-------------------------------------*/
-void SORT(unsigned int *base, unsigned int n, int type)
-{
-  switch(type)
-  {
-  case 0:
-    shellSort(base, n);
-    break;
-  case 1:
-    selection_sort(base, n);
-    break;
-  case 2:
-    insertion_sort(base, n);
-    break;
-  case 3:
-    bubble_sort(base, n);
-    break;
-  default:
-    break;
-  }
-}
-
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication.c	(revision 134)
@@ -0,0 +1,67 @@
+#include "matrix_multiplication.h"
+#include "stdio.h"
+#include "system.h"
+
+void matrix_multiplication_st (int ** a,
+                               int ** b,
+                               int ** d,
+                               unsigned int n)
+{
+  int x, y;
+
+  for (x=0; x<n; ++x)
+    {
+      printf("%d, ",x);
+
+      for (y=0; y<n; ++y)
+        {
+          int i;
+
+          int tmp = 0;
+          for (i=0; i<n; ++i)
+            tmp += a[x][i] * b[i][y];
+          d[x][y] = tmp;
+        }
+    }
+  
+  printf("finish\n");
+}
+
+static int lock;
+static int next;
+
+void matrix_multiplication_mt (int ** a,
+                               int ** b,
+                               int ** d,
+                               unsigned int n,
+                               int lock_by_line)
+{
+  int x, y;
+
+  while (1)
+    {
+      lock_lock(&lock);
+      
+      x=next++;
+      
+      lock_unlock(&lock);
+
+      if (x >= n)
+        break;
+      
+      printf("%d, ",x);
+      for (y=0; y<n; ++y)
+        {
+          int line  =(lock_by_line)?x:y;
+          int column=(lock_by_line)?y:x;
+          
+          int i;
+          int tmp = 0;
+          for (i=0; i<n; ++i)
+            tmp += a[column][i] * b[i][line];
+          d[column][line] = tmp;
+        }
+    }
+  
+  printf("finish\n");
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication.h	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication.h	(revision 134)
@@ -0,0 +1,17 @@
+#ifndef matrix_multiplication_h
+#define matrix_multiplication_h
+
+void matrix_multiplication_st (int ** a,
+                               int ** b,
+                               int ** d,
+                               unsigned int n);
+
+void matrix_multiplication_mt (int ** a,
+                               int ** b,
+                               int ** d,
+                               unsigned int n,
+                               int lock_by_line);
+
+void matrix_multiplication_print (int ** m, unsigned int n);
+
+#endif // matrix_multiplication_h
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication_print.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication_print.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/matrix_multiplication/matrix_multiplication_print.c	(revision 134)
@@ -0,0 +1,13 @@
+#include "matrix_multiplication.h"
+#include "stdio.h"
+
+void matrix_multiplication_print (int ** m, unsigned int n)
+{
+  int i,j;
+  for (i=0; i<n; ++i)
+    {
+      for (j=0; j<n; ++j)
+        printf("%d ",m[i][j]);
+      printf("\n");
+    }
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort.c	(revision 134)
@@ -0,0 +1,25 @@
+#include "sort.h"
+#include "system.h"
+#include "stdio.h"
+
+//-------------------------------------*/
+void sort(unsigned int *base, unsigned int n, sort_t type)
+{
+  switch(type)
+  {
+  case SORT_SHELL:
+    sort_shell(base, n);
+    break;
+  case SORT_SELECTION:
+    sort_selection(base, n);
+    break;
+  case SORT_INSERTION:
+    sort_insertion(base, n);
+    break;
+  case SORT_BUBBLE:
+    sort_bubble(base, n);
+    break;
+  default:
+    break;
+  }
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort.h
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort.h	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort.h	(revision 134)
@@ -0,0 +1,21 @@
+#ifndef sort_h
+#define sort_h
+
+#include "../define.h"
+
+typedef enum
+  {
+    SORT_INSERTION,
+    SORT_SELECTION,
+    SORT_BUBBLE,
+    SORT_SHELL
+  } sort_t;
+
+void         sort            (unsigned int *base, unsigned int n, sort_t type);
+void         sort_insertion  (unsigned int *base, unsigned int n);
+void         sort_selection  (unsigned int *base, unsigned int n);
+void         sort_bubble     (unsigned int *base, unsigned int n);
+void         sort_shell      (unsigned int *base, unsigned int n);
+const char * sort_str        (sort_t x);
+
+#endif //sort_h
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_bubble.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_bubble.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_bubble.c	(revision 134)
@@ -0,0 +1,44 @@
+#include "sort.h"
+#include "system.h"
+#include "stdio.h"
+
+void sort_bubble(unsigned int *base, unsigned int n)
+{
+        int i   = 0; /* Indice de rÃ©pÃ©tition du tri */
+ 	int j   = 0; /* Variable de boucle */
+ 	int tmp = 0; /* Variable de stockage temporaire */
+        int en_desordre = 1; /* BoolÃ©en marquant l'arrÃªt du tri si le tableau est ordonnÃ© */
+
+	/* Boucle de rÃ©pÃ©tition du tri et le test qui arrÃªte le tri dÃšs que le tableau est ordonnÃ© */
+	for(i = 0 ; (i < n) && en_desordre; i++)
+	{
+#if VERBOSE_SORT
+                printf("-"); // added for debug
+#endif
+		/* Supposons le tableau ordonnÃ© */
+		en_desordre = 0;
+		/* VÃ©rification des Ã©lÃ©ments des places j et j-1 */
+		for(j = 1 ; j < n - i ; j++)
+		{
+			/* Si les 2 Ã©lÃ©ments sont mal triÃ©s */
+			if(base[j] < base[j-1])
+			{
+				/* Inversion des 2 Ã©lÃ©ments */
+ 				tmp = base[j-1];
+ 				base[j-1] = base[j];
+ 				base[j] = tmp;
+ 
+ 				/* Le tableau n'est toujours pas triÃ© */
+				en_desordre = 1;
+ 			}
+		}
+
+#if VERBOSE_SORT
+                printf("+"); // added for debug
+#endif
+	}
+
+#if VERBOSE_SORT
+    printf("\n");
+#endif
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_insertion.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_insertion.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_insertion.c	(revision 134)
@@ -0,0 +1,39 @@
+#include "sort.h"
+#include "system.h"
+#include "stdio.h"
+
+//---- insertion sort : non adaptÃ© pour tableaux de grande taille (> 100) --
+void sort_insertion(unsigned int *base, unsigned int n) 
+{
+    /* SpÃ©cifications externes : Tri du tableau base par insertion sÃ©quentielle */
+    int i,p,j;
+    int x;
+
+    for (i = 1; i < n; i++) 
+    {
+
+#if VERBOSE_SORT
+        printf("-"); // added for debug
+#endif
+        /* stockage de la valeur en i */
+        x = base[i]; 
+ 
+        /* recherche du plus petit indice p infÃ©rieur ÃÂ  i tel que base[p] >= base[i] */
+        for(p = 0; base[p] < x; p++);
+        /* p pointe une valeur de base supÃ©rieure ÃÂ  celle en i */ 
+ 
+        /* dÃ©calage avant des valeurs de base entre p et i */         
+        for (j = i-1; j >= p; j--) {
+            base[j+1] = base[j]; 
+        }   
+ 
+        base[p] = x; /* insertion de la valeur stockÃ©e ÃÂ  la place vacante */
+
+#if VERBOSE_SORT
+        printf("+"); // added for debug
+#endif
+    }
+#if VERBOSE_SORT
+    printf("\n");
+#endif
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_selection.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_selection.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_selection.c	(revision 134)
@@ -0,0 +1,41 @@
+#include "sort.h"
+#include "system.h"
+#include "stdio.h"
+
+//------ simple_sort -------------------------------
+void sort_selection(unsigned int *base, unsigned int n)
+{
+     int i, min, j , x;
+
+     for(i = 0 ; i < n - 1 ; i++)
+     {
+
+#if VERBOSE_SORT
+         printf("-"); // added for debug
+#endif
+
+         min = i;
+         
+         for(j = i+1 ; j < n ; j++)
+         {
+        
+            if(base[j] < base[min])
+                  min = j;
+            
+         }
+
+         if(min != i)
+         {
+             x = base[i];
+             base[i] = base[min];
+             base[min] = x;
+         }
+
+#if VERBOSE_SORT
+         printf("+"); // added for debug
+#endif
+     }
+#if VERBOSE_SORT
+    printf("\n");
+#endif
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_shell.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_shell.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_shell.c	(revision 134)
@@ -0,0 +1,50 @@
+#include "sort.h"
+#include "system.h"
+#include "stdio.h"
+
+//------------------------------------------------------
+/*
+ * ExÃ©cute un tri par insertion avec la sÃ©paration donnÃ©e
+ * If gap == 1, on fait un tri ordinaire.
+ * If gap >= length, on ne fait rien.
+ */
+void sort_shell_phase(unsigned int a[],unsigned int length, int gap) {
+    int i;
+ 
+    /* puti(gap); */
+    for (i = gap; i < length; ++i) {
+        unsigned int value = a[i];
+        int j;
+        for (j = i - gap; j >= 0 && a[j] > value; j -= gap) {
+#if VERBOSE_SORT
+	    printf("+");
+#endif
+            a[j + gap] = a[j];
+#if VERBOSE_SORT
+	    printf("-");
+#endif
+        }
+        a[j + gap] = value;
+    }
+}
+ 
+void sort_shell(unsigned int *base, unsigned int n) {
+    /*
+     * gaps[] doit approximer une SÃ©rie gÃ©omÃ©trique.
+     * La sequence suivante est la meilleure connue en terme
+     * de nombre moyen de comparaisons. voir:
+     * http://www.research.att.com/~njas/sequences/A102549
+     */
+    static const int gaps[] = {
+        1, 4, 10, 23, 57, 132, 301, 701
+    };
+    int sizeIndex;
+ 
+    for (sizeIndex = sizeof(gaps)/sizeof(gaps[0]) - 1;
+               sizeIndex >= 0;
+               --sizeIndex)
+        sort_shell_phase(base, n, gaps[sizeIndex]);
+#if VERBOSE_SORT
+    printf("\n");
+#endif
+}
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_str.c
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_str.c	(revision 134)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/soft/sort/sort_str.c	(revision 134)
@@ -0,0 +1,16 @@
+#include "sort.h"
+#include "stdio.h"
+
+static const char * sort_type_str [] = 
+  {
+    "insertion sort",
+    "selection sort",
+    "bubble sort",
+    "shell sort"
+  };
+
+const char * sort_str (sort_t x)
+{
+  return sort_type_str[x];
+}
+
Index: /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/top.cpp
===================================================================
--- /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/top.cpp	(revision 133)
+++ /trunk/platforms/caba-ring-ccxcachev4_memcachev4-mips32el/top.cpp	(revision 134)
@@ -1,27 +1,171 @@
-
 #include <systemc>
 #include <sys/time.h>
 #include <iostream>
+#include <sstream>
 #include <cstdlib>
 #include <cstdarg>
+#include <stdint.h>
+#include <fstream>
 
 #include "mapping_table.h"
 #include "mips32.h"
+#include "vci_simhelper.h"
 #include "vci_simple_ram.h"
 #include "vci_multi_tty.h"
+#include "vci_xicu.h"
 #include "vci_simple_ring_network_2.h"
 #include "vci_vgmn.h"
 #include "vci_mem_cache_v4.h"
 #include "vci_cc_xcache_wrapper_v4.h"
-#include "vci_logger.h"
+#include "alloc_elems.h"
 
 #include "iss/gdbserver.h"
 
-//#define  VCI_LOGGER
 #include "segmentation.h"
-#define USE_VGMN
+
+//===========================================
+// Define before include
+//===========================================
+
+// Parameters
+// * Platforms
+#  define PARAM_VCI                         4,8,32,1,1,1,8,4,4,1
+
+#  define USE_OLD_XCACHE                    1
+#  define USE_VGMN                          1
+#  define NB_PROC_MIN                       1
+#  define NB_PROC_MAX                       15
+//                                          min_latency, fifo_depth
+#  define PARAM_VGMN_P                      1          , 8
+#  define PARAM_VGMN_C                      1          , 8
+#  define PARAM_VGMN_X                      2          , 8
+//                                          wrapper_fifo_depth
+#  define PARAM_RING_P                      2
+#  define PARAM_RING_C                      2
+#  define PARAM_RING_X                      2
+//                                          pti    , hwi    , wti, irq
+#  define PARAM_XICU                        nb_proc, nb_proc, 0  , nb_proc
+
+// * Debug
+#  define DEBUG_TOP                         0
+#  define SOCVIEW                           0
+#  define STOP_SIMULATION_NB_FRZ_CYCLES     100000
+                                            
+// * Simulation                             
+#  define FILE_DEFAULT                      "configuration/default.cfg"
+#  define NCYCLES_DEFAULT                   0
+#  define SOFT_DEFAULT                      "soft/bin.soft"
+//===========================================
+
+void usage (char * funcname)
+{
+  std::cout << funcname << " [nb_cycle [file [soft]]] " << std::endl;
+  std::cout << " * nb_cycle : number of simulated cycle, if 0 then no stop condition. (default : " << NCYCLES_DEFAULT << " cycle(s))" << endl;
+  std::cout << " * file     : Configuration file : nb_proc, iways, isets, iwords, dways, dsets, dwords, wnwords, wnlines, wtimeout, memc_nways, memc_nsets, memc_words, memc_heap_size. (default : " << FILE_DEFAULT << " cycle(s))" << endl;
+  std::cout << " * soft     : software executed by this platforms. (default : \"" << SOFT_DEFAULT << "\")" << endl;
+
+  exit(1);
+}
 
 int _main(int argc, char *argv[])
 {
+        if ((argc < 1) or (argc > 4))
+          {
+            std::cout << "Invalid parameters number." << std::endl;
+            usage(argv[0]);
+          }
+
+#if not SOCVIEW
+	int  ncycles = 0;
+
+	if (argc >= 2)
+          ncycles = std::atoi(argv[1]);
+        else
+          ncycles = NCYCLES_DEFAULT;
+
+        if (ncycles == 0)
+          ncycles = -1;
+#endif
+
+        uint32_t nb_proc;
+        uint32_t iways, isets, iwords;
+        uint32_t dways, dsets, dwords;
+        uint32_t wnwords, wnlines, wtimeout;
+        uint32_t memc_nways, memc_nsets, memc_words, memc_heap_size;
+
+        std::ifstream inFile;
+        const char * filename = (argc>=3)?argv[2]:FILE_DEFAULT;
+
+        inFile.open(filename);
+        
+        if (!inFile) 
+          {
+            std::cout << "Can't open file : \"" << filename << "\"." << std::endl;
+            usage(argv[0]);
+          }
+
+        std::string str;
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        nb_proc         =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        iways           =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        isets           =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        iwords          =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        dways           =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        dsets           =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        dwords          =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        wnwords         =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        wnlines         =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        wtimeout        =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        memc_nways      =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        memc_nsets      =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        memc_words      =std::atoi(str.c_str());
+        if (not (inFile >> str)){std::cout << "Invalid parameters number in configuration file." << std::endl; usage(argv[0]);}
+        memc_heap_size  =std::atoi(str.c_str());
+
+        if ((nb_proc<NB_PROC_MIN) or
+            (nb_proc>NB_PROC_MAX))
+          {
+            std::cout << "Parameters nb_proc is out of bound." << std::endl;
+            usage(argv[0]);
+          }
+
+        char * soft;
+
+        if (argc >= 4)
+          soft = argv[3];
+        else
+          soft = SOFT_DEFAULT;
+
+        std::cout << "  * Parameters : " << std::endl;
+        std::cout << "    * nb_proc          : " << nb_proc          << std::endl;
+        std::cout << "    * iways            : " << iways            << std::endl;
+        std::cout << "    * isets            : " << isets            << std::endl;
+        std::cout << "    * iwords           : " << iwords           << std::endl;
+        std::cout << "    * dways            : " << dways            << std::endl;
+        std::cout << "    * dsets            : " << dsets            << std::endl;
+        std::cout << "    * dwords           : " << dwords           << std::endl;
+        std::cout << "    * wnwords          : " << wnwords          << std::endl;
+        std::cout << "    * wnlines          : " << wnlines          << std::endl;
+        std::cout << "    * wtimeout         : " << wtimeout         << std::endl;
+        std::cout << "    * memc_nways       : " << memc_nways       << std::endl;
+        std::cout << "    * memc_nsets       : " << memc_nsets       << std::endl;
+        std::cout << "    * memc_words       : " << memc_words       << std::endl;
+        std::cout << "    * memc_heap_size   : " << memc_heap_size   << std::endl;
+        std::cout << "  * Simulation : " << std::endl;
+        std::cout << "    * ncycles          : " << ncycles          << std::endl;
+        std::cout << "    * soft             : " << soft             << std::endl;
+
 	using namespace sc_core;
 	// Avoid repeating these everywhere
@@ -30,31 +174,36 @@
 
 	// Define VCI parameters
-	typedef soclib::caba::VciParams<4,8,32,1,1,1,8,4,4,1> vci_param;
+	typedef soclib::caba::VciParams<PARAM_VCI> vci_param;
 	typedef soclib::common::GdbServer<soclib::common::Mips32ElIss> proc_iss;
 	// Mapping table
 
-	soclib::common::MappingTable maptabp(32, IntTab(8), IntTab(8), 0x00300000);
-
-	maptabp.add(Segment("reset", RESET_BASE, RESET_SIZE, IntTab(2), true));
-	maptabp.add(Segment("excep", EXCEP_BASE, EXCEP_SIZE, IntTab(2), true));
-	maptabp.add(Segment("text" , TEXT_BASE , TEXT_SIZE , IntTab(2), true));
-	maptabp.add(Segment("tty"  , TTY_BASE  , TTY_SIZE  , IntTab(1), false));
-	maptabp.add(Segment("mc_r" , MC_R_BASE , MC_R_SIZE , IntTab(2), false, true, IntTab(0)));
-	maptabp.add(Segment("mc_m" , MC_M_BASE , MC_M_SIZE , IntTab(2), true ));
-	maptabp.add(Segment("ptba" , PTD_ADDR , TAB_SIZE   , IntTab(2), true));
+	soclib::common::MappingTable maptabp(32, IntTab(8), IntTab(8), 0x00300000); // size, level_addr_bits, level_id_bits, cacheability_mask
+
+	maptabp.add(Segment("reset"    , RESET_BASE    , RESET_SIZE    , IntTab(2), true));
+	maptabp.add(Segment("excep"    , EXCEP_BASE    , EXCEP_SIZE    , IntTab(2), true));
+
+	maptabp.add(Segment("tty"      , TTY_BASE      , TTY_SIZE      , IntTab(1), false));
+	maptabp.add(Segment("text"     , TEXT_BASE     , TEXT_SIZE     , IntTab(2), true));
+	maptabp.add(Segment("mc_r"     , MC_R_BASE     , MC_R_SIZE     , IntTab(2), false, true, IntTab(0)));
+	maptabp.add(Segment("mc_m"     , MC_M_BASE     , MC_M_SIZE     , IntTab(2), true));
+	// maptabp.add(Segment("ptba"     , PTD_ADDR      , TAB_SIZE      , IntTab(2), true));
+	maptabp.add(Segment("xicu"     , XICU_BASE     , XICU_SIZE     , IntTab(3), false));
+	maptabp.add(Segment("simhelper", SIMHELPER_BASE, SIMHELPER_SIZE, IntTab(4), false));
  
 	std::cout << maptabp << std::endl;
 
         soclib::common::MappingTable maptabc(32, IntTab(8), IntTab(8), 0x00300000);
-	maptabc.add(Segment("c_proc0" , C_PROC0_BASE , C_PROC0_SIZE , IntTab(0), false, true, IntTab(0)));
-	maptabc.add(Segment("c_proc1" , C_PROC1_BASE , C_PROC1_SIZE , IntTab(1), false, true, IntTab(1)));
-	maptabc.add(Segment("c_proc2" , C_PROC2_BASE , C_PROC2_SIZE , IntTab(2), false, true, IntTab(2)));
-	maptabc.add(Segment("c_proc3" , C_PROC3_BASE , C_PROC3_SIZE , IntTab(3), false, true, IntTab(3)));
-	maptabc.add(Segment("mc_r"    , MC_R_BASE , MC_R_SIZE , IntTab(4), false, false));
-	maptabc.add(Segment("mc_m"  , MC_M_BASE , MC_M_SIZE  , IntTab(4), false, false));
-	maptabc.add(Segment("reset", RESET_BASE, RESET_SIZE, IntTab(4), false, false));
-	maptabc.add(Segment("excep", EXCEP_BASE, EXCEP_SIZE, IntTab(4), false, false));
-	maptabc.add(Segment("text" , TEXT_BASE , TEXT_SIZE , IntTab(4), false, false));
-	maptabc.add(Segment("ptba" , PTD_ADDR  , TAB_SIZE  , IntTab(4), false, false));
+        for (uint32_t i=0; i<nb_proc; ++i)
+        {
+          std::ostringstream str;
+          str << "c_proc_" << i;
+          maptabc.add(Segment(str.str().c_str(), C_PROC_BASE+i*C_PROC_SPAN, C_PROC_SIZE , IntTab(i), false, true, IntTab(i)));
+        }
+	maptabc.add(Segment("mc_r"    , MC_R_BASE  , MC_R_SIZE   , IntTab(nb_proc), false, false));
+	maptabc.add(Segment("mc_m"    , MC_M_BASE  , MC_M_SIZE   , IntTab(nb_proc), false, false));
+	maptabc.add(Segment("reset"   , RESET_BASE , RESET_SIZE  , IntTab(nb_proc), false, false));
+	maptabc.add(Segment("excep"   , EXCEP_BASE , EXCEP_SIZE  , IntTab(nb_proc), false, false));
+	maptabc.add(Segment("text"    , TEXT_BASE  , TEXT_SIZE   , IntTab(nb_proc), false, false));
+	// maptabc.add(Segment("ptba"    , PTD_ADDR   , TAB_SIZE    , IntTab(nb_proc), false, false));
 
 	std::cout << maptabc << std::endl;
@@ -65,5 +214,5 @@
 	maptabx.add(Segment("excep", EXCEP_BASE, EXCEP_SIZE, IntTab(0), false));
 	maptabx.add(Segment("text" , TEXT_BASE , TEXT_SIZE , IntTab(0), false));
-	maptabx.add(Segment("ptba" , PTD_ADDR  , TAB_SIZE  , IntTab(0), false));
+	// maptabx.add(Segment("ptba" , PTD_ADDR  , TAB_SIZE  , IntTab(0), false));
 	
 	std::cout << maptabx << std::endl;
@@ -73,57 +222,19 @@
 	sc_signal<bool> signal_resetn("resetn");
    
-	sc_signal<bool> signal_proc0_it0("proc0_it0"); 
-	sc_signal<bool> signal_proc0_it1("proc0_it1"); 
-	sc_signal<bool> signal_proc0_it2("proc0_it2"); 
-	sc_signal<bool> signal_proc0_it3("proc0_it3"); 
-	sc_signal<bool> signal_proc0_it4("proc0_it4"); 
-	sc_signal<bool> signal_proc0_it5("proc0_it5");
-
-	sc_signal<bool> signal_proc1_it0("proc1_it0"); 
-	sc_signal<bool> signal_proc1_it1("proc1_it1"); 
-	sc_signal<bool> signal_proc1_it2("proc1_it2"); 
-	sc_signal<bool> signal_proc1_it3("proc1_it3"); 
-	sc_signal<bool> signal_proc1_it4("proc1_it4"); 
-	sc_signal<bool> signal_proc1_it5("proc1_it5");
-
-	sc_signal<bool> signal_proc2_it0("proc2_it0"); 
-	sc_signal<bool> signal_proc2_it1("proc2_it1"); 
-	sc_signal<bool> signal_proc2_it2("proc2_it2"); 
-	sc_signal<bool> signal_proc2_it3("proc2_it3"); 
-	sc_signal<bool> signal_proc2_it4("proc2_it4"); 
-	sc_signal<bool> signal_proc2_it5("proc2_it5");
-
-	sc_signal<bool> signal_proc3_it0("proc3_it0"); 
-	sc_signal<bool> signal_proc3_it1("proc3_it1"); 
-	sc_signal<bool> signal_proc3_it2("proc3_it2"); 
-	sc_signal<bool> signal_proc3_it3("proc3_it3"); 
-	sc_signal<bool> signal_proc3_it4("proc3_it4"); 
-	sc_signal<bool> signal_proc3_it5("proc3_it5");
-
-	soclib::caba::VciSignals<vci_param> signal_vci_ini_rw_proc0("vci_ini_rw_proc0");
-	soclib::caba::VciSignals<vci_param> signal_vci_ini_c_proc0("vci_ini_c_proc0");
-
-	soclib::caba::VciSignals<vci_param> signal_vci_tgt_proc0("vci_tgt_proc0");
-
-	soclib::caba::VciSignals<vci_param> signal_vci_ini_rw_proc1("vci_ini_rw_proc1");
-	soclib::caba::VciSignals<vci_param> signal_vci_ini_c_proc1("vci_ini_c_proc1");
-
-	soclib::caba::VciSignals<vci_param> signal_vci_tgt_proc1("vci_tgt_proc1");
-
-	soclib::caba::VciSignals<vci_param> signal_vci_ini_rw_proc2("vci_ini_rw_proc2");
-	soclib::caba::VciSignals<vci_param> signal_vci_ini_c_proc2("vci_ini_c_proc2");
-
-	soclib::caba::VciSignals<vci_param> signal_vci_tgt_proc2("vci_tgt_proc2");
-
-	soclib::caba::VciSignals<vci_param> signal_vci_ini_rw_proc3("vci_ini_rw_proc3");
-	soclib::caba::VciSignals<vci_param> signal_vci_ini_c_proc3("vci_ini_c_proc3");
-
-	soclib::caba::VciSignals<vci_param> signal_vci_tgt_proc3("vci_tgt_proc3");
+	sc_signal<bool> ** signal_proc_it = soclib::common::alloc_elems<sc_signal<bool> >("proc_it", nb_proc, 6);
+
+	soclib::caba::VciSignals<vci_param> * signal_vci_ini_rw_proc = soclib::common::alloc_elems<soclib::caba::VciSignals<vci_param> >("vci_ini_rw_proc", nb_proc);
+	soclib::caba::VciSignals<vci_param> * signal_vci_ini_c_proc  = soclib::common::alloc_elems<soclib::caba::VciSignals<vci_param> >("vci_ini_c_proc" , nb_proc);
+	soclib::caba::VciSignals<vci_param> * signal_vci_tgt_proc    = soclib::common::alloc_elems<soclib::caba::VciSignals<vci_param> >("vci_tgt_proc"   , nb_proc);
 
 	soclib::caba::VciSignals<vci_param> signal_vci_tgt_tty("vci_tgt_tty");
 
+	soclib::caba::VciSignals<vci_param> signal_vci_tgt_simhelper("signal_vci_tgt_simhelper");
+
 	soclib::caba::VciSignals<vci_param> signal_vci_tgt_rom("vci_tgt_rom");
 
 	soclib::caba::VciSignals<vci_param> signal_vci_tgt_xram("vci_tgt_xram");
+
+	soclib::caba::VciSignals<vci_param> signal_vci_tgt_xicu("vci_tgt_xicu");
 
 	soclib::caba::VciSignals<vci_param> signal_vci_ixr_memc("vci_ixr_memc");
@@ -132,126 +243,103 @@
 	soclib::caba::VciSignals<vci_param> signal_vci_tgt_cleanup_memc("vci_tgt_cleanup_memc");
 
-	sc_signal<bool> signal_tty_irq0("signal_tty_irq0"); 
-	sc_signal<bool> signal_tty_irq1("signal_tty_irq1"); 
-	sc_signal<bool> signal_tty_irq2("signal_tty_irq2"); 
-	sc_signal<bool> signal_tty_irq3("signal_tty_irq3"); 
-
-	soclib::common::Loader loader("soft/bin.soft");
-
-    soclib::common::GdbServer<soclib::common::Mips32ElIss>::set_loader(loader);
-        //                                  init_rw   init_c   tgt
-/*	soclib::caba::VciCcXCacheWrapperV1<vci_param, proc_iss > 
-	proc0("proc0", 0, maptabp, maptabc, IntTab(0),IntTab(0),IntTab(0),4,64,16,4,64,16);
-
-	soclib::caba::VciCcXCacheWrapperV1<vci_param, proc_iss > 
-	proc1("proc1", 1, maptabp, maptabc, IntTab(1),IntTab(1),IntTab(1),4,64,16,4,64,16);
-
-	soclib::caba::VciCcXCacheWrapperV1<vci_param, proc_iss > 
-	proc2("proc2", 2, maptabp, maptabc, IntTab(2),IntTab(2),IntTab(2),4,64,16,4,64,16);
-
-	soclib::caba::VciCcXCacheWrapperV1<vci_param, proc_iss > 
-	proc3("proc3", 3, maptabp, maptabc, IntTab(3),IntTab(3),IntTab(3),4,64,16,4,64,16);
-*/
-
-	soclib::caba::VciCcXCacheWrapperV4<vci_param, proc_iss > 
-	proc0("proc0", 0, maptabp, maptabc, IntTab(0),IntTab(0),IntTab(0),1,8,16,1,8,16);
-
-	soclib::caba::VciCcXCacheWrapperV4<vci_param, proc_iss > 
-	proc1("proc1", 1, maptabp, maptabc, IntTab(1),IntTab(1),IntTab(1),1,8,16,1,8,16);
-
-	soclib::caba::VciCcXCacheWrapperV4<vci_param, proc_iss > 
-	proc2("proc2", 2, maptabp, maptabc, IntTab(2),IntTab(2),IntTab(2),1,8,16,1,8,16);
-
-	soclib::caba::VciCcXCacheWrapperV4<vci_param, proc_iss > 
-	proc3("proc3", 3, maptabp, maptabc, IntTab(3),IntTab(3),IntTab(3),1,8,16,1,8,16);
-
+	sc_signal<bool> * signal_tty_irq = soclib::common::alloc_elems<sc_signal<bool> >("signal_tty_irq", nb_proc);
+
+	soclib::common::Loader loader(soft);
+
+        soclib::common::GdbServer<soclib::common::Mips32ElIss>::set_loader(loader);
+
+	soclib::caba::VciCcXCacheWrapperV4<vci_param, proc_iss > * proc [nb_proc];
+        for (uint32_t i=0; i<nb_proc; ++i)
+          {
+            std::ostringstream str;
+            str << "proc_" << i;
+
+            proc[i] = new soclib::caba::VciCcXCacheWrapperV4<vci_param, proc_iss > (str.str().c_str(), i, maptabp, maptabc, IntTab(i),IntTab(i),IntTab(i)
+#if USE_OLD_XCACHE
+                                                                                    ,iways, isets, iwords
+                                                                                    ,dways, dsets, dwords
+#else
+                                                                                    ,iways, isets, iwords
+                                                                                    ,dways, dsets, dwords
+                                                                                    ,wnwords, wnlines, wtimeout
+#endif
+                                                                                    );
+
+#if not USE_OLD_XCACHE
+            proc[i]->stop_simulation(STOP_SIMULATION_NB_FRZ_CYCLES);
+#endif
+          }
 
 	soclib::caba::VciSimpleRam<vci_param> 
-	rom("rom", IntTab(0), maptabp, loader);
+	rom ("rom", IntTab(0), maptabp, loader);
 
 	soclib::caba::VciSimpleRam<vci_param> 
 	xram("xram", IntTab(0), maptabx, loader);
 
-        //                                  x_init    c_init    p_tgt     c_tgt
+        //                                  x_init    c_init          p_tgt     c_tgt
 	soclib::caba::VciMemCacheV4<vci_param> 
-	//memc("memc",maptabp,maptabc,maptabx,IntTab(0),IntTab(4),IntTab(2), IntTab(4),16,256,16);
-	//memc("memc",maptabp,maptabc,maptabx,IntTab(0),IntTab(4),IntTab(2), IntTab(4),4,16,16);
-	memc("memc",maptabp,maptabc,maptabx,IntTab(0),IntTab(4),IntTab(2), IntTab(4),4,4,16);
+          memc("memc",maptabp,maptabc,maptabx,IntTab(0),IntTab(nb_proc),IntTab(2),IntTab(nb_proc), memc_nways, memc_nsets, memc_words, memc_heap_size);
+
+        std::vector<std::string> tty_name;
+        for (uint32_t i=0; i<nb_proc; ++i)
+          {
+            std::ostringstream str;
+            str << "tty_" << i;
+
+            tty_name.push_back(str.str());
+          }
 	
 	soclib::caba::VciMultiTty<vci_param> 
-	tty("tty",IntTab(1),maptabp,"tty0","tty1","tty2","tty3",NULL);
-
-#ifdef VCI_LOGGER
-  soclib::caba::VciLogger<vci_param> vci_logger0("vci_logger0",maptabp);
+	tty("tty",IntTab(1),maptabp,tty_name);
+
+        soclib::caba::VciXicu<vci_param> 
+        xicu("xicu", maptabp, IntTab(3), PARAM_XICU);
+
+	// soclib::caba::VciTimer<vci_param> 
+        // timer("timer", IntTab(3), maptabp, nb_proc);
+
+	soclib::caba::VciSimhelper<vci_param> 
+        simhelper("simhelper", IntTab(4), maptabp);
+
+        //                  initiatior | target 
+        // interconnect_p : proc       | rom, tty, memc, xicu, simhelper
+        // interconnect_c : proc, memc | proc, memc
+        // interconnect_x : memc       | xram
+
+#if USE_VGMN
+	soclib::caba::VciVgmn<vci_param> 
+        interconnect_p("interconnect_p",maptabp, nb_proc  , 5        , PARAM_VGMN_P);
+
+	soclib::caba::VciVgmn<vci_param> 
+        interconnect_c("interconnect_c",maptabc, nb_proc+1, nb_proc+1, PARAM_VGMN_C);
+
+	soclib::caba::VciVgmn<vci_param> 
+        interconnect_x("interconnect_x",maptabx, 1        , 1        , PARAM_VGMN_X);
+#else
+	soclib::caba::VciSimpleRingNetwork2<vci_param,37,33> 
+	interconnect_p("interconnect_p",maptabp, IntTab(), PARAM_RING_P,nb_proc  , 5        );
+
+	soclib::caba::VciSimpleRingNetwork2<vci_param,37,33>
+	interconnect_c("interconnect_c",maptabc, IntTab(), PARAM_RING_C,nb_proc+1, nb_proc+1);
+
+	soclib::caba::VciSimpleRingNetwork2<vci_param,37,33>
+	interconnect_x("interconnect_x",maptabx, IntTab(), PARAM_RING_X,1        , 1        );
 #endif
-#ifdef USE_VGMN
-	soclib::caba::VciVgmn<vci_param> 
-	ringp("ringp",maptabp, 4, 3, 1, 8);
-
-	soclib::caba::VciVgmn<vci_param> 
-	ringc("ringc",maptabc, 5, 5, 1, 8);
-
-	soclib::caba::VciVgmn<vci_param> 
-	ringx("ringx",maptabx, 1, 1, 2, 8);
-#else
-
-	soclib::caba::VciSimpleRingNetwork2<vci_param,37,33> 
-	ringp("ringp",maptabp, IntTab(), 2, 4, 3);
-
-	soclib::caba::VciSimpleRingNetwork2<vci_param,37,33> 
-	ringc("ringc",maptabc, IntTab(), 2, 5, 5);
-
-	soclib::caba::VciSimpleRingNetwork2<vci_param,37,33> 
-	ringx("ringx",maptabx, IntTab(), 2, 1, 1);
-#endif
+
 	// Net-List
- 
-	proc0.p_clk(signal_clk);  
-	proc0.p_resetn(signal_resetn);  
-	proc0.p_irq[0](signal_proc0_it0); 
-	proc0.p_irq[1](signal_proc0_it1); 
-	proc0.p_irq[2](signal_proc0_it2); 
-	proc0.p_irq[3](signal_proc0_it3); 
-	proc0.p_irq[4](signal_proc0_it4); 
-	proc0.p_irq[5](signal_proc0_it5); 
-	proc0.p_vci_ini_rw(signal_vci_ini_rw_proc0);
-	proc0.p_vci_ini_c(signal_vci_ini_c_proc0);
-	proc0.p_vci_tgt(signal_vci_tgt_proc0);
-
-	proc1.p_clk(signal_clk);  
-	proc1.p_resetn(signal_resetn);  
-	proc1.p_irq[0](signal_proc1_it0); 
-	proc1.p_irq[1](signal_proc1_it1); 
-	proc1.p_irq[2](signal_proc1_it2); 
-	proc1.p_irq[3](signal_proc1_it3); 
-	proc1.p_irq[4](signal_proc1_it4); 
-	proc1.p_irq[5](signal_proc1_it5); 
-	proc1.p_vci_ini_rw(signal_vci_ini_rw_proc1);
-	proc1.p_vci_ini_c(signal_vci_ini_c_proc1);
-	proc1.p_vci_tgt(signal_vci_tgt_proc1);
-
-	proc2.p_clk(signal_clk);  
-	proc2.p_resetn(signal_resetn);  
-	proc2.p_irq[0](signal_proc2_it0); 
-	proc2.p_irq[1](signal_proc2_it1); 
-	proc2.p_irq[2](signal_proc2_it2); 
-	proc2.p_irq[3](signal_proc2_it3); 
-	proc2.p_irq[4](signal_proc2_it4); 
-	proc2.p_irq[5](signal_proc2_it5); 
-	proc2.p_vci_ini_rw(signal_vci_ini_rw_proc2);
-	proc2.p_vci_ini_c(signal_vci_ini_c_proc2);
-	proc2.p_vci_tgt(signal_vci_tgt_proc2);
-
-	proc3.p_clk(signal_clk);  
-	proc3.p_resetn(signal_resetn);  
-	proc3.p_irq[0](signal_proc3_it0); 
-	proc3.p_irq[1](signal_proc3_it1); 
-	proc3.p_irq[2](signal_proc3_it2); 
-	proc3.p_irq[3](signal_proc3_it3); 
-	proc3.p_irq[4](signal_proc3_it4); 
-	proc3.p_irq[5](signal_proc3_it5); 
-	proc3.p_vci_ini_rw(signal_vci_ini_rw_proc3);
-	proc3.p_vci_ini_c(signal_vci_ini_c_proc3);
-	proc3.p_vci_tgt(signal_vci_tgt_proc3);
+        for (uint32_t i=0; i<nb_proc; ++i)
+          {
+            proc[i]->p_clk(signal_clk);  
+            proc[i]->p_resetn(signal_resetn);  
+            proc[i]->p_irq[0](signal_proc_it[i][0]); 
+            proc[i]->p_irq[1](signal_proc_it[i][1]); 
+            proc[i]->p_irq[2](signal_proc_it[i][2]); 
+            proc[i]->p_irq[3](signal_proc_it[i][3]); 
+            proc[i]->p_irq[4](signal_proc_it[i][4]); 
+            proc[i]->p_irq[5](signal_proc_it[i][5]); 
+            proc[i]->p_vci_ini_rw(signal_vci_ini_rw_proc[i]);
+            proc[i]->p_vci_ini_c(signal_vci_ini_c_proc[i]);
+            proc[i]->p_vci_tgt(signal_vci_tgt_proc[i]);
+          }
 
 	rom.p_clk(signal_clk);
@@ -259,17 +347,22 @@
 	rom.p_vci(signal_vci_tgt_rom);
 
-#ifdef VCI_LOGGER
-  vci_logger0.p_clk(signal_clk);
-  vci_logger0.p_resetn(signal_resetn);
-  vci_logger0.p_vci(signal_vci_ini_rw_proc2);
-#endif
-
 	tty.p_clk(signal_clk);
 	tty.p_resetn(signal_resetn);
 	tty.p_vci(signal_vci_tgt_tty);
-	tty.p_irq[0](signal_tty_irq0); 
-	tty.p_irq[1](signal_tty_irq1); 
-	tty.p_irq[2](signal_tty_irq2); 
-	tty.p_irq[3](signal_tty_irq3); 
+        for (uint32_t i=0; i<nb_proc; ++i)
+          tty.p_irq[i](signal_tty_irq[i]); 
+
+        xicu.p_clk(signal_clk);
+        xicu.p_resetn(signal_resetn);
+        xicu.p_vci(signal_vci_tgt_xicu);
+        for (uint32_t i=0; i<nb_proc; ++i)
+        {
+          xicu.p_hwi[i](signal_tty_irq[i]);
+          xicu.p_irq[i](signal_proc_it[i][0]); 
+        }
+
+        simhelper.p_clk(signal_clk);
+        simhelper.p_resetn(signal_resetn);
+        simhelper.p_vci(signal_vci_tgt_simhelper);
 
 	memc.p_clk(signal_clk);
@@ -281,83 +374,37 @@
 
 	xram.p_clk(signal_clk);
-  xram.p_resetn(signal_resetn);
+	xram.p_resetn(signal_resetn);
 	xram.p_vci(signal_vci_tgt_xram);
-	
-	ringp.p_clk(signal_clk);
-	ringp.p_resetn(signal_resetn);
-
-	ringc.p_clk(signal_clk);
-	ringc.p_resetn(signal_resetn);
-
-	ringx.p_clk(signal_clk);
-	ringx.p_resetn(signal_resetn);
-
-	ringp.p_to_initiator[0](signal_vci_ini_rw_proc0);
-	ringp.p_to_initiator[1](signal_vci_ini_rw_proc1);
-	ringp.p_to_initiator[2](signal_vci_ini_rw_proc2);
-	ringp.p_to_initiator[3](signal_vci_ini_rw_proc3);
-
-	ringc.p_to_initiator[4](signal_vci_ini_memc);
-	ringc.p_to_initiator[0](signal_vci_ini_c_proc0);
-	ringc.p_to_initiator[1](signal_vci_ini_c_proc1);
-	ringc.p_to_initiator[2](signal_vci_ini_c_proc2);
-	ringc.p_to_initiator[3](signal_vci_ini_c_proc3);
-
-	ringx.p_to_initiator[0](signal_vci_ixr_memc);
-
-	ringp.p_to_target[0](signal_vci_tgt_rom);
-	ringp.p_to_target[1](signal_vci_tgt_tty);
-	ringp.p_to_target[2](signal_vci_tgt_memc);
-
-	ringc.p_to_target[0](signal_vci_tgt_proc0);
-	ringc.p_to_target[1](signal_vci_tgt_proc1);
-	ringc.p_to_target[2](signal_vci_tgt_proc2);
-	ringc.p_to_target[3](signal_vci_tgt_proc3);
-	ringc.p_to_target[4](signal_vci_tgt_cleanup_memc);
-
-	ringx.p_to_target[0](signal_vci_tgt_xram);
-
-	int ncycles;
-
-#ifndef SOCVIEW
-/*	if (argc == 2) {
-		ncycles = std::atoi(argv[1]);
-	} else {
-		std::cerr
-			<< std::endl
-			<< "The number of simulation cycles must "
-			   "be defined in the command line"
-			<< std::endl;
-		exit(1);
-	}
-*/
-	sc_start(sc_core::sc_time(0, SC_NS));
-	signal_resetn = false;
-
-	sc_start(sc_core::sc_time(1, SC_NS));
-	signal_resetn = true;
-
-/*
-  while(1){
-    char buf[2];
-	  std::cin.getline(buf,1);
-		sc_start(sc_core::sc_time(1, SC_NS));
-  }
-*/
-
-	for (int i = 0; ; i+=10000) {
-		sc_start(sc_core::sc_time(10000, SC_NS));
-//		proc0.print_stats();
-//		memc.print_stats();
-	}
-
-        std::cout << "Hit ENTER to end simulation" << std::endl;
-        char buf[1];
-
-	std::cin.getline(buf,1);
-
-	return EXIT_SUCCESS;
-#else
-	ncycles = 1;
+        
+	interconnect_p.p_clk(signal_clk);
+	interconnect_p.p_resetn(signal_resetn);
+
+        for (uint32_t i=0; i<nb_proc; ++i)
+        interconnect_p.p_to_initiator[i](signal_vci_ini_rw_proc[i]);
+
+	interconnect_p.p_to_target[0](signal_vci_tgt_rom);
+	interconnect_p.p_to_target[1](signal_vci_tgt_tty);
+	interconnect_p.p_to_target[2](signal_vci_tgt_memc);
+	interconnect_p.p_to_target[3](signal_vci_tgt_xicu);
+	interconnect_p.p_to_target[4](signal_vci_tgt_simhelper);
+
+	interconnect_c.p_clk(signal_clk);
+	interconnect_c.p_resetn(signal_resetn);
+
+        for (uint32_t i=0; i<nb_proc; ++i)
+	interconnect_c.p_to_initiator[i](signal_vci_ini_c_proc[i]);
+	interconnect_c.p_to_initiator[nb_proc](signal_vci_ini_memc);
+
+        for (uint32_t i=0; i<nb_proc; ++i)
+	interconnect_c.p_to_target[i](signal_vci_tgt_proc[i]);
+	interconnect_c.p_to_target[nb_proc](signal_vci_tgt_cleanup_memc);
+
+	interconnect_x.p_clk(signal_clk);
+	interconnect_x.p_resetn(signal_resetn);
+
+	interconnect_x.p_to_initiator[0](signal_vci_ixr_memc);
+
+	interconnect_x.p_to_target[0](signal_vci_tgt_xram);
+
 	sc_start(sc_core::sc_time(0, SC_NS));
 	signal_resetn = false;
@@ -365,19 +412,55 @@
 	signal_resetn = true;
 
+#if SOCVIEW
 	debug();
+#elif DEBUG_TOP
+        for (int32_t i=0; i<ncycles; ++i)
+          {
+            std::cout << std::endl
+                      << std::dec << "===== [ cycle " << i << " ]======" << std::endl
+                      << std::endl;
+            
+            sc_start(sc_core::sc_time(1, SC_NS));
+            
+            // for (uint32_t i=0; i<nb_proc; ++i)
+            //   proc[i]->print_trace(1);
+          }
+#else
+        if (ncycles==-1)
+          sc_start();
+        else
+          sc_start(sc_core::sc_time(ncycles, SC_NS));
+
+        // std::cout << "Hit ENTER to end simulation" << std::endl;
+        // char buf[1];
+	// std::cin.getline(buf,1);
+#endif
+        for (uint32_t i=0; i<nb_proc; ++i)
+          proc[i]->print_cpi();
+        for (uint32_t i=0; i<nb_proc; ++i)
+          proc[i]->print_stats();
+
+        soclib::common::dealloc_elems<sc_signal<bool>                     >(signal_tty_irq         , nb_proc);
+	soclib::common::dealloc_elems<soclib::caba::VciSignals<vci_param> >(signal_vci_tgt_proc    , nb_proc);
+	soclib::common::dealloc_elems<soclib::caba::VciSignals<vci_param> >(signal_vci_ini_c_proc  , nb_proc);
+	soclib::common::dealloc_elems<soclib::caba::VciSignals<vci_param> >(signal_vci_ini_rw_proc , nb_proc);
+	soclib::common::dealloc_elems<sc_signal<bool>                     >(signal_proc_it         , nb_proc, 6);
+
+        for (uint32_t i=0; i<nb_proc; ++i)
+          delete proc[i];
+
 	return EXIT_SUCCESS;
-#endif
 }
 
 int sc_main (int argc, char *argv[])
 {
-	try {
-		return _main(argc, argv);
-	} catch (std::exception &e) {
-		std::cout << e.what() << std::endl;
-	} catch (...) {
-		std::cout << "Unknown exception occured" << std::endl;
-		throw;
-	}
-	return 1;
+  try {
+    return _main(argc, argv);
+  } catch (std::exception &e) {
+    std::cout << e.what() << std::endl;
+  } catch (...) {
+    std::cout << "Unknown exception occured" << std::endl;
+    throw;
+  }
+  return 1;
 }
Index: /trunk/platforms/caba-tsar-ring/Makefile
===================================================================
--- /trunk/platforms/caba-tsar-ring/Makefile	(revision 133)
+++ /trunk/platforms/caba-tsar-ring/Makefile	(revision 134)
@@ -3,7 +3,3 @@
 SOCLIB?=$(shell soclib-cc --getpath)
 export SOCLIB
-<<<<<<< .mine
-include  $(SOCLIB)/soclib/platform/topcells/all.mk
-=======
 include $(SOCLIB)/soclib/platform/topcells/all.mk
->>>>>>> .r1140
Index: /trunk/platforms/tsarv4_dspin_generic_32/tsarv4_dspin_generic_32_top.cpp
===================================================================
--- /trunk/platforms/tsarv4_dspin_generic_32/tsarv4_dspin_generic_32_top.cpp	(revision 133)
+++ /trunk/platforms/tsarv4_dspin_generic_32/tsarv4_dspin_generic_32_top.cpp	(revision 134)
@@ -548,5 +548,6 @@
                     IntTab(cluster(x,y),PROC_SRCID+p),	// SRCID_C
                     IntTab(cluster(x,y),PROC_SRCID+p),	// TGTID_C
-                    4,64,16,4,64,16); 			// Icache and Dcache sizes
+                    4,64,16,4,64,16, 			// Icache and Dcache sizes
+                    4,8,16);
             }
         }
Index: /trunk/platforms/tsarv4_multi_cluster_ring_vdspin/top.cpp
===================================================================
--- /trunk/platforms/tsarv4_multi_cluster_ring_vdspin/top.cpp	(revision 133)
+++ /trunk/platforms/tsarv4_multi_cluster_ring_vdspin/top.cpp	(revision 134)
@@ -202,5 +202,5 @@
 	for(int i=0; i<4; i++)
 		for(int j=0; j<4; j++)
-			new(&proc[4*i+j]) soclib::caba::VciCcXCacheWrapperV4<vci_param, proc_iss> ("proc" + (4*i+j), 4*i+j, maptabp, maptabc,IntTab(i,j),IntTab(i,j),IntTab(i,j),4,64,16,4,64,16);
+                  new(&proc[4*i+j]) soclib::caba::VciCcXCacheWrapperV4<vci_param, proc_iss> ("proc" + (4*i+j), 4*i+j, maptabp, maptabc,IntTab(i,j),IntTab(i,j),IntTab(i,j),4,64,16,4,64,16,4,8,16);
 
 	// ROM which contains boot code
Index: /trunk/platforms/tsarv4_vgmn_generic_32/tsarv4_vgmn_generic_32_top.cpp
===================================================================
--- /trunk/platforms/tsarv4_vgmn_generic_32/tsarv4_vgmn_generic_32_top.cpp	(revision 133)
+++ /trunk/platforms/tsarv4_vgmn_generic_32/tsarv4_vgmn_generic_32_top.cpp	(revision 134)
@@ -539,5 +539,7 @@
                     IntTab(cluster(x,y), PROC_SRCID+p),		// SRCID_C
                     IntTab(cluster(x,y), PROC_SRCID+p),		// TGTID_C
-                    4,64,16,4,64,16); 				// Icache and Dcache sizes
+                    4,64,16,4,64,16 				// Icache and Dcache sizes
+                    ,4,8,16
+                    );
 	}
       }
@@ -561,5 +563,5 @@
                 IntTab(cluster(x,y), MEMC_TGTID),		// TGTID_D
                 IntTab(cluster(x,y), nprocs),         		// TGTID_C
-                4,16,16,					// CACHE SIZE
+                16,256,16,					// CACHE SIZE
                 4096);						// HEAP SIZE
         }
@@ -834,4 +836,9 @@
     std::cin.getline(buf,1);
 
+    for( size_t x = 0 ; x < xmax ; x++ )
+      for( size_t y = 0 ; y < ymax ; y++ )
+	for ( size_t p = 0 ; p < nprocs ; p++ ) 
+          proc[x][y][p]->print_stats();
+
     return EXIT_SUCCESS;
 }
