⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cache.c

📁 32cpu的代码
💻 C
📖 第 1 页 / 共 2 页
字号:
#include <stdio.h>


unsigned long load_instruction(unsigned long virtual_addr);
unsigned long addr_translate(unsigned long virtual_addr);
long load_align(unsigned long virtual_addr, long data_in, unsigned data_width);
long store_align(unsigned long virtual_addr,long data_store,long data_old,unsigned data_width);
long load_data(unsigned long virtual_addr,unsigned data_width);
long store_data(unsigned long virtual_addr,long data_in,unsigned data_width);
extern instr_out[10000];
extern instr_out_1[10000];
extern instr_out_2[10000];
extern mem_data[1000][2];
extern *mem_data_fp;
extern unsigned long sysad_addr;
extern long sysad_data[4];
extern long GPR[32],CPR[34];
extern   FILE *lf_fp_code,*reg_trace_fp,*pc_trace_fp,*sysad_trace_fp;
extern   unsigned  long  pc_address_ip,pc_address_dp,pc_address_ep,pc_address_mp,pc_address_wp;
extern  int  tlb_dirty_bit_flag;
//extern   long Watchhi,Watchlo,Entryhi;
//extern   long Index,Random,Entrylo0,Entrylo1,Context,Pagemask,Wired,Badvaddr,Count,Entryhi,Compare,Status,Cause,EPC,Processor_Identification,Config,Config1,Load_Linked_Address,Watchlo,Watchhi,Errctl,Taglo,Datalo,ErrorEPC,Desave;
extern   long Index;
extern   long Random;
extern   long Entrylo0;
extern   long Entrylo1;
extern   long Context;
extern   long Pagemask;
extern   long Wired;
extern   long Badvaddr;
extern   long Count;
extern   long Entryhi;
extern   long Compare;
extern   long Status;
extern   long Cause;
extern   long EPC;
extern   long Processor_Identification;
extern   long Config;
extern   long Config1;
extern   long Load_Linked_Address;
extern   long Watchlo;
extern   long Watchhi;
extern   long Errctl;
extern   long Taglo;
extern   long Datalo;
extern   long ErrorEPC;
extern   long Desave;
extern   int  exception_flag_ip,exception_flag_mp;
void biu(unsigned long read_write_flag);
struct cache_data
{
unsigned  pa : 20;
unsigned  valid : 4;
unsigned  l : 1;
unsigned  lrf :1;
unsigned long word0;
unsigned long word1;
unsigned long word2;
unsigned long word3;
	}icache_data[256],dcache_data[256];

unsigned long icache(unsigned long virtual_addr,unsigned read_invalidate_flag){

	int i;
	auto char except;
	unsigned long load_instr,condition0,condition1;
                    if((virtual_addr&(0x00000003)) != 0){
                    	    exception_flag_ip=11;  
                    	    Badvaddr=virtual_addr;
                    	    EPC=virtual_addr;
                    	    CPR[8]=Badvaddr;
                    	    CPR[14]=EPC;
		            ErrorEPC=virtual_addr;
		            CPR[30]=virtual_addr;
                    	}
	   if(read_invalidate_flag == 0){
	   	condition0=((Watchlo>>2)&(0x00000001)) && ((Watchhi>>30)&(0x00000001)) &&  (((Watchlo>>12)&(0x000fffff))==((virtual_addr>>12)&(0x000fffff))) && (((Watchhi>>3)&(0x00000001))||(((Watchlo>>3)&(0x00000001))==((virtual_addr>>3)&(0x00000001)))) && (((Watchhi>>4)&(0x00000001))||(((Watchlo>>4)&(0x00000001))==((virtual_addr>>4)&(0x00000001)))) && (((Watchhi>>5)&(0x00000001))||(((Watchlo>>5)&(0x00000001))==((virtual_addr>>5)&(0x00000001)))) && (((Watchhi>>6)&(0x00000001))||(((Watchlo>>6)&(0x00000001))==((virtual_addr>>6)&(0x00000001)))) && (((Watchhi>>7)&(0x00000001))||(((Watchlo>>7)&(0x00000001))==((virtual_addr>>7)&(0x00000001)))) && (((Watchhi>>8)&(0x00000001))||(((Watchlo>>8)&(0x00000001))==((virtual_addr>>8)&(0x00000001)))) && (((Watchhi>>9)&(0x00000001))||(((Watchlo>>9)&(0x00000001))==((virtual_addr>>9)&(0x00000001)))) && (((Watchhi>>10)&(0x00000001))||(((Watchlo>>10)&(0x00000001))==((virtual_addr>>10)&(0x00000001)))) && (((Watchhi>>11)&(0x00000001))||(((Watchlo>>11)&(0x00000001))==((virtual_addr>>11)&(0x00000001))));
                condition1=((Watchlo>>2)&(0x00000001)) && (((Watchhi>>30)&(0x00000001)) == 0) && (((Watchhi>>16)&(0x000000ff))==(Entryhi&(0x000000ff))) && (((Watchlo>>12)&(0x000fffff))==((virtual_addr>>12)&(0x000fffff))) && (((Watchhi>>3)&(0x00000001))||(((Watchlo>>3)&(0x00000001))==((virtual_addr>>3)&(0x00000001)))) && (((Watchhi>>4)&(0x00000001))||(((Watchlo>>4)&(0x00000001))==((virtual_addr>>4)&(0x00000001)))) && (((Watchhi>>5)&(0x00000001))||(((Watchlo>>5)&(0x00000001))==((virtual_addr>>5)&(0x00000001)))) && (((Watchhi>>6)&(0x00000001))||(((Watchlo>>6)&(0x00000001))==((virtual_addr>>6)&(0x00000001)))) && (((Watchhi>>7)&(0x00000001))||(((Watchlo>>7)&(0x00000001))==((virtual_addr>>7)&(0x00000001)))) && (((Watchhi>>8)&(0x00000001))||(((Watchlo>>8)&(0x00000001))==((virtual_addr>>8)&(0x00000001)))) && (((Watchhi>>9)&(0x00000001))||(((Watchlo>>9)&(0x00000001))==((virtual_addr>>9)&(0x00000001)))) && (((Watchhi>>10)&(0x00000001))||(((Watchlo>>10)&(0x00000001))==((virtual_addr>>10)&(0x00000001)))) && (((Watchhi>>11)&(0x00000001))||(((Watchlo>>11)&(0x00000001))==((virtual_addr>>11)&(0x00000001))));
                 if(condition0 ||condition1){
                 	if((Status&(0x00000006)) == 0){
                 		//both EXL and ERL are zero ,Watch exception happen
                 		exception_flag_ip=10;
		                    ErrorEPC=virtual_addr;
		                    EPC=virtual_addr;
		                    CPR[30]=virtual_addr;
		                    CPR[14]=virtual_addr;
                 	}else{
                 	        Cause=Cause|(0x00400000);
                 	}
                 }

                        if((virtual_addr >= 0xa0000000)&&(virtual_addr <= 0xbfffffff)){
                            //uncache address
                                sysad_addr=addr_translate(virtual_addr,0);
           		  	biu(0);
           		  	switch(((virtual_addr>>2)&(0x00000003)))
	                        {
	                        case 0 : load_instr=sysad_data[0]; break;
	                        case 1 : load_instr=sysad_data[1]; break;
	                        case 2 : load_instr=sysad_data[2]; break;
	                        case 3 : load_instr=sysad_data[3]; break;
	     	                default : printf("icache word select error!\n");
	     	                }
           		  	return(load_instr);
                        }else{
                           //cache address
                                 if((icache_data[(unsigned long)(virtual_addr>>4)&(0x000000ff)].pa == ((addr_translate(virtual_addr,0)>>12)&(0x000fffff)))&&(icache_data[(unsigned long)(virtual_addr>>4)&(0x000000ff)].valid == 15)){
	                                 #ifdef DEBUG
	                                 printf("icache hit!  0x%08x \n",virtual_addr);
	                                 #endif
	                                 return(load_instruction(virtual_addr));
                                  }else{
                                         #ifdef DEBUG
                                         printf("icache miss!  0x%08x \n",virtual_addr);
           		  	         #endif
           		  	         sysad_addr=addr_translate(virtual_addr,0);
           		  	         biu(0);
                                         icache_data[(virtual_addr>>4)&(0x000000ff)].word0=sysad_data[0];
                                         icache_data[(virtual_addr>>4)&(0x000000ff)].word1=sysad_data[1];
                                         icache_data[(virtual_addr>>4)&(0x000000ff)].word2=sysad_data[2];
                                         icache_data[(virtual_addr>>4)&(0x000000ff)].word3=sysad_data[3];
                                         icache_data[(virtual_addr>>4)&(0x000000ff)].pa=((addr_translate(virtual_addr,0)>>12)&(0x000fffff));
           		                 icache_data[(virtual_addr>>4)&(0x000000ff)].valid=15;
	                                 return(load_instruction(virtual_addr));
                                   }
                        }
                

	   }else if(read_invalidate_flag == 2){
	            //index invalidate icache
	            icache_data[(unsigned long)(virtual_addr>>4)&(0x000000ff)].valid=0;
	            return((unsigned long)(virtual_addr>>4)&(0x000000ff));
	   }else if(read_invalidate_flag == 3){
		    //hit invalidate icache
		    if((icache_data[(unsigned long)(virtual_addr>>4)&(0x000000ff)].pa == ((addr_translate(virtual_addr,0)>>12)&(0x000fffff)))){
		           icache_data[(unsigned long)(virtual_addr>>4)&(0x000000ff)].valid=0;
		    	return((unsigned long)(virtual_addr>>4)&(0x000000ff));
		    	}else{
		    	return(0);
		    	}
	   }else{
	    printf("read_invalidate_flag error when call icache function!\n");
	  }

}

unsigned long load_instruction(unsigned long virtual_addr){
	
	          switch(((virtual_addr>>2)&(0x00000003)))
	         {
	           case 0 : return(icache_data[(virtual_addr>>4)&(0x000000ff)].word0); break;
	           case 1 : return(icache_data[(virtual_addr>>4)&(0x000000ff)].word1); break;
	           case 2 : return(icache_data[(virtual_addr>>4)&(0x000000ff)].word2); break;
	           case 3 : return(icache_data[(virtual_addr>>4)&(0x000000ff)].word3); break;
	     	   default : printf("icache word select error!\n");
	     	    }	
	}

long dcache(unsigned long virtual_addr,long data_in,unsigned data_width,unsigned read_write_flag){

	auto char except;
	unsigned long condition0,condition1;

	       if(read_write_flag == 0){
	       	//load data from dcache
	   	condition0=((Watchlo>>1)&(0x00000001)) && ((Watchhi>>30)&(0x00000001)) &&  (((Watchlo>>12)&(0x000fffff))==((virtual_addr>>12)&(0x000fffff))) && (((Watchhi>>3)&(0x00000001))||(((Watchlo>>3)&(0x00000001))==((virtual_addr>>3)&(0x00000001)))) && (((Watchhi>>4)&(0x00000001))||(((Watchlo>>4)&(0x00000001))==((virtual_addr>>4)&(0x00000001)))) && (((Watchhi>>5)&(0x00000001))||(((Watchlo>>5)&(0x00000001))==((virtual_addr>>5)&(0x00000001)))) && (((Watchhi>>6)&(0x00000001))||(((Watchlo>>6)&(0x00000001))==((virtual_addr>>6)&(0x00000001)))) && (((Watchhi>>7)&(0x00000001))||(((Watchlo>>7)&(0x00000001))==((virtual_addr>>7)&(0x00000001)))) && (((Watchhi>>8)&(0x00000001))||(((Watchlo>>8)&(0x00000001))==((virtual_addr>>8)&(0x00000001)))) && (((Watchhi>>9)&(0x00000001))||(((Watchlo>>9)&(0x00000001))==((virtual_addr>>9)&(0x00000001)))) && (((Watchhi>>10)&(0x00000001))||(((Watchlo>>10)&(0x00000001))==((virtual_addr>>10)&(0x00000001)))) && (((Watchhi>>11)&(0x00000001))||(((Watchlo>>11)&(0x00000001))==((virtual_addr>>11)&(0x00000001))));
                condition1=((Watchlo>>1)&(0x00000001)) && (((Watchhi>>30)&(0x00000001)) == 0) && (((Watchhi>>16)&(0x000000ff))==(Entryhi&(0x000000ff))) && (((Watchlo>>12)&(0x000fffff))==((virtual_addr>>12)&(0x000fffff))) && (((Watchhi>>3)&(0x00000001))||(((Watchlo>>3)&(0x00000001))==((virtual_addr>>3)&(0x00000001)))) && (((Watchhi>>4)&(0x00000001))||(((Watchlo>>4)&(0x00000001))==((virtual_addr>>4)&(0x00000001)))) && (((Watchhi>>5)&(0x00000001))||(((Watchlo>>5)&(0x00000001))==((virtual_addr>>5)&(0x00000001)))) && (((Watchhi>>6)&(0x00000001))||(((Watchlo>>6)&(0x00000001))==((virtual_addr>>6)&(0x00000001)))) && (((Watchhi>>7)&(0x00000001))||(((Watchlo>>7)&(0x00000001))==((virtual_addr>>7)&(0x00000001)))) && (((Watchhi>>8)&(0x00000001))||(((Watchlo>>8)&(0x00000001))==((virtual_addr>>8)&(0x00000001)))) && (((Watchhi>>9)&(0x00000001))||(((Watchlo>>9)&(0x00000001))==((virtual_addr>>9)&(0x00000001)))) && (((Watchhi>>10)&(0x00000001))||(((Watchlo>>10)&(0x00000001))==((virtual_addr>>10)&(0x00000001)))) && (((Watchhi>>11)&(0x00000001))||(((Watchlo>>11)&(0x00000001))==((virtual_addr>>11)&(0x00000001))));
                       if(condition0 || condition1){
                 	     if((Status&(0x00000006)) == 0){
                 		   //both EXL and ERL are zero ,Watch exception happen
                 		       exception_flag_mp=21;
		                    ErrorEPC=pc_address_mp;
		                    EPC=pc_address_mp;
		                    CPR[30]=pc_address_mp;
		                    CPR[14]=pc_address_mp;
                 	          }else{
                 	                Cause=Cause|(0x00400000);
                 	          }
                 	       return(load_data(virtual_addr,data_width));
                	 /*    printf("Watch exception occur! Please input enter key to exit:");
		             scanf("%c",&except);
                             if(except){
   	                             exit(0);
                                   }*/
                         }else{
	                         return(load_data(virtual_addr,data_width));
                         }

	        }else if(read_write_flag == 1){
			//store data to dcache
	   	     condition0=((Watchlo)&(0x00000001)) && ((Watchhi>>30)&(0x00000001)) &&  (((Watchlo>>12)&(0x000fffff))==((virtual_addr>>12)&(0x000fffff))) && (((Watchhi>>3)&(0x00000001))||(((Watchlo>>3)&(0x00000001))==((virtual_addr>>3)&(0x00000001)))) && (((Watchhi>>4)&(0x00000001))||(((Watchlo>>4)&(0x00000001))==((virtual_addr>>4)&(0x00000001)))) && (((Watchhi>>5)&(0x00000001))||(((Watchlo>>5)&(0x00000001))==((virtual_addr>>5)&(0x00000001)))) && (((Watchhi>>6)&(0x00000001))||(((Watchlo>>6)&(0x00000001))==((virtual_addr>>6)&(0x00000001)))) && (((Watchhi>>7)&(0x00000001))||(((Watchlo>>7)&(0x00000001))==((virtual_addr>>7)&(0x00000001)))) && (((Watchhi>>8)&(0x00000001))||(((Watchlo>>8)&(0x00000001))==((virtual_addr>>8)&(0x00000001)))) && (((Watchhi>>9)&(0x00000001))||(((Watchlo>>9)&(0x00000001))==((virtual_addr>>9)&(0x00000001)))) && (((Watchhi>>10)&(0x00000001))||(((Watchlo>>10)&(0x00000001))==((virtual_addr>>10)&(0x00000001)))) && (((Watchhi>>11)&(0x00000001))||(((Watchlo>>11)&(0x00000001))==((virtual_addr>>11)&(0x00000001))));
                     condition1=((Watchlo)&(0x00000001)) && (((Watchhi>>30)&(0x00000001)) == 0) && (((Watchhi>>16)&(0x000000ff))==(Entryhi&(0x000000ff))) && (((Watchlo>>12)&(0x000fffff))==((virtual_addr>>12)&(0x000fffff))) && (((Watchhi>>3)&(0x00000001))||(((Watchlo>>3)&(0x00000001))==((virtual_addr>>3)&(0x00000001)))) && (((Watchhi>>4)&(0x00000001))||(((Watchlo>>4)&(0x00000001))==((virtual_addr>>4)&(0x00000001)))) && (((Watchhi>>5)&(0x00000001))||(((Watchlo>>5)&(0x00000001))==((virtual_addr>>5)&(0x00000001)))) && (((Watchhi>>6)&(0x00000001))||(((Watchlo>>6)&(0x00000001))==((virtual_addr>>6)&(0x00000001)))) && (((Watchhi>>7)&(0x00000001))||(((Watchlo>>7)&(0x00000001))==((virtual_addr>>7)&(0x00000001)))) && (((Watchhi>>8)&(0x00000001))||(((Watchlo>>8)&(0x00000001))==((virtual_addr>>8)&(0x00000001)))) && (((Watchhi>>9)&(0x00000001))||(((Watchlo>>9)&(0x00000001))==((virtual_addr>>9)&(0x00000001)))) && (((Watchhi>>10)&(0x00000001))||(((Watchlo>>10)&(0x00000001))==((virtual_addr>>10)&(0x00000001)))) && (((Watchhi>>11)&(0x00000001))||(((Watchlo>>11)&(0x00000001))==((virtual_addr>>11)&(0x00000001))));
                       if(condition0 || condition1){
                 	     if((Status&(0x00000006)) == 0){
                 		   //both EXL and ERL are zero ,Watch exception happen
                 		       exception_flag_mp=21;
		                    ErrorEPC=pc_address_mp;
		                    EPC=pc_address_mp;
		                    CPR[30]=pc_address_mp;
		                    CPR[14]=pc_address_mp;
                 	          }else{
                 	                Cause=Cause|(0x00400000);
                 	          }
                 	          return(0x00000000);
                	 /*    printf("Watch exception occur! Please input enter key to exit:");
		             scanf("%c",&except);
                             if(except){
   	                             exit(0);
                                   }*/
                         }else{
	                       return(store_data(virtual_addr,data_in,data_width));
                         }	
                         	
	       }else if(read_write_flag == 2){
		        //index invalidate dcache
		               dcache_data[(unsigned long)(virtual_addr>>4)&(0x000000ff)].valid=0;
		               return(0x00000000);
		               printf("dcache invalidate\n");
	       }else if(read_write_flag == 3){
	                //hit invalidate dcache
		        if((dcache_data[(unsigned long)(virtual_addr>>4)&(0x000000ff)].pa == ((addr_translate(virtual_addr,1)>>12)&(0x000fffff)))){
		               dcache_data[(unsigned long)(virtual_addr>>4)&(0x000000ff)].valid=0;
		    	      }
		    	 return(0x00000000);
	       }else{

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -