Changeset 540 for branches/RWT/modules/vci_mem_cache
- Timestamp:
- Oct 3, 2013, 4:17:09 PM (11 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/RWT/modules/vci_mem_cache/caba/source/src/vci_mem_cache.cpp
r539 r540 2252 2252 if(((m_cmd_read_pktid_fifo.read() & 0x7) == TYPE_LL) and not r_read_ll_done.read()) // access the global table ONLY when we have an LL cmd 2253 2253 { 2254 addr_t nline = m_nline[(addr_t)(m_cmd_read_addr_fifo.read())]; 2255 r_read_ll_key = m_llsc_table.ll(nline); 2256 //r_read_ll_key = m_llsc_table.ll(m_cmd_read_addr_fifo.read()); 2254 r_read_ll_key = m_llsc_table.ll(m_cmd_read_addr_fifo.read()); 2257 2255 /**//*std::cout << "MEMCACHE : from proc " << m_cmd_read_srcid_fifo.read() 2258 2259 2256 << " | @ " << std::hex << m_cmd_read_addr_fifo.read() 2257 << " | LL" << std::endl;*/ 2260 2258 r_read_ll_done = true; 2261 2259 } … … 2275 2273 // TYPE_READ_INS_MISS 0bX011 with TSAR encoding 2276 2274 bool cached_read = (m_cmd_read_pktid_fifo.read() & 0x1); 2277 2278 2275 2279 2276 if(entry.valid) // hit … … 2870 2867 r_write_address = (addr_t)(m_cmd_write_addr_fifo.read()); 2871 2868 r_write_word_index = index; 2872 r_write_word_count = 1;2869 r_write_word_count = 0; 2873 2870 r_write_data[index] = m_cmd_write_data_fifo.read(); 2874 2871 r_write_srcid = m_cmd_write_srcid_fifo.read(); 2875 2872 r_write_trdid = m_cmd_write_trdid_fifo.read(); 2876 2873 r_write_pktid = m_cmd_write_pktid_fifo.read(); 2877 r_write_pending_sc = false; 2874 2875 if ((m_cmd_write_pktid_fifo.read() & 0x7) == TYPE_SC) 2876 { 2877 assert( not m_cmd_write_eop_fifo.read() && 2878 "MEMC ERROR in WRITE_IDLE state: " 2879 "invalid packet format for SC command"); 2880 2881 r_write_sc_key = m_cmd_write_data_fifo.read(); 2882 } 2878 2883 2879 2884 // initialize the be field for all words … … 2884 2889 } 2885 2890 2886 if (m_cmd_write_eop_fifo.read() or ((m_cmd_write_pktid_fifo.read() & 0x7) == TYPE_SC))2891 if (m_cmd_write_eop_fifo.read()) 2887 2892 { 2888 2893 r_write_fsm = WRITE_DIR_REQ; … … 2898 2903 << " srcid = " << std::hex << m_cmd_write_srcid_fifo.read() 2899 2904 << " / address = " << std::hex << m_cmd_write_addr_fifo.read() 2900 << " / data = " << m_cmd_write_data_fifo.read() << std::endl; 2905 << " / data = " << m_cmd_write_data_fifo.read() 2906 << " / pktid = " << m_cmd_write_pktid_fifo.read() 2907 << std::endl; 2901 2908 #endif 2902 2909 } … … 2910 2917 { 2911 2918 2912 #if DEBUG_MEMC_WRITE2913 if(m_debug)2914 std::cout << " <MEMC " << name()2915 << " WRITE_NEXT> Write another word in local buffer"2916 << std::endl;2917 #endif2918 2919 m_cpt_write_cells++; 2919 2920 2920 2921 // check that the next word is in the same cache line 2921 assert( (m_nline[(addr_t)(r_write_address.read())] == 2922 m_nline[(addr_t)(m_cmd_write_addr_fifo.read())]) and 2923 "MEMC ERROR in WRITE_NEXT state: Illegal write burst"); 2924 2922 assert((m_nline[(addr_t)(r_write_address.read())] == 2923 m_nline[(addr_t)(m_cmd_write_addr_fifo.read())]) && 2924 "MEMC ERROR in WRITE_NEXT state: Illegal write burst"); 2925 2926 size_t index = m_x[(addr_t)(m_cmd_write_addr_fifo.read())]; 2927 bool is_sc = ((m_cmd_write_pktid_fifo.read() & 0x7) == TYPE_SC); 2928 2929 // check that SC command has constant address 2930 assert((not is_sc or (index == r_write_word_index)) && 2931 "MEMC ERROR in WRITE_NEXT state: " 2932 "the address must be constant on a SC command"); 2933 2934 // check that SC command has two flits 2935 assert((not is_sc or m_cmd_write_eop_fifo.read()) && 2936 "MEMC ERROR in WRITE_NEXT state: " 2937 "invalid packet format for SC command"); 2925 2938 // consume a word in the FIFO & write it in the local buffer 2926 2939 cmd_write_fifo_get = true; 2927 size_t index = r_write_word_index.read() + r_write_word_count.read();2928 2940 2929 2941 r_write_be[index] = m_cmd_write_be_fifo.read(); 2930 2942 r_write_data[index] = m_cmd_write_data_fifo.read(); 2931 r_write_word_count = r_write_word_count.read() + 1; 2932 2933 if(m_cmd_write_eop_fifo.read()) 2934 { 2935 r_write_fsm = WRITE_DIR_REQ; 2936 } 2943 2944 // the first flit of a SC command is the reservation key and 2945 // therefore it must not be counted as a data to write 2946 if (not is_sc) 2947 { 2948 r_write_word_count = r_write_word_count.read() + 1; 2949 } 2950 2951 if (m_cmd_write_eop_fifo.read()) r_write_fsm = WRITE_DIR_REQ; 2952 2953 #if DEBUG_MEMC_WRITE 2954 if (m_debug) 2955 std::cout << " <MEMC " << name() 2956 << " WRITE_NEXT> Write another word in local buffer" 2957 << std::endl; 2958 #endif 2937 2959 } 2938 2960 break; … … 2946 2968 if(r_alloc_dir_fsm.read() == ALLOC_DIR_WRITE) 2947 2969 { 2948 /////////////////////////////////////////////////////////////////////// 2949 // SC command handling 2950 // We test the r_write_pending_sc register to know if we are returning 2951 // from the WAIT state. 2952 // In this case, the SC has already succeed and we cannot consume 2953 // another time from the FIFO. Also, we don't have to test another 2954 // time if the SC has succeed 2955 2956 addr_t nline = m_nline[(addr_t)(r_write_address.read())]; 2957 if(((r_write_pktid.read() & 0x7) == TYPE_SC) and not r_write_pending_sc.read()) 2958 { 2959 if(not m_cmd_write_addr_fifo.rok()) break; 2960 2961 assert(m_cmd_write_eop_fifo.read() and 2962 "Error in VCI_MEM_CACHE : " 2963 "invalid packet format for SC command"); 2964 //BUG LLSC 2965 size_t index = r_write_word_index.read(); 2966 bool sc_success = m_llsc_table.sc(nline , 2967 r_write_data[index].read()); 2968 2969 //bool sc_success = m_llsc_table.sc(r_write_address.read() , 2970 // r_write_data[index].read()); 2971 // consume a word in the FIFO & write it in the local buffer 2972 cmd_write_fifo_get = true; 2973 r_write_data[index] = m_cmd_write_data_fifo.read(); 2970 2971 if( (r_write_pktid.read() & 0x7) == TYPE_SC ) 2972 { 2973 // test address and key match of the SC command on the 2974 // LL/SC table without removing reservation. The reservation 2975 // will be erased after in this FSM. 2976 bool sc_success = m_llsc_table.check(r_write_address.read(), 2977 r_write_sc_key.read()); 2978 2974 2979 r_write_sc_fail = not sc_success; 2975 //WARNING: if the SC is a success, it might still fail at next cycle if the line is NCC2976 r_write_pending_sc = true;2977 2980 2978 2981 if(not sc_success) r_write_fsm = WRITE_RSP; 2979 2982 else r_write_fsm = WRITE_DIR_LOCK; 2980 2983 2984 2985 //std::cout << " <MEMC " << name() 2986 // << " WRITE_DIR_REQ> sc fail = " << not sc_success 2987 // << " / addr" << std::hex << r_write_address.read() 2988 // << " / key" << std::hex << r_write_sc_key.read() 2989 // << " / srcid" << std::hex << r_write_srcid.read() 2990 // << std::endl; 2991 2981 2992 break; 2982 2993 } … … 2990 3001 addr_t min = r_write_address.read(); 2991 3002 addr_t max = r_write_address.read() + 2992 ((r_write_word_count.read() -1) << L2(vci_param_int::B));3003 ((r_write_word_count.read()) << L2(vci_param_int::B)); 2993 3004 #undef L2 2994 3005 m_llsc_table.sw(min, max); … … 3039 3050 else 3040 3051 { 3041 r_write_fsm = WRITE_DIR_HIT;3052 r_write_fsm = WRITE_DIR_HIT; 3042 3053 } 3043 3054 } … … 3051 3062 { 3052 3063 r_write_fsm = WRITE_IVT_LOCK_HIT_WB; 3053 3054 3055 3056 3064 // if(r_write_pktid.read() == TYPE_SC) 3065 // { 3066 // r_write_sc_fail = true; 3067 // } 3057 3068 } 3058 3069 } … … 3067 3078 { 3068 3079 std::cout << " <MEMC " << name() << " WRITE_DIR_LOCK> Check the directory: " 3069 3070 3071 3072 3080 << " address = " << std::hex << r_write_address.read() 3081 << " / hit = " << std::dec << entry.valid 3082 << " / count = " << entry.count 3083 << " / is_cnt = " << entry.is_cnt ; 3073 3084 if((r_write_pktid.read() & 0x7) == TYPE_SC) 3074 3085 std::cout << " / SC access" << std::endl; … … 3079 3090 break; 3080 3091 } 3081 3082 3083 3084 3085 3086 3087 3088 3089 3090 3091 3092 3093 3094 3095 3096 3097 3098 3099 3100 3101 3102 3103 3104 3105 3106 3107 3108 3109 3110 3111 3112 3113 3114 3115 3116 3092 //////////////////// 3093 case WRITE_IVT_LOCK_HIT_WB: 3094 { 3095 if(r_alloc_ivt_fsm.read() == ALLOC_IVT_WRITE) 3096 { 3097 3098 size_t index = 0; 3099 bool match_inval; 3100 addr_t nline = m_nline[(addr_t)(r_write_address.read())]; 3101 3102 //std::cout << "WRITE on NCC on line" << std::hex << nline << std::dec << std::endl; 3103 //if there is a matched updt req, we should wait until it is over. Because 3104 //we need the lastest updt data. 3105 match_inval = m_ivt.search_inval(nline, index); 3106 3107 assert ((r_write_count.read() == 1) and "NCC to CC req without copy"); 3108 if(!match_inval and !r_write_to_cc_send_req.read()) 3109 { 3110 r_write_to_cc_send_req = true; 3111 r_write_to_cc_send_dest = r_write_copy; 3112 r_write_to_cc_send_nline = nline; 3113 r_write_to_cleanup_req = true; 3114 r_write_to_cleanup_nline = nline; 3115 3116 m_ivt.set(false, // it's an inval transaction 3117 false, // it's not a broadcast 3118 true, // it needs no read response 3119 false, // no acknowledge required 3120 m_cmd_write_srcid_fifo.read(), //never read, used for debug 3121 m_cmd_write_trdid_fifo.read(), //never read, used for debug 3122 m_cmd_write_pktid_fifo.read(), //never read, used for debug 3123 nline, 3124 0x1, //Expect only one answer 3125 index); 3126 } 3127 r_write_fsm = WRITE_WAIT; 3117 3128 #if DEBUG_MEMC_WRITE 3118 3119 3120 3121 3122 3123 3124 #endif 3125 3129 if(m_debug) 3130 { 3131 std::cout << " <MEMC " << name() << " WRITE_IVT_LOCK_HIT_WB> get access to the UPT: " 3132 << " Inval requested = " << (!match_inval and !r_write_to_cc_send_req.read()) 3133 << std::endl; 3134 } 3135 #endif 3136 } 3126 3137 #if DEBUG_MEMC_WRITE 3127 3128 3129 3130 3131 3132 #endif 3133 3134 3135 3136 3137 3138 if(m_debug) 3139 { 3140 std::cout << " <MEMC " << name() << " WRITE_IVT_LOCK_HIT_WB> failed to access to the UPT: " 3141 << std::endl; 3142 } 3143 #endif 3144 break; 3145 } 3146 3147 /////////////////// 3148 case WRITE_DIR_HIT: 3138 3149 { 3139 3150 assert( (r_alloc_dir_fsm.read() == ALLOC_DIR_WRITE) and … … 3167 3178 // (tests for sc requests) 3168 3179 bool no_update = ((r_write_count.read() ==0) || //no need for coherency 3169 (owner && (r_write_count.read() ==1) && (r_write_pktid.read() != TYPE_SC)) 3170 ((r_write_pktid.read() == TYPE_SC) && r_write_sc_fail.read())); //SC failed: no data update3180 (owner && (r_write_count.read() ==1) && (r_write_pktid.read() != TYPE_SC))); //|| //writer is owner 3181 // ((r_write_pktid.read() == TYPE_SC) && r_write_sc_fail.read())); //SC failed: no data update 3171 3182 3172 3183 // write data in the cache if no coherence transaction 3173 if(no_update and ((r_write_pktid.read() != TYPE_SC) or !r_write_sc_fail.read())) 3174 { 3184 if(no_update) 3185 { 3186 // SC command but zero copies 3187 if ((r_write_pktid.read() & 0x7) == TYPE_SC) 3188 { 3189 m_llsc_table.sc(r_write_address.read(), 3190 r_write_sc_key.read()); 3191 } 3192 3175 3193 for(size_t word=0 ; word<m_words ; word++) 3176 3194 { … … 3252 3270 if(wok) // write data in cache 3253 3271 { 3272 3273 if ((r_write_pktid.read() & 0x7) == TYPE_SC) 3274 { 3275 m_llsc_table.sc(r_write_address.read(), 3276 r_write_sc_key.read()); 3277 } 3278 3254 3279 for(size_t word=0 ; word<m_words ; word++) 3255 3280 { … … 3328 3353 size_t min = r_write_word_index.read(); 3329 3354 size_t max = r_write_word_index.read() + r_write_word_count.read(); 3330 for(size_t i=min ; i< max ; i++) r_write_to_cc_send_data[i] = r_write_data[i];3355 for(size_t i=min ; i<=max ; i++) r_write_to_cc_send_data[i] = r_write_data[i]; 3331 3356 3332 3357 if((r_write_copy.read() != r_write_srcid.read()) or(r_write_pktid.read() == TYPE_SC) or r_write_copy_inst.read()) … … 3494 3519 r_write_address = (addr_t)(m_cmd_write_addr_fifo.read()); 3495 3520 r_write_word_index = index; 3496 r_write_word_count = 1;3521 r_write_word_count = 0; 3497 3522 r_write_data[index] = m_cmd_write_data_fifo.read(); 3498 3523 r_write_srcid = m_cmd_write_srcid_fifo.read(); 3499 3524 r_write_trdid = m_cmd_write_trdid_fifo.read(); 3500 3525 r_write_pktid = m_cmd_write_pktid_fifo.read(); 3501 r_write_pending_sc = false; 3526 3527 if ((m_cmd_write_pktid_fifo.read() & 0x7) == TYPE_SC) 3528 { 3529 assert( not m_cmd_write_eop_fifo.read() && 3530 "MEMC ERROR in WRITE_RSP state: " 3531 "invalid packet format for SC command"); 3532 3533 r_write_sc_key = m_cmd_write_data_fifo.read(); 3534 } 3535 3502 3536 3503 3537 // initialize the be field for all words … … 3505 3539 { 3506 3540 if(word == index) r_write_be[word] = m_cmd_write_be_fifo.read(); 3507 else 3541 else r_write_be[word] = 0x0; 3508 3542 } 3509 3543 3510 if( m_cmd_write_eop_fifo.read() or ((m_cmd_write_pktid_fifo.read() & 0x7) == TYPE_SC))3544 if( m_cmd_write_eop_fifo.read()) 3511 3545 { 3512 3546 r_write_fsm = WRITE_DIR_REQ; … … 3526 3560 { 3527 3561 std::cout << " <MEMC " << name() << " WRITE_RSP> Post a request to TGT_RSP FSM" 3528 << " : rsrcid = " << std::hex << r_write_srcid.read() << std::endl; 3562 << " : rsrcid = " << std::hex << r_write_srcid.read() 3563 << " : rpktid = " << std::hex << r_write_pktid.read() 3564 << " : sc_fail= " << std::hex << r_write_sc_fail.read() 3565 << std::endl; 3529 3566 if(m_cmd_write_addr_fifo.rok()) 3530 3567 { … … 3532 3569 << " srcid = " << std::hex << m_cmd_write_srcid_fifo.read() 3533 3570 << " / address = " << m_cmd_write_addr_fifo.read() 3534 << " / data = " << m_cmd_write_data_fifo.read() << std::endl; 3571 << " / data = " << m_cmd_write_data_fifo.read() 3572 << " / pktid = " << m_cmd_write_pktid_fifo.read() 3573 << std::endl; 3535 3574 } 3536 3575 } … … 3573 3612 bool hit_write = m_trt.hit_write(m_nline[addr]); 3574 3613 bool wok = not m_trt.full(wok_index); 3614 3615 // wait an empty entry in TRT 3616 if(not hit_read and (not wok or hit_write)) 3617 { 3618 r_write_fsm = WRITE_WAIT; 3619 m_cpt_trt_full++; 3620 break; 3621 } 3622 3623 if ((r_write_pktid.read() & 0x7) == TYPE_SC) 3624 { 3625 m_llsc_table.sc(r_write_address.read(), 3626 r_write_sc_key.read()); 3627 } 3628 3575 3629 //std::cout << "MEMCACHE : WRITE MISS at " << std::hex << (uint32_t)addr << std::dec << std::endl; 3576 3630 if(hit_read) // register the modified data in TRT … … 3579 3633 r_write_fsm = WRITE_MISS_TRT_DATA; 3580 3634 m_cpt_write_miss++; 3581 } 3582 else if(wok and !hit_write) // set a new entry in TRT 3635 break; 3636 } 3637 3638 if(wok and not hit_write) // set a new entry in TRT 3583 3639 { 3584 3640 r_write_trt_index = wok_index; 3585 3641 r_write_fsm = WRITE_MISS_TRT_SET; 3586 3642 m_cpt_write_miss++; 3587 } 3588 else // wait an empty entry in TRT 3589 { 3590 r_write_fsm = WRITE_WAIT; 3591 m_cpt_trt_full++; 3592 } 3643 break; 3644 } 3645 assert(false && "VCI_MEM_CACHE ERROR: this part must not be reached"); 3593 3646 m_cpt_write_fsm_n_trt_lock++; 3594 3647 } … … 3849 3902 3850 3903 m_cache_directory.write(set, way, entry); 3904 3905 if ((r_write_pktid.read() & 0x7) == TYPE_SC) 3906 { 3907 m_llsc_table.sc(r_write_address.read(), 3908 r_write_sc_key.read()); 3909 } 3910 3851 3911 3852 3912 #if DEBUG_MEMC_WRITE … … 7309 7369 { 7310 7370 if(not p_dspin_m2p.read) break; 7311 if(r_cc_send_cpt.read() == (r_write_to_cc_send_count.read()-1))7371 if(r_cc_send_cpt.read() == r_write_to_cc_send_count.read()) 7312 7372 { 7313 7373 write_to_cc_send_fifo_get = true; … … 8693 8753 r_alloc_trt_fsm = ALLOC_TRT_IXR_RSP; 8694 8754 8695 8755 else if( r_config_fsm.read() == CONFIG_TRT_LOCK ) 8696 8756 r_alloc_trt_fsm = ALLOC_TRT_CONFIG; 8697 8757 … … 9021 9081 r_alloc_heap_fsm = ALLOC_HEAP_CLEANUP; 9022 9082 9023 if(r_xram_rsp_fsm.read() == XRAM_RSP_HEAP_REQ)9083 else if(r_xram_rsp_fsm.read() == XRAM_RSP_HEAP_REQ) 9024 9084 r_alloc_heap_fsm = ALLOC_HEAP_XRAM_RSP; 9025 9085 … … 9820 9880 9821 9881 p_dspin_m2p.write = true; 9822 p_dspin_m2p.eop = (r_cc_send_cpt.read() == (r_write_to_cc_send_count.read()-1));9882 p_dspin_m2p.eop = (r_cc_send_cpt.read() == r_write_to_cc_send_count.read()); 9823 9883 p_dspin_m2p.data = flit; 9824 9884
Note: See TracChangeset
for help on using the changeset viewer.