OpenCores
URL https://opencores.org/ocsvn/ahb_system_generator/ahb_system_generator/trunk

Subversion Repositories ahb_system_generator

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /
    from Rev 2 to Rev 3
    Reverse comparison

Rev 2 → Rev 3

/trunk/src/slv_mem.vhd File deleted
/trunk/src/fifo.vhd File deleted
/trunk/docs/ahb_generator.pdf Cannot display: file marked as a binary type. svn:mime-type = application/octet-stream
trunk/docs/ahb_generator.pdf Property changes : Deleted: svn:mime-type ## -1 +0,0 ## -application/octet-stream \ No newline at end of property Index: ahb_system_generator/trunk/references/m###.ref =================================================================== --- ahb_system_generator/trunk/references/m###.ref (nonexistent) +++ ahb_system_generator/trunk/references/m###.ref (revision 3) @@ -0,0 +1,124 @@ +640 ns MEM 0 DATA 0 +1600 ns MEM 0 DATA 0 +1610 ns MEM 1 DATA 1 +1640 ns MEM 2 DATA 2 +1690 ns MEM 3 DATA 3 +2560 ns MEM 0 DATA 0 +2570 ns MEM 1 DATA 1 +2600 ns MEM 2 DATA 2 +2610 ns MEM 3 DATA 3 +4020 ns MEM 0 DATA 0 +4030 ns MEM 1 DATA 1 +4060 ns MEM 2 DATA 2 +4070 ns MEM 3 DATA 3 +4100 ns MEM 4 DATA 4 +4170 ns MEM 5 DATA 5 +4180 ns MEM 6 DATA 6 +4210 ns MEM 7 DATA 7 +5590 ns MEM 0 DATA 0 +5600 ns MEM 1 DATA 1 +5630 ns MEM 2 DATA 2 +5640 ns MEM 3 DATA 3 +5670 ns MEM 4 DATA 4 +5680 ns MEM 5 DATA 5 +5710 ns MEM 6 DATA 6 +5720 ns MEM 7 DATA 7 +8040 ns MEM 0 DATA 0 +8050 ns MEM 1 DATA 1 +8080 ns MEM 2 DATA 2 +8090 ns MEM 3 DATA 3 +8120 ns MEM 4 DATA 4 +8130 ns MEM 5 DATA 5 +8160 ns MEM 6 DATA 6 +8170 ns MEM 7 DATA 7 +8200 ns MEM 8 DATA 8 +8210 ns MEM 9 DATA 9 +8240 ns MEM 10 DATA 10 +8290 ns MEM 11 DATA 11 +8300 ns MEM 12 DATA 12 +8330 ns MEM 13 DATA 13 +8340 ns MEM 14 DATA 14 +8370 ns MEM 15 DATA 15 +10680 ns MEM 0 DATA 0 +10690 ns MEM 1 DATA 1 +10720 ns MEM 2 DATA 2 +10730 ns MEM 3 DATA 3 +10760 ns MEM 4 DATA 4 +10770 ns MEM 5 DATA 5 +10800 ns MEM 6 DATA 6 +10810 ns MEM 7 DATA 7 +10840 ns MEM 8 DATA 8 +10850 ns MEM 9 DATA 9 +10880 ns MEM 10 DATA 10 +10890 ns MEM 11 DATA 11 +10920 ns MEM 12 DATA 12 +10930 ns MEM 13 DATA 13 +10960 ns MEM 14 DATA 14 +10970 ns MEM 15 DATA 15 +11500 ns MEM 0 DATA 0 +12940 ns MEM 0 DATA 0 +12950 ns MEM 1 DATA 1 +12980 ns MEM 2 DATA 2 +12990 ns MEM 3 DATA 3 +13020 ns MEM 4 DATA 4 +13030 ns MEM 5 DATA 5 +13060 ns MEM 6 DATA 6 +13070 ns MEM 7 DATA 7 +13100 ns MEM 8 DATA 8 +14120 ns MEM 0 DATA 0 +14130 ns MEM 1 DATA 1 +14160 ns MEM 2 DATA 2 +14200 ns MEM 3 DATA 3 +15090 ns MEM 0 DATA 0 +15100 ns MEM 1 DATA 1 +15130 ns MEM 2 DATA 2 +15140 ns MEM 3 DATA 3 +16680 ns MEM 0 DATA 0 +16690 ns MEM 1 DATA 1 +16720 ns MEM 2 DATA 2 +16730 ns MEM 3 DATA 3 +16760 ns MEM 4 DATA 4 +16810 ns MEM 5 DATA 5 +16820 ns MEM 6 DATA 6 +16850 ns MEM 7 DATA 7 +18180 ns MEM 0 DATA 0 +18190 ns MEM 1 DATA 1 +18220 ns MEM 2 DATA 2 +18230 ns MEM 3 DATA 3 +18260 ns MEM 4 DATA 4 +18270 ns MEM 5 DATA 5 +18300 ns MEM 6 DATA 6 +18310 ns MEM 7 DATA 7 +20680 ns MEM 0 DATA 0 +20690 ns MEM 1 DATA 1 +20720 ns MEM 2 DATA 2 +20760 ns MEM 3 DATA 3 +20770 ns MEM 4 DATA 4 +20800 ns MEM 5 DATA 5 +20810 ns MEM 6 DATA 6 +20840 ns MEM 7 DATA 7 +20850 ns MEM 8 DATA 8 +20880 ns MEM 9 DATA 9 +20890 ns MEM 10 DATA 10 +20920 ns MEM 11 DATA 11 +20930 ns MEM 12 DATA 12 +20960 ns MEM 13 DATA 13 +20970 ns MEM 14 DATA 14 +21000 ns MEM 15 DATA 15 +23130 ns MEM 0 DATA 0 +23140 ns MEM 1 DATA 1 +23170 ns MEM 2 DATA 2 +23180 ns MEM 3 DATA 3 +23210 ns MEM 4 DATA 4 +23220 ns MEM 5 DATA 5 +23250 ns MEM 6 DATA 6 +23260 ns MEM 7 DATA 7 +23290 ns MEM 8 DATA 8 +23300 ns MEM 9 DATA 9 +23330 ns MEM 10 DATA 10 +23340 ns MEM 11 DATA 11 +23370 ns MEM 12 DATA 12 +23380 ns MEM 13 DATA 13 +23410 ns MEM 14 DATA 14 +23420 ns MEM 15 DATA 15 +23930 ns MEM 0 DATA 0 Index: ahb_system_generator/trunk/simulate/cds.lib =================================================================== --- ahb_system_generator/trunk/simulate/cds.lib (nonexistent) +++ ahb_system_generator/trunk/simulate/cds.lib (revision 3) @@ -0,0 +1,2 @@ +DEFINE work ../compile +SOFTINCLUDE $CADENCEDIR/ncsim/tools/inca/files/cds.lib Index: ahb_system_generator/trunk/simulate/hdl.var =================================================================== --- ahb_system_generator/trunk/simulate/hdl.var (nonexistent) +++ ahb_system_generator/trunk/simulate/hdl.var (revision 3) @@ -0,0 +1,5 @@ +softinclude $CDS_INST_DIR/inca/files/hdl.var +define LIB_MAP ( $LIB_MAP, + => work ) +DEFINE NCELABOPTS -timescale "1ns / 100 ps" +DEFINE NCVHDLOPTS -errormax 100 +define WORK work Index: ahb_system_generator/trunk/conf/ahb_5mst_2slv_1arb.conf =================================================================== --- ahb_system_generator/trunk/conf/ahb_5mst_2slv_1arb.conf (nonexistent) +++ ahb_system_generator/trunk/conf/ahb_5mst_2slv_1arb.conf (revision 3) @@ -0,0 +1,18 @@ +# ahb_master 0: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst0,8,1,7,4,1,0,2,2,0 +# ahb_master 1: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst1,4,1,3,4,1,1,2,2,128 +# ahb_master 2: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst2,4,1,2,4,0,1,2,2,256 +# ahb_master 3: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst3,8,1,7,4,1,1,2,2,1024 +# ahb_master 4: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst4,4,1,3,4,1,1,1,2,1280 +# ahb_slave 0: +# module,name,NOT_USED,type,add_h,add_l,remap add_h,remap add_l,NOT_USED,fifo_le,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat +ahb_slave,ahb_slv0,(SLAVE_LIST),wait,1023,0,1023,0,0,8,1,7,8,1,0,2,2 +# ahb_slave 1: +# module,name,NOT_USED,type,add_h,add_l,remap add_h,remap add_l,NOT_USED,fifo_le,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat +ahb_slave,ahb_slv1,(SLAVE_LIST),wait,2047,1024,2047,1024,0,8,1,7,8,1,1,3,1 +# ahb_arbiter 0: module,name,default master,master_list,slave_list,arbitration type +ahb_arbiter,ahb_arb0,2,(4,1,0,2,3),(1,0),2 Index: ahb_system_generator/trunk/conf/ahb_generate.conf =================================================================== Index: ahb_system_generator/trunk/conf/ahb_3mst_1slv.conf =================================================================== --- ahb_system_generator/trunk/conf/ahb_3mst_1slv.conf (nonexistent) +++ ahb_system_generator/trunk/conf/ahb_3mst_1slv.conf (revision 3) @@ -0,0 +1,11 @@ +# ahb_master 0: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst0,4,1,3,4,1,1,1,1,0 +# ahb_master 1: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst1,8,1,7,4,1,1,3,4,128 +# ahb_master 2: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst2,4,1,3,4,1,1,2,1,256 +# ahb_slave 0: +# module,name,NOT_USED,type,add_h,add_l,remap add_h,remap add_l,NOT_USED,fifo_le,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat +ahb_slave,ahb_slv0,(SLAVE_LIST),wait,1023,0,1023,0,0,8,1,7,7,1,1,2,2 +# ahb_arbiter 0: module,name,default master,master_list,slave_list,arbitration type +ahb_arbiter,ahb_arb0,1,(0,2,1),(0),0 Index: ahb_system_generator/trunk/conf/ahb_6mst_1slv.conf =================================================================== --- ahb_system_generator/trunk/conf/ahb_6mst_1slv.conf (nonexistent) +++ ahb_system_generator/trunk/conf/ahb_6mst_1slv.conf (revision 3) @@ -0,0 +1,17 @@ +# ahb_master 0: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst0,8,1,7,4,0,0,2,2,0 +# ahb_master 1: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst1,8,1,7,4,0,0,2,2,128 +# ahb_master 2: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst2,8,1,7,4,0,0,2,2,256 +# ahb_master 3: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst3,8,1,7,4,0,0,2,2,384 +# ahb_master 4: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst4,8,1,7,4,0,0,2,2,512 +# ahb_master 5: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst5,8,1,7,4,0,0,2,2,640 +# ahb_slave 0: +# module,name,NOT_USED,type,add_h,add_l,remap add_h,remap add_l,NOT_USED,fifo_le,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat +ahb_slave,ahb_slv0,(SLAVE_LIST),wait,1023,0,1023,0,0,8,1,7,8,0,0,2,2 +# ahb_arbiter 0: module,name,default master,master_list,slave_list,arbitration type +ahb_arbiter,ahb_arb0,0,(0,1,2,3,4,5),(0),0 Index: ahb_system_generator/trunk/conf/ahb_6mst_3slv.conf =================================================================== --- ahb_system_generator/trunk/conf/ahb_6mst_3slv.conf (nonexistent) +++ ahb_system_generator/trunk/conf/ahb_6mst_3slv.conf (revision 3) @@ -0,0 +1,23 @@ +# ahb_master 0: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst0,4,1,3,4,1,1,1,1,0 +# ahb_master 1: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst1,8,1,7,4,0,1,2,2,128 +# ahb_master 2: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst2,2,1,1,4,1,0,1,3,256 +# ahb_master 3: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst3,8,1,7,4,1,1,2,2,384 +# ahb_master 4: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst4,8,1,7,4,0,1,1,4,1024 +# ahb_master 5: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr +ahb_master,ahb_mst5,2,1,1,4,1,0,2,1,1152 +# ahb_slave 0: +# module,name,NOT_USED,type,add_h,add_l,remap add_h,remap add_l,NOT_USED,fifo_le,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat +ahb_slave,ahb_slv0,(SLAVE_LIST),wait,1023,0,1023,0,0,8,1,7,8,0,0,2,2 +# ahb_slave 1: +# module,name,NOT_USED,type,add_h,add_l,remap add_h,remap add_l,NOT_USED,fifo_le,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat +ahb_slave,ahb_slv1,(SLAVE_LIST),wait,1023,0,1023,0,0,8,1,7,8,0,0,2,2 +# ahb_slave 2: +# module,name,NOT_USED,type,add_h,add_l,remap add_h,remap add_l,NOT_USED,fifo_le,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat +ahb_slave,ahb_slv2,(SLAVE_LIST),wait,1023,0,1023,0,0,8,1,7,8,0,0,2,2 +# ahb_arbiter 0: module,name,default master,master_list,slave_list,arbitration type +ahb_arbiter,ahb_arb0,0,(5,4,3,2,1,0),(2,1,0),0 Index: ahb_system_generator/trunk/scripts/vdiff.pl =================================================================== --- ahb_system_generator/trunk/scripts/vdiff.pl (nonexistent) +++ ahb_system_generator/trunk/scripts/vdiff.pl (revision 3) @@ -0,0 +1,50 @@ +#!/usr/bin/perl + +open(FIL1,"<$ARGV[0]")|| die "## cannot open reference $ARGV[0]\nUSAGE: vdiff.pl ref_file out_file\n"; +open(FIL2,"<$ARGV[1]")|| die "## cannot open log file $ARGV[1]\nUSAGE: vdiff.pl ref_file out_file\n"; +$ok=1; +$lines=0; + + + while(){ + $lines++; + if(/(\w+)\s+\w+\s+\w+\s+(\w+)\s+\w+\s+(\w+)/){ + $timel=$1; + $addrl=$2; + $valuel=$3; +# print "$1=$timel $2=$addrl $3=$valuel\n"; + $line=; + + + if($line=~/(\w+)\s+\w+\s+\w+\s+(\w+)\s+\w+\s+(\w+)/){ + $timer=$1; + $addrr=$2; + $valuer=$3; +# print "$1=$timer $2=$addrr $3=$valuer\n"; + if(!("$addrl" eq "$addrr")){ + print "#### (line:$lines) < $_ (line:$lines)> $line"; + $ok=0; + } + if((!($valuel=~/U+/)) && (!($valuel eq $valuer))){ + print "#### ------------ $timer $addrr $valuel $valuer \n"; + print "#### (line:$lines)< $_ (line:$lines)> $line"; + $ok=0; + } + +# if((!($valr=~/U+/)) && (!($valr eq $valrr))){ +# print "++++++++++ $addr $vall $valr $1 $2 $3\n"; +# print " (line:$lines)< $_ (line:$lines)> $line"; +# $ok=0; +# } + + } + else { + print "#### log missing from (line:$lines) !!!\n"; + $ok=0; + exit($ok); + } + } + } +exit($ok); + +#exit(-99); Index: ahb_system_generator/trunk/scripts/AHB_GENERATE.pl =================================================================== --- ahb_system_generator/trunk/scripts/AHB_GENERATE.pl (nonexistent) +++ ahb_system_generator/trunk/scripts/AHB_GENERATE.pl (revision 3) @@ -0,0 +1,2496 @@ +#!/usr/bin/perl +use Tk; +use Time::Local; + +use strict; +use strict 'subs'; +#use warnings; + + +#LOCAL VARIABLES + +my $infile=$ENV{DSN}."/scripts/ahb_generate.conf"; + +my $conffile=$ENV{DSN}."/src/ahb_configure.vhd"; +my $matfile=$ENV{DSN}."/src/ahb_matrix.vhd"; +my $sysfile=$ENV{DSN}."/src/ahb_system.vhd"; +my $tbfile=$ENV{DSN}."/src/ahb_tb.vhd"; + + +my @master_list; +my @slave_list; + +my @mst_list; +my @slv_list; +my @pslv_list; + +my $inst_name; +my $entity; + +my $num_arb; +my $num_arb_msts; +my $def_arb_mst; +my @arb_master_list; +my @arb_slave_list; + +my $num_brg; +my $num_brg_slvs; +my $def_brg_slv; +my $brg_master; +my @brg_slave_list; + +my $num_apb; +my $num_apb_slvs; +my $apb_max_addr; +my $apb_slave_id; +my @apb_slave_list; + + +my $alg_number; +my @alg_list = qw/"Fixed" "Round-Robin" "Pseudo-Random" "Locked-Fixed" "Locked-R-R" "Locked-P-R"/; + +my @gen_signal; +my @gen_ahb_signal; +my @gen_conf; +my @gen_comp; +my @gen_tbcomp; +my @gen_uut; +my @ass_signal; + +my $curr_line; +my $cnt; +my $item; + +my $chk=0; +my @tmp_chk; +my @tmp_lst; +my $tmp; + + +my $mat; +my @matrix; + + +# GUI SHAPING +my (@pt)=qw/-side top -fill both -anchor n -pady 10/; +my (@pc)=qw/-side top -fill both -anchor center -pady 10/; +my (@pw)=qw/-side left -fill both -anchor w -padx 10/; +my (@pe)=qw/-side right -fill both -anchor e -padx 10/; + +# GUI FSM +my $state='WinGlobal'; +my $i=0; +my $j; + +my $a; +my $b; +my $c; +my $d; +my $e; +my $f; + +my $mw; +my $frame; + +my $done='disabled'; + +my $masters=-1; +my $slaves=-1; +my $pslaves=-1; +my $arbs=-1; +my $ahbs=-1; +my $apbs=-1; + +my @master; +my @slave; +my @pslave; +my @arb; +my @ahb; +my @apb; +my @uut; + +my @tmp_mat; + + +sub ResetConf + +{ +$state='WinGlobal'; +$masters=-1; +$slaves=-1; +$pslaves=-1; +$arbs=-1; +$ahbs=-1; +$apbs=-1; +$#master=-1; +$#slave=-1; +$#pslave=-1; +$#arb=-1; +$#ahb=-1; +$#apb=-1; +} + +sub ReadConf +{ + +$state='WinGlobal'; +seek(file1,0,0); +$masters=-1; +$slaves=-1; +$pslaves=-1; +$arbs=-1; +$ahbs=-1; +$apbs=-1; + + +while(defined($curr_line=)) { + chop $curr_line; + if($curr_line =~ /^#/) { + print "# Comment skipped ...\n"; + } elsif($curr_line =~ /^(ahb_master),(\w+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+)$/){ + $masters++; + print "Reading AHB Master $masters...\n"; + $master[$masters]{"module"}=$1; + $master[$masters]{"name"}=$2; + $master[$masters]{"id"}=$masters; + $master[$masters]{"fifo_ln"}=$3; + $master[$masters]{"fifo_he"}=$4; + $master[$masters]{"fifo_hf"}=$5; + $master[$masters]{"num_bits_addr"}=$6; + $master[$masters]{"write_burst"}=$7; + $master[$masters]{"read_burst"}=$8; + $master[$masters]{"write_lat"}=$9; + $master[$masters]{"read_lat"}=$10; + $uut[$masters]{"base_addr"}=$11; + } elsif($curr_line =~ /^(ahb_slave),(\w+),\((.*)\),(\w+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+),(\d+)$/){ + $slaves++; + print "Reading AHB Slave $slaves...\n"; + $slave[$slaves]{"module"}=$1; + $slave[$slaves]{"name"}=$2; + foreach $item (split(',',$3)) { + $slave[$slaves]{"list"} .= " $item"; + } + $slave[$slaves]{"id"}=$slaves; + $slave[$slaves]{"type"}=$4; + $slave[$slaves]{"add_h"}=$5; + $slave[$slaves]{"add_l"}=$6; + $slave[$slaves]{"add_hh"}=$7; + $slave[$slaves]{"add_ll"}=$8; + $slave[$slaves]{"alg"}=$9; + $slave[$slaves]{"fifo_ln"}=$10; + $slave[$slaves]{"fifo_he"}=$11; + $slave[$slaves]{"fifo_hf"}=$12; + $slave[$slaves]{"num_bits_addr"}=$13; + $slave[$slaves]{"write_burst"}=$14; + $slave[$slaves]{"read_burst"}=$15; + $slave[$slaves]{"write_lat"}=$16; + $slave[$slaves]{"read_lat"}=$17; + } elsif($curr_line =~ /^(apb_slave),(\w+),(\d+),(\d+),(\d+),(\d+),(\d+)$/){ + $pslaves++; + print "Reading APB Slave $pslaves...\n"; + $pslave[$pslaves]{"module"}=$1; + $pslave[$pslaves]{"name"}=$2; + $pslave[$pslaves]{"id"}=$pslaves; + $pslave[$pslaves]{"add_h"}=$3; + $pslave[$pslaves]{"add_l"}=$4; + $pslave[$pslaves]{"add_hh"}=$5; + $pslave[$pslaves]{"add_ll"}=$6; + $pslave[$pslaves]{"num_bits_addr"}=$7; + } elsif($curr_line =~ /^(ahb_arbiter),(\w+),(\d+),\((.*)\),\((.*)\),(\d+)$/){ + $arbs++; + print "Reading AHB Arbiter $arbs...\n"; + $arb[$arbs]{"module"}=$1; + $arb[$arbs]{"name"}=$2; + $arb[$arbs]{"id"}=$arbs; + $arb[$arbs]{"def"}=$3; + foreach $item (split(',',$4)) { + $arb[$arbs]{"m_list"} .= " $item"; + } + foreach $item (split(',',$5)) { + $arb[$arbs]{"s_list"} .= " $item"; + } + $arb[$arbs]{"alg"}=$6; + } elsif($curr_line =~ /^(ahb_bridge),(\w+),(\d+),(\d+),\((.*)\),(\d+)$/){ + $ahbs++; + print "Reading AHB Bridge $ahbs...\n"; + $ahb[$ahbs]{"module"}=$1; + $ahb[$ahbs]{"name"}=$2; + $ahb[$ahbs]{"id"}=$ahbs; + $ahb[$ahbs]{"alg"}=$3; + $ahb[$ahbs]{"def"}=$4; + foreach $item (split(',',$5)) { + $ahb[$ahbs]{"list"} .= " $item"; + } + $ahb[$ahbs]{"mst"}=$6; + } elsif($curr_line =~ /^(apb_bridge),(\w+),(\d+),(\d+),\((.*)\)$/){ + $apbs++; + print "Reading APB Bridge $apbs...\n"; + $apb[$apbs]{"module"}=$1; + $apb[$apbs]{"name"}=$2; + $apb[$apbs]{"id"}=$apbs; + $apb[$apbs]{"num_bits_addr"}=$3; + $apb[$apbs]{"slv"}=$4; + foreach $item (split(',',$5)) { + $apb[$apbs]{"list"} .= " $item"; + } + + } else { + print "#### wrong format!!!\n"; + } +# close(file1); +} + + +sub SaveConf +{ + +$state='WinGlobal'; +open(file1,">$infile")|| die "Cannot write ahb configuration output file $infile\n"; + + +$i=0; +while($i<=$masters) { + print file1 "# ahb_master $i: module,name,fifo_length,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat,UUT_BaseAddr\n"; + print file1 "$master[$i]{\"module\"},"; + print file1 "$master[$i]{\"name\"},"; + print file1 "$master[$i]{\"fifo_ln\"},"; + print file1 "$master[$i]{\"fifo_he\"},"; + print file1 "$master[$i]{\"fifo_hf\"},"; + print file1 "$master[$i]{\"num_bits_addr\"},"; + print file1 "$master[$i]{\"write_burst\"},"; + print file1 "$master[$i]{\"read_burst\"},"; + print file1 "$master[$i]{\"write_lat\"},"; + print file1 "$master[$i]{\"read_lat\"},"; + print file1 "$uut[$i]{\"base_addr\"}\n"; + $i++; + } + +$i=0; +while($i<=$slaves) { + print file1 "# ahb_slave $i: +# module,name,NOT_USED,type,add_h,add_l,remap add_h,remap add_l,NOT_USED,fifo_le,fifo_he,fifo_hf,num_bits_adds,write_burst,read_burst,write_lat,read_lat\n"; + print file1 "$slave[$i]{\"module\"},"; + print file1 "$slave[$i]{\"name\"},"; + print file1 "("; + $_=$slave[$i]{"list"}; + s/^[ ]+//g; + s/[ ]+$//g; + s/[ ]+/,/g; + print file1 "$_),"; +# print file1 "$slave[$i]{\"id\"},"; + print file1 "$slave[$i]{\"type\"},"; + print file1 "$slave[$i]{\"add_h\"},"; + print file1 "$slave[$i]{\"add_l\"},"; + print file1 "$slave[$i]{\"add_hh\"},"; + print file1 "$slave[$i]{\"add_ll\"},"; + print file1 "$slave[$i]{\"alg\"},"; + print file1 "$slave[$i]{\"fifo_ln\"},"; + print file1 "$slave[$i]{\"fifo_he\"},"; + print file1 "$slave[$i]{\"fifo_hf\"},"; + print file1 "$slave[$i]{\"num_bits_addr\"},"; + print file1 "$slave[$i]{\"write_burst\"},"; + print file1 "$slave[$i]{\"read_burst\"},"; + print file1 "$slave[$i]{\"write_lat\"},"; + print file1 "$slave[$i]{\"read_lat\"}\n"; + $i++; +} + +$i=0; +while($i<=$pslaves) { + print file1 "# apb_slave $i: module,name,add_h,add_l,remap add_h,remap add_l,num_bits_adds\n"; + print file1 "$pslave[$i]{\"module\"},"; + print file1 "$pslave[$i]{\"name\"},"; +# print file1 "$pslave[$i]{\"id\"},"; + print file1 "$pslave[$i]{\"add_h\"},"; + print file1 "$pslave[$i]{\"add_l\"},"; + print file1 "$pslave[$i]{\"add_hh\"},"; + print file1 "$pslave[$i]{\"add_ll\"},"; + print file1 "$pslave[$i]{\"num_bits_addr\"}\n"; + $i++; + } + +$i=0; +while($i<=$arbs) { + print file1 "# ahb_arbiter $i: module,name,default master,master_list,slave_list,arbitration type\n"; + print file1 "$arb[$i]{\"module\"},"; + print file1 "$arb[$i]{\"name\"},"; +# print file1 "$arb[$i]{\"id\"},"; + print file1 "$arb[$i]{\"def\"},"; + print file1 "("; + $_=$arb[$i]{"m_list"}; + s/^[ ]+//g; + s/[ ]+$//g; + s/[ ]+/,/g; + print file1 "$_),"; + print file1 "("; + $_=$arb[$i]{"s_list"}; + s/^[ ]+//g; + s/[ ]+$//g; + s/[ ]+/,/g; + print file1 "$_),"; + print file1 "$arb[$i]{\"alg\"}\n"; + $i++; +} + +$i=0; +while($i<=$ahbs) { + print file1 "# ahb_bridge $i: module,name,arbitration type,default slave,slave_list,master\n"; + print file1 "$ahb[$i]{\"module\"},"; + print file1 "$ahb[$i]{\"name\"},"; +# print file1 "$ahb[$i]{\"id\"},"; + print file1 "$ahb[$i]{\"alg\"},"; + print file1 "$ahb[$i]{\"def\"},"; + print file1 "("; + $_=$ahb[$i]{"list"}; + s/^[ ]+//g; + s/[ ]+$//g; + s/[ ]+/,/g; + print file1 "$_),"; + print file1 "$ahb[$ahbs]{\"mst\"}\n"; + $i++; +} + + +$i=0; +while($i<=$apbs) { + print file1 "# apb_bridge $i: module,name,num_bits_adds,slave,periph list\n"; + print file1 "$apb[$i]{\"module\"},"; + print file1 "$apb[$i]{\"name\"},"; +# print file1 "$apb[$i]{\"id\"},"; + print file1 "$apb[$i]{\"num_bits_addr\"},"; + print file1 "$apb[$i]{\"slv\"},"; + print file1 "("; + $_=$apb[$i]{"list"}; + s/^[ ]+//g; + s/[ ]+$//g; + s/[ ]+/,/g; + print file1 "$_)\n"; + $i++; + } + +} + + +sub gen_master +{ + + my $tmp_mst=shift(@_); + + @gen_tbcomp = (@gen_tbcomp, " +$tmp_mst->{\"name\"}: ahb_master +generic map( + fifohempty_level => $tmp_mst->{\"fifo_he\"}, + fifohfull_level => $tmp_mst->{\"fifo_hf\"}, + fifo_length => $tmp_mst->{\"fifo_ln\"}) +port map ( + hresetn => hresetn, + hclk => hclk, + mst_in => ahb_mst_$tmp_mst->{\"id\"}_in, + mst_out => ahb_mst_$tmp_mst->{\"id\"}_out, + dma_start => dma_start($tmp_mst->{\"id\"}), + m_wrap_out => m_wrap_out($tmp_mst->{\"id\"}), + m_wrap_in => m_wrap_in($tmp_mst->{\"id\"}), + eot_int => eot_int($tmp_mst->{\"id\"}), + slv_running => zero, + mst_running => open); + +$tmp_mst->{\"name\"}_wrap: mst_wrap +generic map( +--synopsys translate_off +dump_file => \"m$tmp_mst->{\"id\"}.log\", +dump_type => dump_all, +--synopsys translate_on +ahb_max_addr => $tmp_mst->{\"num_bits_addr\"}, +m_const_lat_write => $tmp_mst->{\"write_lat\"}, +m_const_lat_read => $tmp_mst->{\"read_lat\"}, +m_write_burst => $tmp_mst->{\"write_burst\"}, +m_read_burst => $tmp_mst->{\"read_burst\"}) +port map( + hresetn => hresetn, + clk => hclk, + conf => conf($tmp_mst->{\"id\"}), + dma_start => dma_start($tmp_mst->{\"id\"}), + m_wrap_in => m_wrap_out($tmp_mst->{\"id\"}), + m_wrap_out => m_wrap_in($tmp_mst->{\"id\"})); +"); + + + @gen_uut = (@gen_uut, " +uut_stimulator_$tmp_mst->{\"id\"}: uut_stimulator +generic map( +enable => 1, +stim_type => stim_$tmp_mst->{\"id\"}, +eot_enable => 1) +port map( + hclk => hclk, + hresetn => hresetn, + amba_error => zero, + eot_int => eot_int($tmp_mst->{\"id\"}), + conf => conf($tmp_mst->{\"id\"}), + sim_end => sim_end($tmp_mst->{\"id\"})); + +"); + + +} + +sub gen_slave { + +my $tmp_slv=shift(@_); + +#if ($tmp_slv->{"type"}=='wait') { +#@gen_tbcomp = (@gen_tbcomp, " +#$tmp_slv->{\"name\"}: ahb_single_slave"); +#} else { +@gen_tbcomp = (@gen_tbcomp, " +$tmp_slv->{\"name\"}: ahb_slave_$tmp_slv->{\"type\"}"); +#}; + +@gen_tbcomp = (@gen_tbcomp, " +generic map( + num_slv => $tmp_slv->{\"id\"}, + fifohempty_level => $tmp_slv->{\"fifo_he\"}, + fifohfull_level => $tmp_slv->{\"fifo_hf\"}, + fifo_length => $tmp_slv->{\"fifo_ln\"}) +port map ( + hresetn => hresetn, + hclk => hclk, + remap => remap, + slv_in => ahb_slv_$tmp_slv->{\"id\"}_in, + slv_out => ahb_slv_$tmp_slv->{\"id\"}_out, + s_wrap_out => s_wrap_out($tmp_slv->{\"id\"}), + s_wrap_in => s_wrap_in($tmp_slv->{\"id\"}), + mst_running => zero, + prior_in => zero, + slv_running => open, + slv_err => open); + + +$tmp_slv->{\"name\"}_wrap: slv_mem +generic map( +--synopsys translate_off +dump_file => \"s$tmp_slv->{\"id\"}.log\", +dump_type => dump_all, +--synopsys translate_on +ahb_max_addr => $tmp_slv->{\"num_bits_addr\"}, +s_const_lat_write => $tmp_slv->{\"write_lat\"}, +s_const_lat_read => $tmp_slv->{\"read_lat\"}, +s_write_burst => $tmp_slv->{\"write_burst\"}, +s_read_burst => $tmp_slv->{\"read_burst\"}) +port map( + hresetn => hresetn, + clk => hclk, + conf => no_conf_s, + dma_start => open, + s_wrap_in => s_wrap_out($tmp_slv->{\"id\"}), + s_wrap_out => s_wrap_in($tmp_slv->{\"id\"})); + +"); + + +} + + + +sub gen_pslave +{ +my $tmp_pslv=shift(@_); +@gen_tbcomp = (@gen_tbcomp, " +$tmp_pslv->{\"name\"}: apb_slave +generic map( + --synopsys translate_off + dump_file => \"p$tmp_pslv->{\"id\"}.log\", + --synopsys translate_on + apb_slv_addr => $tmp_pslv->{\"num_bits_addr\"}) +port map ( + hresetn => hresetn, + hclk => hclk, + apb_in => apb_slv_$tmp_pslv->{\"id\"}_in, + apb_out => apb_slv_$tmp_pslv->{\"id\"}_out); + +"); + + +} + + + +sub gen_arbiter +{ + my $tmp_arb=shift(@_); + + @arb_master_list = split(' ',$tmp_arb->{"m_list"}); + $def_arb_mst = $arb_master_list[0]; + $num_arb_msts = $#arb_master_list+1; + @arb_slave_list = split(' ',$tmp_arb->{"s_list"}); + + print "\nModule/ID: $tmp_arb->{\"module\"}, $tmp_arb->{\"id\"}"; + print "\nName: $tmp_arb->{\"name\"}"; + print "\nMasters'list:\n(@arb_master_list)"; + print "\nDefault master: $tmp_arb->{\"def\"}"; + print "\nType of arbitration: ".$alg_list[$tmp_arb->{"alg"}]; + print "\nSlaves'list:\n(@arb_slave_list)\n\n"; + + $cnt=0; + foreach $item (@arb_master_list) { + ++$mst_list[$item]; + if ($item==$tmp_arb->{"def"}) {$def_arb_mst=$cnt;} + $cnt++; + } + + foreach $item (@arb_slave_list) {++$slv_list[$item];} + + @gen_comp = (@gen_comp," +$tmp_arb->{\"name\"}: $tmp_arb->{\"module\"} +generic map( +num_arb => $tmp_arb->{\"id\"}, +num_arb_msts => $num_arb_msts, +num_slvs => ".($#arb_slave_list+1).", +def_arb_mst => $def_arb_mst, +alg_number => $tmp_arb->{\"alg\"}) +port map( + hresetn => hresetn, + hclk => hclk, + remap => remap, + mst_in_v => mst_in_arb_$tmp_arb->{\"id\"}_v(".($num_arb_msts-1)." downto 0), + mst_out_v => mst_out_arb_$tmp_arb->{\"id\"}_v(".($num_arb_msts-1)." downto 0), + slv_in_v => slv_in_arb_$tmp_arb->{\"id\"}_v($#arb_slave_list downto 0), + slv_out_v => slv_out_arb_$tmp_arb->{\"id\"}_v($#arb_slave_list downto 0)); + +"); + + @gen_signal = (@gen_signal, +"signal mst_out_arb_$tmp_arb->{\"id\"}_v: mst_in_v_t(".($num_arb_msts-1)." downto 0); +signal mst_in_arb_$tmp_arb->{\"id\"}_v: mst_out_v_t(".($num_arb_msts-1)." downto 0); +signal slv_out_arb_$tmp_arb->{\"id\"}_v: slv_in_v_t($#arb_slave_list downto 0); +signal slv_in_arb_$tmp_arb->{\"id\"}_v: slv_out_v_t($#arb_slave_list downto 0); +"); + + $cnt = $#arb_master_list; + foreach $item (@arb_master_list){ + @ass_signal = (@ass_signal, "ahb_mst_".$item."_in <= mst_out_arb_$tmp_arb->{\"id\"}_v($cnt);\n"); + @ass_signal = (@ass_signal, "mst_in_arb_$tmp_arb->{\"id\"}_v($cnt) <= ahb_mst_".$item."_out;\n"); + $cnt--; + } + + $cnt = $#arb_slave_list; + foreach $item (@arb_slave_list){ + @ass_signal = (@ass_signal, "ahb_slv_".$item."_in <= slv_out_arb_$tmp_arb->{\"id\"}_v($cnt);\n"); + @ass_signal = (@ass_signal, "slv_in_arb_$tmp_arb->{\"id\"}_v($cnt) <= ahb_slv_".$item."_out;\n"); + $cnt--; + } +} + + +sub gen_bridge +{ + + my $tmp_brg=shift(@_); + + @brg_slave_list = split(' ',$tmp_brg->{"list"}); + $def_brg_slv=$brg_slave_list[0]; + $num_brg_slvs = $#brg_slave_list+1; + + + print "Module/ID: $tmp_brg->{\"module\"}, $tmp_brg->{\"id\"}"; + print "\nName: $tmp_brg->{\"name\"}"; + print "\nSlaves'list:\n(@brg_slave_list)"; + print "\nDefault slave: $tmp_brg->{\"def\"}"; + print "\nType of arbitration: ".$alg_list[$tmp_brg->{"alg"}]; + print "\nMaster: $tmp_brg->{\"mst\"}\n\n"; + + + --$mst_list[$tmp_brg->{"mst"}]; + @gen_signal = (@gen_signal, "signal ahb_mst_$tmp_brg->{\"mst\"}_in: mst_in_t;\n"); + @gen_signal = (@gen_signal, "signal ahb_mst_$tmp_brg->{\"mst\"}_out: mst_out_t;\n"); + + + $cnt = 0; + foreach $item (@brg_slave_list) { + --$slv_list[$item]; + @gen_signal = (@gen_signal, "signal ahb_slv_".$item."_in: slv_in_t;\n"); + @gen_signal = (@gen_signal, "signal ahb_slv_".$item."_out: slv_out_t;\n"); + if ($item==$tmp_brg->{"def"}) {$def_brg_slv=$cnt;} + $cnt++; + } + + + @gen_comp = (@gen_comp, "\n$tmp_brg->{\"name\"}: $tmp_brg->{\"module\"}\n"); + @gen_comp = (@gen_comp, "generic map(\n"); + @gen_comp = (@gen_comp, "num_brg => $tmp_brg->{\"id\"},\n"); + @gen_comp = (@gen_comp, "num_brg_slvs => $num_brg_slvs,\n"); + @gen_comp = (@gen_comp, "def_brg_slv => $def_brg_slv,\n"); + @gen_comp = (@gen_comp, "alg_number => $tmp_brg->{\"alg\"})\n"); + @gen_comp = (@gen_comp, "port map(\n"); + @gen_comp = (@gen_comp, " hresetn => hresetn,\n"); + @gen_comp = (@gen_comp, " hclk => hclk,\n"); + @gen_comp = (@gen_comp, " remap => remap,\n"); + @gen_comp = (@gen_comp, " slv_in_v => slv_in_brg_$tmp_brg->{\"id\"}_v($#brg_slave_list downto 0),\n"); + @gen_comp = (@gen_comp, " slv_out_v => slv_out_brg_$tmp_brg->{\"id\"}_v($#brg_slave_list downto 0),\n"); + @gen_comp = (@gen_comp, " mst_in => mst_in_brg_$tmp_brg->{\"id\"},\n"); + @gen_comp = (@gen_comp, " mst_out => mst_out_brg_$tmp_brg->{\"id\"},\n"); + @gen_comp = (@gen_comp, " slv_err => open,\n"); + @gen_comp = (@gen_comp, " mst_err => open);\n"); + @gen_comp = (@gen_comp, "\n\n"); + + @gen_signal = (@gen_signal, "signal mst_out_brg_$tmp_brg->{\"id\"}: mst_out_t;\n"); + @gen_signal = (@gen_signal, "signal mst_in_brg_$tmp_brg->{\"id\"}: mst_in_t;\n"); + @gen_signal = (@gen_signal, "signal slv_out_brg_$tmp_brg->{\"id\"}_v: slv_out_v_t($#brg_slave_list downto 0);\n"); + @gen_signal = (@gen_signal, "signal slv_in_brg_$tmp_brg->{\"id\"}_v: slv_in_v_t($#brg_slave_list downto 0);\n"); + + @ass_signal = (@ass_signal, "ahb_mst_$tmp_brg->{\"mst\"}_out <= mst_out_brg_$tmp_brg->{\"id\"};\n"); + @ass_signal = (@ass_signal, "mst_in_brg_$tmp_brg->{\"id\"} <= ahb_mst_$tmp_brg->{\"mst\"}_in;\n"); + + $cnt = $#brg_slave_list; + foreach $item (@brg_slave_list){ + @ass_signal = (@ass_signal, "ahb_slv_".$item."_out <= slv_out_brg_$tmp_brg->{\"id\"}_v($cnt);\n"); + @ass_signal = (@ass_signal, "slv_in_brg_$tmp_brg->{\"id\"}_v($cnt) <= ahb_slv_".$item."_in;\n"); + $cnt--; + } + +} + + +sub gen_apb +{ + my $tmp_apb=shift(@_); + + @apb_slave_list = split(' ',$tmp_apb->{"list"}); + + print "Module/ID: $tmp_apb->{\"module\"}, $tmp_apb->{\"id\"}"; + print "\nName: $tmp_apb->{\"name\"}"; + print "\nNumber of address bits to decode: $tmp_apb->{\"num_bits_addr\"}"; + print "\nAHB Slave: $tmp_apb->{\"slv\"}"; + print "\nSlaves'list:\n(@apb_slave_list)\n\n"; + + + --$slv_list[$tmp_apb->{"slv"}]; + @gen_signal = (@gen_signal, "signal ahb_slv_$tmp_apb->{\"slv\"}_in: slv_in_t;\n"); + @gen_signal = (@gen_signal, "signal ahb_slv_$tmp_apb->{\"slv\"}_out: slv_out_t;\n"); + + + @gen_comp = (@gen_comp, "$tmp_apb->{\"name\"}: $tmp_apb->{\"module\"}\n"); + @gen_comp = (@gen_comp, "generic map(\n"); + @gen_comp = (@gen_comp, "num_brg => $tmp_apb->{\"id\"},\n"); + @gen_comp = (@gen_comp, "num_brg_slvs => ".($#apb_slave_list+1).",\n"); + @gen_comp = (@gen_comp, "apb_max_addr => $tmp_apb->{\"num_bits_addr\"})\n"); + @gen_comp = (@gen_comp, "port map(\n"); + @gen_comp = (@gen_comp, " hresetn => hresetn,\n"); + @gen_comp = (@gen_comp, " hclk => hclk,\n"); + @gen_comp = (@gen_comp, " remap => remap,\n"); + @gen_comp = (@gen_comp, " slv_in => slv_in_apb_$tmp_apb->{\"id\"},\n"); + @gen_comp = (@gen_comp, " slv_out => slv_out_apb_$tmp_apb->{\"id\"},\n"); + @gen_comp = (@gen_comp, " apb_mst_in => apb_slv_$tmp_apb->{\"id\"}_out_v(".($#apb_slave_list)." downto 0),\n"); + @gen_comp = (@gen_comp, " apb_mst_out => apb_slv_$tmp_apb->{\"id\"}_in_v(".($#apb_slave_list)." downto 0));\n"); + @gen_comp = (@gen_comp, "\n\n"); + + @gen_signal = (@gen_signal, "signal slv_in_apb_$tmp_apb->{\"id\"}: slv_in_t;\n"); + @gen_signal = (@gen_signal, "signal slv_out_apb_$tmp_apb->{\"id\"}: slv_out_t;\n"); + @gen_signal = (@gen_signal, "signal apb_slv_$tmp_apb->{\"id\"}_out_v: apb_out_v_t($#apb_slave_list downto 0);\n"); + @gen_signal = (@gen_signal, "signal apb_slv_$tmp_apb->{\"id\"}_in_v: apb_in_v_t($#apb_slave_list downto 0);\n"); + + @ass_signal = (@ass_signal, "slv_in_apb_$tmp_apb->{\"id\"} <= ahb_slv_$tmp_apb->{\"slv\"}_in;\n"); + @ass_signal = (@ass_signal, "ahb_slv_$tmp_apb->{\"slv\"}_out <= slv_out_apb_$tmp_apb->{\"id\"};\n"); + + $cnt = $#apb_slave_list; + foreach $item (@apb_slave_list){ + @ass_signal = (@ass_signal, "apb_slv_$tmp_apb->{\"id\"}_out_v($cnt) <= apb_slv_${item}_out;\n"); + @ass_signal = (@ass_signal, "apb_slv_${item}_in <= apb_slv_$tmp_apb->{\"id\"}_in_v($cnt);\n"); + ++$pslv_list[$item]; + $cnt--; + } +} + +sub gen_lib() +{ + +print file3 ( +" +--******************************************************************* +--** **** +--** AHB system generator **** +--** **** +--** Author: Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--******************************************************************* +--** **** +--** Copyright (C) 2004 Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--** This source file may be used and distributed without **** +--** restriction provided that this copyright statement is not **** +--** removed from the file and that any derivative work contains **** +--** the original copyright notice and the associated disclaimer.**** +--** **** +--** THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY **** +--** EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED **** +--** TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS **** +--** FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR **** +--** OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, **** +--** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES **** +--** (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE **** +--** GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR **** +--** BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF **** +--** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT **** +--** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT **** +--** OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE **** +--** POSSIBILITY OF SUCH DAMAGE. **** +--** **** +--******************************************************************* +library ieee; +use ieee.std_logic_arith.all; +use ieee.std_logic_misc.all; +use ieee.std_logic_unsigned.all; +use ieee.std_logic_1164.all; + +use work.ahb_package.all; +use work.ahb_configure.all; +use work.ahb_components.all; +"); + +print file4 ( +" +--******************************************************************* +--** **** +--** AHB system generator **** +--** **** +--** Author: Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--******************************************************************* +--** **** +--** Copyright (C) 2004 Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--** This source file may be used and distributed without **** +--** restriction provided that this copyright statement is not **** +--** removed from the file and that any derivative work contains **** +--** the original copyright notice and the associated disclaimer.**** +--** **** +--** THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY **** +--** EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED **** +--** TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS **** +--** FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR **** +--** OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, **** +--** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES **** +--** (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE **** +--** GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR **** +--** BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF **** +--** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT **** +--** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT **** +--** OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE **** +--** POSSIBILITY OF SUCH DAMAGE. **** +--** **** +--******************************************************************* +library ieee; +use ieee.std_logic_arith.all; +use ieee.std_logic_misc.all; +use ieee.std_logic_unsigned.all; +use ieee.std_logic_1164.all; +use IEEE.std_logic_textio.all; + +use work.ahb_package.all; +use work.ahb_configure.all; +use work.ahb_components.all; +"); + +print file5 ( +" +--******************************************************************* +--** **** +--** AHB system generator **** +--** **** +--** Author: Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--******************************************************************* +--** **** +--** Copyright (C) 2004 Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--** This source file may be used and distributed without **** +--** restriction provided that this copyright statement is not **** +--** removed from the file and that any derivative work contains **** +--** the original copyright notice and the associated disclaimer.**** +--** **** +--** THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY **** +--** EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED **** +--** TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS **** +--** FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR **** +--** OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, **** +--** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES **** +--** (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE **** +--** GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR **** +--** BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF **** +--** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT **** +--** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT **** +--** OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE **** +--** POSSIBILITY OF SUCH DAMAGE. **** +--** **** +--******************************************************************* +library ieee; +use ieee.std_logic_arith.all; +use ieee.std_logic_misc.all; +use ieee.std_logic_unsigned.all; +use ieee.std_logic_1164.all; +use IEEE.std_logic_textio.all; + +use work.ahb_package.all; +use work.ahb_configure.all; +use work.ahb_components.all; +"); + +} + +sub gen_ent() +{ +print file3 (" +entity ahb_matrix is +port( +hresetn: in std_logic; +hclk: in std_logic; +"); +$cnt=0; +foreach $item (@mst_list){ + if ($item > 0) { +print file3 (" +ahb_mst_${cnt}_out: in mst_out_t; +ahb_mst_${cnt}_in: out mst_in_t; +"); +@gen_ahb_signal = (@gen_ahb_signal, " +signal ahb_mst_${cnt}_out: mst_out_t; +signal ahb_mst_${cnt}_in: mst_in_t; +"); + }; + $cnt++; +}; +$cnt=0; +foreach $item (@slv_list){ + if ($item > 0) { +print file3 (" +ahb_slv_${cnt}_out: in slv_out_t; +ahb_slv_${cnt}_in: out slv_in_t; +"); +@gen_ahb_signal = (@gen_ahb_signal, " +signal ahb_slv_${cnt}_out: slv_out_t; +signal ahb_slv_${cnt}_in: slv_in_t; +"); + }; + $cnt++; +}; +$cnt=0; +foreach $item (@pslv_list){ + if ($item > 0) { +print file3 (" +apb_slv_${cnt}_out: in apb_out_t; +apb_slv_${cnt}_in: out apb_in_t; +"); +@gen_ahb_signal = (@gen_ahb_signal, " +signal apb_slv_${cnt}_out: apb_out_t; +signal apb_slv_${cnt}_in: apb_in_t; +"); + }; + $cnt++; +}; +print file3 (" +remap: in std_logic + ); +end; + +architecture rtl of ahb_matrix is + +"); + +print file4 (" +entity ahb_system is +port( + hresetn: in std_logic; + hclk: in std_logic; + + eot_int: out std_logic_vector($masters downto 0); + conf: in conf_type_v($masters downto 0); + + remap: in std_logic + ); +end; + +architecture rtl of ahb_system is + + +"); + +print file5 (" +entity ahb_tb is +end; + +architecture rtl of ahb_tb is + + +"); + +} + +sub gen_arrays { + +@gen_conf = " +library ieee; + +use ieee.std_logic_1164.all; +use ieee.std_logic_arith.all; +use work.ahb_package.all; + +package ahb_configure is + +--*************************************************************** +-- definition of custom amba system parameters +--*************************************************************** + +--*************************************************************** +-- AMBA SLAVES address configuration space +--*************************************************************** +--For every slave define HIGH and LOW address, before and after (r)emap + +constant n_u: addr_t := (0, 0);\n\n"; + + +#### PERIPHERAL SLAVES + + for $i (0 .. $pslaves) {@gen_conf = (@gen_conf, "constant $pslave[$i]->{\"name\"}: addr_t := ($pslave[$i]->{\"add_h\"}, $pslave[$i]->{add_l});\n");} + for $i (0 .. $pslaves) {@gen_conf = (@gen_conf, "constant r$pslave[$i]->{\"name\"}: addr_t := ($pslave[$i]->{\"add_hh\"}, $pslave[$i]->{add_ll});\n");} + +#### PERIPHERAL SLAVES ARRAY + + for $i (0 .. 15) { + if ($i <= $pslaves) {$tmp_mat[$i] = ("r$pslave[$i]->{\"name\"}");} else {$tmp_mat[$i] = ("n_u");}; + }; + + @gen_conf = (@gen_conf, "\nconstant pslv_matrix: addr_matrix_t(1 downto 0) := (\n("); + $i=15; + while ($i > 0) {@gen_conf = (@gen_conf, "$tmp_mat[$i],");$i--;} + @gen_conf = (@gen_conf, "$tmp_mat[0]),\n("); + + for $i (0 .. 15) { + if ($i <= $pslaves) {$tmp_mat[$i] = ("$pslave[$i]->{\"name\"}");} else {$tmp_mat[$i] = ("n_u");}; + }; + + $i=15; + while ($i > 0) {@gen_conf = (@gen_conf, "$tmp_mat[$i],");$i--;} + @gen_conf = (@gen_conf, "$tmp_mat[0]));\n\n"); + +#### SLAVES + + for $i (0 .. $slaves) {@gen_conf = (@gen_conf, "constant $slave[$i]->{\"name\"}: addr_t := ($slave[$i]->{\"add_h\"}, $slave[$i]->{add_l});\n");} + for $i (0 .. $slaves) {@gen_conf = (@gen_conf, "constant r$slave[$i]->{\"name\"}: addr_t := ($slave[$i]->{\"add_hh\"}, $slave[$i]->{add_ll});\n");} + +#### SLAVES ARRAY + + for $i (0 .. 15) { + if ($i <= $slaves) { + $tmp_mat[$i] = ("r$slave[$i]->{\"name\"}"); + } else { + $tmp_mat[$i] = ("n_u"); + }; + }; + + @gen_conf = (@gen_conf, "\nconstant slv_matrix: addr_matrix_t(1 downto 0) := (\n("); + $i=15; + while ($i > 0) {@gen_conf = (@gen_conf, "$tmp_mat[$i],");$i--;} + @gen_conf = (@gen_conf, "$tmp_mat[0]),\n("); + + for $i (0 .. 15) { + if ($i <= $slaves) { + $tmp_mat[$i] = ("$slave[$i]->{\"name\"}"); + } else { + $tmp_mat[$i] = ("n_u"); + }; + }; + + $i=15; + while ($i > 0) {@gen_conf = (@gen_conf, "$tmp_mat[$i],");$i--;} + @gen_conf = (@gen_conf, "$tmp_mat[0]));\n\n"); + + +#### AHB ARBITERS ARRAY + + if ($arbs>0) { + @gen_conf = (@gen_conf, "constant arb_matrix: addr_matrix_t($arbs downto 0):= (\n"); + @gen_signal = (@gen_signal, "signal addr_arb_matrix: addr_matrix_t($arbs downto 0);\n"); + } elsif ($arbs==0) { + @gen_conf = (@gen_conf, "constant arb_matrix: addr_matrix_t(1 downto 0):= (\n"); + @gen_signal = (@gen_signal, "signal addr_arb_matrix: addr_matrix_t($arbs downto 0);\n"); + } + + + if ($arbs==0) { + @arb_slave_list = split(' ',$arb[$0]->{"s_list"}); + $j=15; + while ($j>$#arb_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("ahb_slv".shift(@arb_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]),\n"); + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]\)\);\n\n"); + + } else { + + $i=$arbs; + while ($i>=0) { + @arb_slave_list = split(' ',$arb[$i]->{"s_list"}); + $j=15; + while ($j>$#arb_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("ahb_slv".shift(@arb_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + + if ($i==0) {@gen_conf = (@gen_conf, "$tmp_mat[$0]));\n\n");} + else {@gen_conf = (@gen_conf, "$tmp_mat[$0]),\n");} + + $i--; + }; + }; + + + if ($arbs>0) { + @gen_conf = (@gen_conf, "constant rarb_matrix: addr_matrix_t($arbs downto 0):= (\n"); + } elsif ($arbs==0) { + @gen_conf = (@gen_conf, "constant rarb_matrix: addr_matrix_t(1 downto 0):= (\n"); + }; + + + if ($arbs==0) { + @arb_slave_list = split(' ',$arb[$0]->{"s_list"}); + $j=15; + while ($j>$#arb_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("rahb_slv".shift(@arb_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]),\n"); + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]\)\);\n\n"); + + } else { + + $i=$arbs; + while ($i>=0) { + + @arb_slave_list = split(' ',$arb[$i]->{"s_list"}); + $j=15; + while ($j>$#arb_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("rahb_slv".shift(@arb_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + + if ($i==0) {@gen_conf = (@gen_conf, "$tmp_mat[$0]));\n\n");} + else {@gen_conf = (@gen_conf, "$tmp_mat[$0]),\n");} + + $i--; + } + } + + + +#### AHB-AHB BRIDGES ARRAY + + if ($ahbs>0) { + @gen_conf = (@gen_conf, "constant ahbbrg_matrix: addr_matrix_t($ahbs downto 0):= (\n"); + @gen_signal = (@gen_signal, "signal addr_ahbbrg_matrix: addr_matrix_t($ahbs downto 0);\n"); + } elsif ($ahbs==0) { + @gen_conf = (@gen_conf, "constant ahbbrg_matrix: addr_matrix_t(1 downto 0):= (\n"); + @gen_signal = (@gen_signal, "signal addr_ahbbrg_matrix: addr_matrix_t(1 downto 0);\n"); + } else { + @gen_conf = (@gen_conf, +"constant ahbbrg_matrix: addr_matrix_t(1 downto 0) := ( +(n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u), +(n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u)); + +constant rahbbrg_matrix: addr_matrix_t(1 downto 0) := ( +(n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u), +(n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u)); + +"); + @gen_signal = (@gen_signal, "signal addr_ahbbrg_matrix: addr_matrix_t(1 downto 0);\n"); + } + + if ($ahbs==0) { + + @brg_slave_list = split(' ',$ahb[$0]->{"list"}); + $j=15; + while ($j>$#brg_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("ahb_slv".shift(@brg_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]),\n"); + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]\)\);\n\n"); + + } else { + + $i=$ahbs; + while ($i>=0) { + + @brg_slave_list = split(' ',$ahb[$i]->{"list"}); + $j=15; + while ($j>$#brg_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("ahb_slv".shift(@brg_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + + if ($i==0) {@gen_conf = (@gen_conf, "$tmp_mat[$0]));\n\n");} + else {@gen_conf = (@gen_conf, "$tmp_mat[$0]),\n");} + + $i--; + }; + } + + if ($ahbs>0) { + @gen_conf = (@gen_conf, "constant rahbbrg_matrix: addr_matrix_t($ahbs downto 0):= (\n"); + } elsif ($ahbs==0) { + @gen_conf = (@gen_conf, "constant rahbbrg_matrix: addr_matrix_t(1 downto 0):= (\n"); + }; + + if ($ahbs==0) { + + @brg_slave_list = split(' ',$ahb[$0]->{"list"}); + $j=15; + while ($j>$#brg_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("rahb_slv".shift(@brg_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]),\n"); + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]\)\);\n\n"); + + } else { + + $i=$ahbs; + while ($i>=0) { + + @brg_slave_list = split(' ',$ahb[$i]->{"list"}); + $j=15; + while ($j>$#brg_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("rahb_slv".shift(@brg_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + + if ($i==0) {@gen_conf = (@gen_conf, "$tmp_mat[$0]));\n\n");} + else {@gen_conf = (@gen_conf, "$tmp_mat[$0]),\n");} + + $i--; + }; + }; + +#### APB BRIDGES ARRAY + + if ($apbs>0) { + @gen_conf = (@gen_conf, "constant apbbrg_matrix: addr_matrix_t($apbs downto 0):= (\n"); + @gen_signal = (@gen_signal, "signal addr_apbbrg_matrix: addr_matrix_t($apbs downto 0);\n"); + } elsif ($apbs==0) { + @gen_conf = (@gen_conf, "constant apbbrg_matrix: addr_matrix_t(1 downto 0):= (\n"); + @gen_signal = (@gen_signal, "signal addr_apbbrg_matrix: addr_matrix_t(1 downto 0);\n"); + } else { + @gen_conf = (@gen_conf, +"constant apbbrg_matrix: addr_matrix_t(1 downto 0) := ( +(n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u), +(n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u)); + +constant rapbbrg_matrix: addr_matrix_t(1 downto 0) := ( +(n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u), +(n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u,n_u)); + +"); + @gen_signal = (@gen_signal, "signal addr_apbbrg_matrix: addr_matrix_t(1 downto 0);\n"); + }; + + if ($apbs==0) { + + @apb_slave_list = split(' ',$apb[$0]->{"list"}); + $j=15; + while ($j>$#apb_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("apb_slv".shift(@apb_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]),\n"); + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]\)\);\n\n"); + + } elsif ($apbs>0) { + + $i=$apbs; + while ($i>=0) { + + @apb_slave_list = split(' ',$apb[$i]->{"list"}); + $j=15; + while ($j>$#apb_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("apb_slv".shift(@apb_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + + if ($i==0) {@gen_conf = (@gen_conf, "$tmp_mat[$0]));\n\n");} + else {@gen_conf = (@gen_conf, "$tmp_mat[$0]),\n");} + + $i--; + }; + } else { + ; + }; + + if ($apbs>0) { + @gen_conf = (@gen_conf, "constant rapbbrg_matrix: addr_matrix_t($apbs downto 0):= (\n"); + } elsif ($apbs==0) { + @gen_conf = (@gen_conf, "constant rapbbrg_matrix: addr_matrix_t(1 downto 0):= (\n"); + }; + + if ($apbs==0) { + + @apb_slave_list = split(' ',$apb[$0]->{"list"}); + $j=15; + while ($j>$#apb_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("rapb_slv".shift(@apb_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]),\n"); + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + @gen_conf = (@gen_conf, "$tmp_mat[$0]\)\);\n\n"); + + } elsif ($apbs>0) { + + $i=$apbs; + while ($i>=0) { + + @apb_slave_list = split(' ',$apb[$i]->{"list"}); + $j=15; + while ($j>$#apb_slave_list) {$tmp_mat[$j] = ("n_u");$j--;} + while ($j>=0) {$tmp_mat[$j] = ("rapb_slv".shift(@apb_slave_list));$j--;} + + $j=15; + @gen_conf = (@gen_conf, "("); + while ($j>0) {@gen_conf = (@gen_conf, "$tmp_mat[$j],");$j--;} + + if ($i==0) {@gen_conf = (@gen_conf, "$tmp_mat[$0]));\n\n");} + else {@gen_conf = (@gen_conf, "$tmp_mat[$0]),\n");} + + $i--; + }; + } else { + ; + }; +#### END OF FILE + +@gen_conf = (@gen_conf," + +end; + +package body ahb_configure is +end; + +"); + +}; + +sub master_init { + $masters += 1; + $master[$masters]{"module"}='ahb_master'; + $master[$masters]{"name"}='ahb_mst'.$masters; + $master[$masters]{"id"}=$masters; + $master[$masters]{"fifo_ln"}='8'; + $master[$masters]{"fifo_he"}='1'; + $master[$masters]{"fifo_hf"}='7'; + $master[$masters]{"num_bits_addr"}='4'; + $master[$masters]{"write_burst"}='0'; + $master[$masters]{"read_burst"}='0'; + $master[$masters]{"write_lat"}='2'; + $master[$masters]{"read_lat"}='2'; + + $uut[$masters]{"base_addr"}='2048'; +}; + +sub slave_init { + $slaves += 1; + $slave[$slaves]{"module"}='ahb_slave'; + $slave[$slaves]{"name"}='ahb_slv'.$slaves; + $slave[$slaves]{"list"}=('SLAVE_LIST'); + $slave[$slaves]{"id"}=$slaves; + $slave[$slaves]{"type"}='wait'; + $slave[$slaves]{"add_h"}='0'; + $slave[$slaves]{"add_l"}='0'; + $slave[$slaves]{"add_hh"}='0'; + $slave[$slaves]{"add_ll"}='0'; + $slave[$slaves]{"alg"}=0; + $slave[$slaves]{"fifo_ln"}='8'; + $slave[$slaves]{"fifo_he"}='1'; + $slave[$slaves]{"fifo_hf"}='7'; + $slave[$slaves]{"num_bits_addr"}='4'; + $slave[$slaves]{"write_burst"}='0'; + $slave[$slaves]{"read_burst"}='0'; + $slave[$slaves]{"write_lat"}='2'; + $slave[$slaves]{"read_lat"}='2'; +}; + +sub pslave_init { + $pslaves += 1; + $pslave[$pslaves]{"module"}='apb_slave'; + $pslave[$pslaves]{"name"}='apb_slv'.$pslaves; + $pslave[$pslaves]{"id"}=$pslaves; + $pslave[$pslaves]{"add_h"}='0'; + $pslave[$pslaves]{"add_l"}='0'; + $pslave[$pslaves]{"add_hh"}='0'; + $pslave[$pslaves]{"add_ll"}='0'; + $pslave[$pslaves]{"num_bits_addr"}='4'; +}; + +sub arb_init { + $arbs += 1; + $arb[$arbs]{"module"}='ahb_arbiter'; + $arb[$arbs]{"name"}='ahb_arb'.$arbs; + $arb[$arbs]{"id"}=$arbs; + $arb[$arbs]{"def"}='DEFAULT_MASTER'; + $arb[$arbs]{"m_list"}=('MASTER_LIST'); + $arb[$arbs]{"s_list"}=('SLAVE_LIST'); + $arb[$arbs]{"alg"}=0; + }; + +sub ahb_init { + $ahbs += 1; + $ahb[$ahbs]{"module"}='ahb_bridge'; + $ahb[$ahbs]{"name"}='ahb_brg'.$ahbs; + $ahb[$ahbs]{"id"}=$ahbs; + $ahb[$ahbs]{"alg"}=0; + $ahb[$ahbs]{"def"}='DEFAULT_SLAVE'; + $ahb[$ahbs]{"list"}=('SLAVE_LIST'); + $ahb[$ahbs]{"mst"}='BRIDGE_MASTER'; + }; + +sub apb_init { + $apbs += 1; + $apb[$apbs]{"module"}='apb_bridge'; + $apb[$apbs]{"name"}='apb_brg'.$apbs; + $apb[$apbs]{"id"}=$apbs; + $apb[$apbs]{"num_bits_addr"}='4'; + $apb[$apbs]{"slv"}='BRIDGE_SLAVE'; + $apb[$apbs]{"list"}=('SLAVE_LIST'); + }; + + +# GUI FUNCTIONS + +sub WinGlobalExit { + $mw->destroy(); +}; + + +sub WinAddMaster { + $state='WinGlobal'; + &master_init; + + $mw = MainWindow->new; + + $frame=$mw->Frame(-label=>"New AHB Master"); + # AHB Master + $frame->pack(@pt); + $frame->Label(-text => "AHB Master name: ")->pack(@pw); + $frame->Entry(-textvariable => \$master[$masters]{"name"})->pack(@pe); + + # id + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "AHB Master number: ")->pack(@pw); + $frame->Entry(-state => 'disabled', -textvariable => \$master[$masters]{"id"})->pack(@pe); + + $frame=$mw->Frame(-label=>"AHB Master internal fifo"); + # fifo length + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Fifo length: ")->pack(@pw); + $frame->Entry(-textvariable => \$master[$masters]{"fifo_ln"})->pack(@pe); + $frame=$mw->Frame(); + # fifo half empty + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Fifo half-empty level: ")->pack(@pw); + $frame->Entry(-textvariable => \$master[$masters]{"fifo_he"})->pack(@pe); + $frame=$mw->Frame(); + # fifo half full + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Fifo half-full level: ")->pack(@pw); + $frame->Entry(-textvariable => \$master[$masters]{"fifo_hf"})->pack(@pe); + $frame=$mw->Frame(); + + # number of addressable bits + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Number of addr bits: ")->pack(@pw); + $frame->Entry(-textvariable => \$master[$masters]{"num_bits_addr"})->pack(@pe); + $frame=$mw->Frame(); + # burst capability in write + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Write burst capability: ")->pack(@pw); + $a = $frame->Radiobutton ( -variable => \$master[$masters]{"write_burst"}, -text => 'YES', -value => '1')->pack(@pw); + $b = $frame->Radiobutton ( -variable => \$master[$masters]{"write_burst"}, -text => 'NO', -value => '0')->pack(@pe); + # burst capability in read + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Read burst capability: ")->pack(@pw); + $c = $frame->Radiobutton ( -variable => \$master[$masters]{"read_burst"}, -text => 'YES', -value => '1')->pack(@pw); + $d = $frame->Radiobutton ( -variable => \$master[$masters]{"read_burst"}, -text => 'NO', -value => '0')->pack(@pe); + # write latency + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Write access latency: ")->pack(@pw); + $frame->Entry(-textvariable => \$master[$masters]{"write_lat"})->pack(@pe); + $frame=$mw->Frame(); + # read latency + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Read access latency: ")->pack(@pw); + $frame->Entry(-textvariable => \$master[$masters]{"read_lat"})->pack(@pe); + $frame=$mw->Frame(); + # UUT base address + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "UUT Base Address: ")->pack(@pw); + $frame->Entry(-textvariable => \$uut[$masters]{"base_addr"})->pack(@pe); + $frame=$mw->Frame(); + + # exit + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button(-text => "cancel", -command =>sub {WinGlobalExit(); $state='WinGlobal'; $masters--;})->pack (@pw); + $frame->Button(-text => "done", -command =>sub {WinGlobalExit(); $state='WinGlobal';})->pack (@pe); + + MainLoop; +}; + + +sub WinAddSlave { + $state='WinGlobal'; + &slave_init; + + $mw = MainWindow->new; + + $frame=$mw->Frame(-label=>"New AHB Slave"); + # AHB Slave + $frame->pack(@pt); + $frame->Label(-text => "AHB Slave name: ")->pack(@pw); + $frame->Entry(-textvariable => \$slave[$slaves]{"name"})->pack(@pe); + + # type:multi/wait/retry/split + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Slave type: ")->pack(@pw); + $a = $frame->Radiobutton (-state => 'disabled', -variable => \$slave[$slaves]{"type"}, -text => 'Multi slave', -value => 'multi')->pack(@pw); + $b = $frame->Radiobutton ( -variable => \$slave[$slaves]{"type"}, -text => 'Single slave, wait', -value => 'wait')->pack(@pw); + $c = $frame->Radiobutton (-state => 'disabled', -variable => \$slave[$slaves]{"type"}, -text => 'Single slave, retry', -value => 'retry')->pack(@pw); + $d = $frame->Radiobutton (-state => 'disabled', -variable => \$slave[$slaves]{"type"}, -text => 'Single slave, split', -value => 'split')->pack(@pw); + + # exit + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button(-text => "cancel", -command =>sub {WinGlobalExit(); $slaves--;})->pack (@pw); + $frame->Button(-text => "done", -command =>sub {WinGlobalExit(); WinDefSlave(); })->pack (@pe); + + MainLoop; +} + + +sub WinDefSlave { + + $state='WinGlobal'; + + $mw = MainWindow->new; + + if ($slave[$slaves]{"type"} eq 'multi') { + + # slave list: first is default + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Slave list: ")->pack(@pw); + $frame->Entry(-textvariable => \$slave[$slaves]{"list"})->pack(@pe); + $frame=$mw->Frame(); + # algorithm number: 0,1,2 + $frame=$mw->Frame(); + + $frame->pack(@pt); + $frame->Label(-text => "Arbitration type: ")->pack(@pw); + $a = $frame->Radiobutton ( -variable => \$slave[$slaves]{"alg"}, -text => 'Fixed ', -value => '0')->pack(@pw); + $b = $frame->Radiobutton ( -variable => \$slave[$slaves]{"alg"}, -text => 'Round Robin ', -value => '1')->pack(@pw); + $c = $frame->Radiobutton ( -variable => \$slave[$slaves]{"alg"}, -text => 'Pseudo Random', -value => '2')->pack(@pw); + $frame=$mw->Frame(); + + } else { + + # id + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "AHB Slave number: ")->pack(@pw); + $frame->Entry(-state => 'disabled', -textvariable => \$slave[$slaves]{"id"})->pack(@pe); + + + if (($slave[$slaves]{"type"} eq 'retry') or ($slave[$slaves]{"type"} eq 'split')) { + + # fifo length + $frame=$mw->Frame(-label=>"AHB Slave internal fifo"); + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Fifo length: ")->pack(@pw); + $frame->Entry( -textvariable => \$slave[$slaves]{"fifo_ln"})->pack(@pe); + $frame=$mw->Frame(); + # fifo half empty + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Fifo half-empty level: ")->pack(@pw); + $frame->Entry( -textvariable => \$slave[$slaves]{"fifo_he"})->pack(@pe); + $frame=$mw->Frame(); + # fifo half full + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Fifo half-full level: ")->pack(@pw); + $frame->Entry( -textvariable => \$slave[$slaves]{"fifo_hf"})->pack(@pe); + $frame=$mw->Frame(); + + } + + # add before remap + $frame=$mw->Frame(-label=>"ADDRESS before remap"); + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Add high-low: ")->pack(@pt); + $frame->Entry(-textvariable => \$slave[$slaves]{"add_h"})->pack(@pw); + $frame->Entry(-textvariable => \$slave[$slaves]{"add_l"})->pack(@pe); + + # add after remap + $frame=$mw->Frame(-label=>"ADDRESS after remap"); + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Add high-low after remap: ")->pack(@pt); + $frame->Entry(-textvariable => \$slave[$slaves]{"add_hh"})->pack(@pw); + $frame->Entry(-textvariable => \$slave[$slaves]{"add_ll"})->pack(@pe); + + # number of addressable bits + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Number of addr bits: ")->pack(@pw); + $frame->Entry(-textvariable => \$slave[$slaves]{"num_bits_addr"})->pack(@pe); + $frame=$mw->Frame(); + # burst capability in write + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Write burst capability: ")->pack(@pw); + $a = $frame->Radiobutton ( -variable => \$slave[$slaves]{"write_burst"}, -text => 'YES', -value => '1')->pack(@pw); + $b = $frame->Radiobutton ( -variable => \$slave[$slaves]{"write_burst"}, -text => 'NO', -value => '0')->pack(@pe); + # burst capability in read + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Read burst capability: ")->pack(@pw); + $c = $frame->Radiobutton ( -variable => \$slave[$slaves]{"read_burst"}, -text => 'YES', -value => '1')->pack(@pw); + $d = $frame->Radiobutton ( -variable => \$slave[$slaves]{"read_burst"}, -text => 'NO', -value => '0')->pack(@pe); + # write latency + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Write access latency: ")->pack(@pw); + $frame->Entry(-textvariable => \$slave[$slaves]{"write_lat"})->pack(@pe); + $frame=$mw->Frame(); + # read latency + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Read access latency: ")->pack(@pw); + $frame->Entry(-textvariable => \$slave[$slaves]{"read_lat"})->pack(@pe); + $frame=$mw->Frame(); + + # exit + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button(-text => "cancel", -command =>sub {WinGlobalExit(); $slaves--; WinAddSlave();})->pack (@pw); + $frame->Button(-text => "done", -command =>sub {WinGlobalExit(); })->pack (@pe); + + MainLoop; + } + +}; + + +sub WinAddPslave { + + $state='WinGlobal'; + &pslave_init; + + $mw = MainWindow->new; + + $frame=$mw->Frame(-label=>"New APB Slave"); + # APB Slave + $frame->pack(@pt); + $frame->Label(-text => "APB Salve name: ")->pack(@pw); + $frame->Entry(-textvariable => \$pslave[$pslaves]{"name"})->pack(@pe); + + # id + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "APB Slave number: ")->pack(@pw); + $frame->Entry(-state => 'disabled', -textvariable => \$pslave[$pslaves]{"id"})->pack(@pe); + + # add before remap + $frame=$mw->Frame(-label=>"ADDRESS before remap"); + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Add high-low: ")->pack(@pt); + $frame->Entry(-textvariable => \$pslave[$pslaves]{"add_h"})->pack(@pw); + $frame->Entry(-textvariable => \$pslave[$pslaves]{"add_l"})->pack(@pe); + + # add after remap + $frame=$mw->Frame(-label=>"ADDRESS after remap"); + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Add high-low after remap: ")->pack(@pt); + $frame->Entry(-textvariable => \$pslave[$pslaves]{"add_hh"})->pack(@pw); + $frame->Entry(-textvariable => \$pslave[$pslaves]{"add_ll"})->pack(@pe); + + # number of addressable bits + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Number of addr bits: ")->pack(@pw); + $frame->Entry(-textvariable => \$pslave[$pslaves]{"num_bits_addr"})->pack(@pe); + $frame=$mw->Frame(); + + # exit + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button(-text => "cancel", -command =>sub {WinGlobalExit(); $pslaves--;})->pack (@pw); + $frame->Button(-text => "done", -command =>sub {WinGlobalExit(); })->pack (@pe); + + MainLoop; +}; + + +sub WinAddArbiter { + $state='WinGlobal'; + &arb_init; + + $mw = MainWindow->new; + + $frame=$mw->Frame(-label=>"New AHB Arbiter"); + # AHB Arbiter + $frame->pack(@pt); + $frame->Label(-text => "AHB Arbiter name: ")->pack(@pw); + $frame->Entry(-textvariable => \$arb[$arbs]{"name"})->pack(@pe); + + # id + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "AHB Arbiter number: ")->pack(@pw); + $frame->Entry(-state => 'disabled', -textvariable => \$arb[$arbs]{"id"})->pack(@pe); + + # Default master + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Default Master: ")->pack(@pw); + $frame->Entry(-textvariable => \$arb[$arbs]{"def"})->pack(@pe); + + # master list: first is default + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Master list: ")->pack(@pw); + $frame->Entry(-textvariable => \$arb[$arbs]{"m_list"})->pack(@pe); + $frame=$mw->Frame(); + + # algorithm number: 0,1,2,3,4,5 + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Arbitration type: ")->pack(@pt); + $a = $frame->Radiobutton ( -variable => \$arb[$arbs]{"alg"}, -text => 'Fixed ', -value => '0')->pack(@pw); + $b = $frame->Radiobutton ( -variable => \$arb[$arbs]{"alg"}, -text => 'Round Robin ', -value => '1')->pack(@pw); + $c = $frame->Radiobutton ( -variable => \$arb[$arbs]{"alg"}, -text => 'Pseudo Random', -value => '2')->pack(@pw); + $d = $frame->Radiobutton ( -variable => \$arb[$arbs]{"alg"}, -text => 'Fixed Modif. ', -value => '3')->pack(@pe); + $e = $frame->Radiobutton ( -variable => \$arb[$arbs]{"alg"}, -text => 'RR Modif. ', -value => '4')->pack(@pe); + $f = $frame->Radiobutton ( -variable => \$arb[$arbs]{"alg"}, -text => 'PR Modif. ', -value => '5')->pack(@pe); + $frame=$mw->Frame(); + + # slave list + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Slave list: ")->pack(@pw); + $frame->Entry(-textvariable => \$arb[$arbs]{"s_list"})->pack(@pe); + $frame=$mw->Frame(); + + # exit + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button(-text => "cancel", -command =>sub {WinGlobalExit(); $arbs--;})->pack (@pw); + $frame->Button(-text => "done", -command =>sub {WinGlobalExit(); })->pack (@pe); + + MainLoop; +}; + + +sub WinAddAhb { + $state='WinGlobal'; + &ahb_init; + + $mw = MainWindow->new; + + $frame=$mw->Frame(-label=>"New AHB Bridge"); + # AHB Bridge + $frame->pack(@pt); + $frame->Label(-text => "AHB Bridge name: ")->pack(@pw); + $frame->Entry(-textvariable => \$ahb[$ahbs]{"name"})->pack(@pe); + + # id + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "AHB Bridge number: ")->pack(@pw); + $frame->Entry(-state => 'disabled', -textvariable => \$ahb[$ahbs]{"id"})->pack(@pe); + + # Default slave + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Default Slave: ")->pack(@pw); + $frame->Entry(-textvariable => \$ahb[$ahbs]{"def"})->pack(@pe); + + # slave list + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Slave list: ")->pack(@pw); + $frame->Entry(-textvariable => \$ahb[$ahbs]{"list"})->pack(@pe); + $frame=$mw->Frame(); + + # master + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Master: ")->pack(@pw); + $frame->Entry(-textvariable => \$ahb[$ahbs]{"mst"})->pack(@pe); + $frame=$mw->Frame(); + + # algorithm number: 0,1,2 + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Arbitration type: ")->pack(@pt); + $a = $frame->Radiobutton ( -variable => \$ahb[$ahbs]{"alg"}, -text => 'Fixed ', -value => '0')->pack(@pw); + $b = $frame->Radiobutton ( -variable => \$ahb[$ahbs]{"alg"}, -text => 'Round Robin ', -value => '1')->pack(@pw); + $c = $frame->Radiobutton ( -variable => \$ahb[$ahbs]{"alg"}, -text => 'Pseudo Random', -value => '2')->pack(@pw); + $frame=$mw->Frame(); + + # exit + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button(-text => "cancel", -command =>sub {WinGlobalExit(); $ahbs--;})->pack (@pw); + $frame->Button(-text => "done", -command =>sub {WinGlobalExit(); })->pack (@pe); + + MainLoop; +}; + + +sub WinAddApb { + + $state='WinGlobal'; + &apb_init; + + $mw = MainWindow->new; + + $frame=$mw->Frame(-label=>"New APB Bridge"); + # APB Bridge + $frame->pack(@pt); + $frame->Label(-text => "APB Bridge name: ")->pack(@pw); + $frame->Entry(-textvariable => \$apb[$apbs]{"name"})->pack(@pe); + + # id + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "AHB Bridge number: ")->pack(@pw); + $frame->Entry(-state => 'disabled', -textvariable => \$apb[$apbs]{"id"})->pack(@pe); + + # number of addressable bits + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "Number of addr bits: ")->pack(@pw); + $frame->Entry(-textvariable => \$apb[$apbs]{"num_bits_addr"})->pack(@pe); + $frame=$mw->Frame(); + + # slave + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "AHB Slave: ")->pack(@pw); + $frame->Entry(-textvariable => \$apb[$apbs]{"slv"})->pack(@pe); + + # slave list + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "APB Slave list: ")->pack(@pw); + $frame->Entry(-textvariable => \$apb[$apbs]{"list"})->pack(@pe); + $frame=$mw->Frame(); + + # exit + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button(-text => "cancel", -command =>sub {WinGlobalExit(); $apbs--;})->pack (@pw); + $frame->Button(-text => "done", -command =>sub {WinGlobalExit(); })->pack (@pe); + + MainLoop; +}; + + +sub WinCheck { + + $mw = MainWindow->new; + + $state='WinGlobal'; + @gen_signal=(); + @ass_signal=(); + @gen_comp=(); + @gen_tbcomp=(); + @gen_uut=(); + $chk=0; + @tmp_chk=(); + + print "\n*******************************************\n*******************************************\n"; + # check for masters: + if ($masters >= 0) {$chk++;for $j ( 0 .. $masters ) {&gen_master($master[$j]);}} else + { + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: No AHB Masters")->pack(@pt); + } + + # check for slaves: + if ($slaves >= 0) {$chk++;} else + { + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: No AHB Slaves")->pack(@pt); + } + + # check for per slaves: + if ($pslaves >= 0) {for $j ( 0 .. $pslaves ) {&gen_pslave($pslave[$j]);}} else { + if ($apbs >= 0) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: No APB Peripherals")->pack(@pt); + } + } + + if ($arbs >= 0) {$chk++;for $j ( 0 .. $arbs ) {&gen_arbiter($arb[$j]);}} else + { + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: No AHB Arbiters")->pack(@pt); + } + + # CONNECTION CHECKS: + # Masters: + for $i (0 .. $masters) {$tmp_chk[$i]=0}; + for $i (0 .. $ahbs) {$tmp_chk[$ahb[$i]{'mst'}]=0}; + + for $i (0 .. $arbs) { + @tmp_lst=split(' ',$arb[$i]{'m_list'}); + foreach (@tmp_lst) { + if ($_>$#tmp_chk) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: MASTER $_ used in ARBITER but not declared!")->pack(@pt); + } else { + $tmp_chk[$_]++; + }; + }; + }; + for $i (0 .. $ahbs) { + $tmp_chk[$ahb[$i]{'mst'}]+=10; + }; + for $i (0 .. $#tmp_chk) { + if ($tmp_chk[$i]==0) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: MASTER $i not connected to any AHB ARBITER!")->pack(@pt); + } elsif ($tmp_chk[$i]>1 and $tmp_chk[$i]<10 and $i<=$masters) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: MASTER $i connected to more than one AHB ARBITER!")->pack(@pt); + } elsif ($tmp_chk[$i]>=10 and $i<=$masters) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: MASTER $i cannot be used as AHB BRIDGE master!")->pack(@pt); + } elsif ($tmp_chk[$i]>=20 and $i>$masters) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: MASTER $i used more than one AHB BRIDGE!")->pack(@pt); + }; + }; + # Slaves: + $#tmp_chk=-1; + for $i (0 .. $slaves) {$tmp_chk[$i]=0}; + for $i (0 .. $arbs) { + @tmp_lst=split(' ',$arb[$i]{'s_list'}); + foreach (@tmp_lst) { + if ($_>$slaves) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: SLAVE $_ still not declared!")->pack(@pt); + } else { + $tmp_chk[$_]++; + }; + }; + }; + for $i (0 .. $slaves) { + if ($tmp_chk[$i]==0) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: SLAVE $i not connected to any AHB ARBITER!")->pack(@pt); + }; + }; + for $i (0 .. $slaves) {$tmp_chk[$i]=0}; + for $i (0 .. $ahbs) { + @tmp_lst=split(' ',$ahb[$i]{'s_list'}); + foreach (@tmp_lst) {$tmp_chk[$_]++;} + }; + for $i (0 .. $apbs) { + if ($i>$slaves) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: SLAVE $_ still not declared!")->pack(@pt); + } else { + $tmp_chk[$apb[$i]{'slv'}]++; + }; + }; + for $i (0 .. $slaves) { + if ($tmp_chk[$i]>1) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: SLAVE $i cannot be connected to more than one BRIDGE!")->pack(@pt); + }; + }; + + # APB Peripherals: + $#tmp_chk=-1; + for $i (0 .. $pslaves) {$tmp_chk[$i]=0}; + for $i (0 .. $apbs) { + @tmp_lst=split(' ',$apb[$i]{'list'}); + foreach (@tmp_lst) { + if ($_>$pslaves) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: APB Peripheral $_ still not declared!")->pack(@pt); + } else { + $tmp_chk[$_]++; + }; + }; + }; + for $i (0 .. $pslaves) { + if ($tmp_chk[$i]==0) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: APB Peripheral $i not assigned to any APB master!")->pack(@pt); + } elsif ($tmp_chk[$i]>1) { + $chk--; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "## ERROR: APB Peripheral $i connected more than once!")->pack(@pt); + }; + }; + +# WARNINGS on missing AHBAHB and AHBAPB BRIDGES + if ($apbs >= 0) { + for $j ( 0 .. $apbs ) {&gen_apb($apb[$j]);} + } else { + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "** WARNING: No APB Bridges")->pack(@pt); + } + + if ($ahbs >= 0) {for $j ( 0 .. $ahbs ) {&gen_bridge($ahb[$j]);}} else + { + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "** WARNING: No AHB/AHB Bridges")->pack(@pt); + } + + + # number '$chk' should indicate 'all checks OK!!' + $done='disabled'; + if ($chk>=3) { + $done='normal'; + $frame=$mw->Frame(); + $frame->pack(@pt); + $frame->Label(-text => "**** CHECK PASSED ****")->pack(@pt); + }; + # exit + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button(-text => "done", -command =>sub {WinGlobalExit(); })->pack (@pt); + + MainLoop; +}; + + +} + + + + + + +# global assignments +sub WinGlobal { + $mw = MainWindow->new; + + $mw->title ("AHB system generator"); + $frame=$mw->Frame(-label=>"Main menu\n"); + $frame->pack(@pt); + $frame->Button( +# -default=>'normal', +# -foreground=>'black',-background=>'grey', +# -state=>'active',-activeforeground=>'blue',-activebackground=>'white', +# -disabledforeground=>'black', + -text=>"add master",-command=>sub {WinGlobalExit(); $state='WinAddMaster';})->pack (@pw); + + $frame->Button( + -text=>"add slave",-command=>sub {WinGlobalExit(); $state='WinAddSlave';})->pack (@pw); + + $frame->Button( + -text=>"add arbiter",-command=>sub {WinGlobalExit(); $state='WinAddArbiter';})->pack (@pw); + + $frame->Button(-state=>'disabled', + -text=>"add per. slave",-command=>sub {WinGlobalExit(); $state='WinAddPslave';})->pack (@pe); + + $frame->Button(-state=>'disabled', + -text=>"add apb bridge",-command=>sub {WinGlobalExit(); $state='WinAddApb';})->pack (@pe); + + $frame->Button(-state=>'disabled', + -text=>"add ahb bridge",-command=>sub {WinGlobalExit(); $state='WinAddAhb';})->pack (@pe); + + $frame=$mw->Frame(-label=>"\n"); + $frame->pack(@pt); + $frame->Button( + -text=>"RESET conf",-command=>sub {WinGlobalExit(); $state='ResetConf';})->pack (@pt); + + $frame->Button( + -text=>"READ conf",-command=>sub {WinGlobalExit(); $state='ReadConf';})->pack (@pt); + + $frame->Button( + -text=>"SAVE conf",-command=>sub {WinGlobalExit(); $state='SaveConf';})->pack (@pt); + + # check and elaborate + $frame->Button( + -text=>"check/generate",-command=>sub {WinGlobalExit(); $state='WinCheck';})->pack (@pt); + + # exit + $frame->Button( + -state=>$done,-activeforeground=>'red',-activebackground=>'blue', + -text=>"done",-command => sub {WinGlobalExit(); $state='quit';})->pack (@pt); + + MainLoop; +}; + + + +# GUI FSM + +sub gui_fsm { +$i=1; +until ($state eq "quit") { + if ($state eq 'WinGlobal') { + &WinGlobal; + } elsif ($state eq 'WinAddMaster') { + &WinAddMaster; + } elsif ($state eq 'WinAddSlave') { + &WinAddSlave; + } elsif ($state eq 'WinAddPslave') { + &WinAddPslave; + } elsif ($state eq 'WinAddArbiter') { + &WinAddArbiter; + } elsif ($state eq 'WinAddAhb') { + &WinAddAhb; + } elsif ($state eq 'WinAddApb') { + &WinAddApb; + } elsif ($state eq 'WinCheck') { + &WinCheck; + } elsif ($state eq 'SaveConf') { + &SaveConf; + } elsif ($state eq 'ReadConf') { + &ReadConf; + } elsif ($state eq 'ResetConf') { + &ResetConf; + } else { + print "Bye!\n"; + }; + }; +}; + + +sub NoWinCheck { + + @gen_signal=(); + @ass_signal=(); + @gen_comp=(); + @gen_tbcomp=(); + @gen_uut=(); + $chk=0; + @tmp_chk=(); + + print "\n*******************************************\n*******************************************\n"; + # check for masters: + if ($masters >= 0) {$chk++;for $j ( 0 .. $masters ) {&gen_master($master[$j]);}} else + { + print "## ERROR: No AHB Masters\n\n"; + } + + # check for slaves: + if ($slaves >= 0) {$chk++;} else + { + print "## ERROR: No AHB Slaves\n\n"; + } + + # check for per slaves: + if ($pslaves >= 0) {for $j ( 0 .. $pslaves ) { + &gen_pslave($pslave[$j]);} + } else { + if ($apbs >= 0) { + $chk--; + print "## ERROR: No APB Peripheralss\n\n"; + } + } + + if ($arbs >= 0) {$chk++;for $j ( 0 .. $arbs ) {&gen_arbiter($arb[$j]);}} else + { + print "## ERROR: No AHB Arbiters\n\n"; + } + + # CONNECTION CHECKS: + # Masters: + for $i (0 .. $masters) {$tmp_chk[$i]=0}; + for $i (0 .. $ahbs) {$tmp_chk[$ahb[$i]{'mst'}]=0}; + + for $i (0 .. $arbs) { + @tmp_lst=split(' ',$arb[$i]{'m_list'}); + foreach (@tmp_lst) { + if ($_>$#tmp_chk) { + $chk--; + print "## ERROR: MASTER $_ used in ARBITER but not declared!\n\n"; + } else { + $tmp_chk[$_]++; + }; + }; + }; + for $i (0 .. $ahbs) { + $tmp_chk[$ahb[$i]{'mst'}]+=10; + }; + for $i (0 .. $#tmp_chk) { + if ($tmp_chk[$i]==0) { + $chk--; + print "## ERROR: MASTER $i not connected to any AHB ARBITER!\n\n"; + } elsif ($tmp_chk[$i]>1 and $tmp_chk[$i]<10 and $i<=$masters) { + $chk--; + print "## ERROR: MASTER $i connected to more than 1 AHB ARBITER!\n\n"; + } elsif ($tmp_chk[$i]>=10 and $i<=$masters) { + $chk--; + print "## ERROR: MASTER $i cannot be used as AHB BRIDGE master!\n\n"; + } elsif ($tmp_chk[$i]>=20 and $i>$masters) { + $chk--; + print "## ERROR: MASTER $i used in 2 or more AHB BRIDGE!\n\n"; + }; + }; + # Slaves: + $#tmp_chk=-1; + for $i (0 .. $slaves) {$tmp_chk[$i]=0}; + for $i (0 .. $arbs) { + @tmp_lst=split(' ',$arb[$i]{'s_list'}); + foreach (@tmp_lst) { + if ($_>$slaves) { + $chk--; + print "## ERROR: SLAVE $_ still not declared!\n\n"; + } else { + $tmp_chk[$_]++; + }; + }; + }; + for $i (0 .. $slaves) { + if ($tmp_chk[$i]==0) { + $chk--; + print "## ERROR: SLAVE $i not connected to any AHB ARBITER!\n\n"; + }; + }; + for $i (0 .. $slaves) {$tmp_chk[$i]=0}; + for $i (0 .. $ahbs) { + @tmp_lst=split(' ',$ahb[$i]{'s_list'}); + foreach (@tmp_lst) {$tmp_chk[$_]++;} + }; + for $i (0 .. $apbs) { + if ($i>$slaves) { + $chk--; + print "## ERROR: SLAVE $_ still not declared!\n\n"; + } else { + $tmp_chk[$apb[$i]{'slv'}]++; + }; + }; + for $i (0 .. $slaves) { + if ($tmp_chk[$i]>1) { + $chk--; + print "## ERROR: SLAVE $i cannot be connected to more than 1 BRIDGE!\n\n"; + }; + }; + + # APB Peripherals: + $#tmp_chk=-1; + for $i (0 .. $pslaves) {$tmp_chk[$i]=0}; + for $i (0 .. $apbs) { + @tmp_lst=split(' ',$apb[$i]{'list'}); + foreach (@tmp_lst) { + if ($_>$pslaves) { + $chk--; + print "## ERROR: APB Peripheral $_ still not declared!\n\n"; + } else { + $tmp_chk[$_]++; + }; + }; + }; + for $i (0 .. $pslaves) { + if ($tmp_chk[$i]==0) { + $chk--; + print "## ERROR: APB Peripheral $i not assigned to any APB master!\n\n"; + } elsif ($tmp_chk[$i]>1) { + $chk--; + print "## ERROR: APB Peripheral $i connected 2 or more times!\n\n"; + }; + }; + +# WARNINGS on missing AHBAHB and AHBAPB BRIDGES + + if ($apbs >= 0) { + for $j ( 0 .. $apbs ) {&gen_apb($apb[$j]);} + } else { + print "** WARNING: No APB Bridges\n\n"; + } + + if ($ahbs >= 0) {for $j ( 0 .. $ahbs ) {&gen_bridge($ahb[$j]);}} else + { + print "** WARNING: No AHB/AHB Bridges\n\n"; + } + + + # number '$chk' should indicate 'all checks OK!!' + if ($chk>=3) { + print "**** CHECK PASSED ****\n\n"; + } else { + print "#### CHECK NOT PASSED!!\n\n" + }; +}; + + + + +print "\nAHB system generator version 1.0\n\n"; + +if (!defined($ENV{DSN})) { + die "Env variable DSN should point to project home\n"; +} + +#the ahb_system.vhd file is made of header, signal part, component +open(file2,">$conffile")|| die "Cannot open output file $conffile\n"; +open(file3,">$matfile")|| die "Cannot open output file $matfile\n"; +open(file4,">$sysfile")|| die "Cannot open output file $sysfile\n"; +open(file5,">$tbfile")|| die "Cannot open output file $tbfile\n"; + + +#USAGE: AHB_SYS_VERIF.pl [-nogui] [filename] +# if no file is specified "$DSN/scripts/ahb_generate.conf" +#open(file1,"<$infile")|| die "Cannot open ahb configuration input file $infile\n"; + +$tmp=shift; +if ($tmp eq "-nogui") { + $infile = shift; + open(file1,"<$infile")|| die "Cannot open ahb configuration input file $infile\n"; + print "Reading configuration in $infile .....\n\n"; + &ReadConf; + print "Generating configuration read by $infile .....\n\n"; + &NoWinCheck; +} else { + if ($tmp ne ) { + $infile=$tmp; + open(file1,"<$infile")|| die "Cannot open ahb configuration input file $infile\n"; + print "Reading configuration in $infile .....\n\n"; + &ReadConf; + } else { + print "No configuration read; using ahb_generate.conf as output file\n" + }; + &gui_fsm; +}; + +&gen_lib(); +&gen_ent(); +&gen_arrays(); + + +##### GENERATION ON CONFIGURATION FILE +print file2 @gen_conf; + + +##### GENERATION ON AHB_MATRIX FILE +print file3 @gen_signal; +print file3 "\nbegin\n\n"; +print file3 @ass_signal; +print file3 @gen_comp; +print file3 "\nend rtl;\n\n"; + + + +##### GENERATION ON SLAVE COMPONENTS (in @gen_tbcomp) +$cnt=0; +foreach $item (@slv_list){ + if ($item == 1) {&gen_slave($slave[$cnt]);} + $cnt++;} +##### + +##### GENERATION ON AHB_SYSTEM FILE +print file4 @gen_signal; +print file4 @gen_ahb_signal; +print file4 " +signal dma_start : start_type_v($masters downto 0); + +signal m_wrap_out : wrap_out_v($masters downto 0); +signal m_wrap_in : wrap_in_v($masters downto 0); +signal s_wrap_out : wrap_out_v($slaves downto 0); +signal s_wrap_in : wrap_in_v($slaves downto 0); + +signal zero : std_logic; +signal no_conf_s : conf_type_t; +constant no_conf_c: conf_type_t:= ('0',\"0000\",\"00000000000000000000000000000000\"); + +begin + +zero <= '0'; +no_conf_s <= no_conf_c; + +"; + +print file4 @ass_signal; +print file4 @gen_comp; +print file4 @gen_tbcomp; +print file4 "\nend rtl;\n\n"; + + +##### GENERATION ON AHB_TB FILE + +print file5 @gen_signal; +print file5 @gen_ahb_signal; +print file5 " +signal conf : conf_type_v($masters downto 0); +signal dma_start : start_type_v($masters downto 0); +signal eot_int : std_logic_vector($masters downto 0); +signal sim_end : std_logic_vector($masters downto 0); + +signal m_wrap_out : wrap_out_v($masters downto 0); +signal m_wrap_in : wrap_in_v($masters downto 0); +signal s_wrap_out : wrap_out_v($slaves downto 0); +signal s_wrap_in : wrap_in_v($slaves downto 0); + +signal hresetn: std_logic; +signal hclk: std_logic; +signal remap: std_logic; + +signal zero : std_logic; +signal no_conf_s : conf_type_t; +constant no_conf_c: conf_type_t:= ('0',\"0000\",\"00000000000000000000000000000000\"); +"; + +for $i (0 .. $masters) { +print file5 "constant stim_$i: uut_params_t:= (bits32,retry,master,'0',single,2,4,hprot_posted,$uut[$i]{\"base_addr\"},1,0,'0');\n" +} + +print file5 " +begin + +zero <= '0'; +no_conf_s <= no_conf_c; + +"; +print file5 @ass_signal; +print file5 @gen_comp; +print file5 @gen_tbcomp; +print file5 @gen_uut; + +print file5 " +clock_pr:process +begin + if hclk='1' then + hclk <= '0'; + wait for 5 ns; + else + hclk <= '1'; + wait for 5 ns; + end if; +end process; + +reset_pr:process +begin + hresetn<= '0'; + wait for 20 ns; + hresetn <= '1'; + wait; +end process; + +remap_pr:process +begin + remap <= '0'; + wait for 2000 ns; + remap <= '1'; + wait; +end process; + +"; + +print file5 "assert (not("; +if ($masters >0) { +$i = $masters; +while ($i > 0) {print file5 "sim_end($i)='1' and ";$i--;} +} +print file5 "sim_end(0)='1')) report \"*** SIMULATION ENDED ***\" severity failure;\n"; +print file5 "\nend rtl;\n\n"; + + +exit; + Index: ahb_system_generator/trunk/scripts/ahb_simulate.do =================================================================== --- ahb_system_generator/trunk/scripts/ahb_simulate.do (nonexistent) +++ ahb_system_generator/trunk/scripts/ahb_simulate.do (revision 3) @@ -0,0 +1,26 @@ +#!/bin/tcsh +if !(${?DSN}) then + echo "Please set DSN variable to design path!" +endif +if !(${?SIMULATOR}) then + echo "Please set SIMULATOR variable to 'vcom' or 'ncvhdl'!" +endif +$SIMULATOR $DSN/src/ahb_package.vhd +$SIMULATOR $DSN/src/ahb_configure.vhd +$SIMULATOR $DSN/src/ahb_funct.vhd +$SIMULATOR $DSN/src/fifo.vhd +$SIMULATOR $DSN/src/slv_mem.vhd +$SIMULATOR $DSN/src/ahb_slave_wait.vhd +$SIMULATOR $DSN/src/mst_wrap.vhd +$SIMULATOR $DSN/src/ahb_master.vhd +$SIMULATOR $DSN/src/ahb_arbiter.vhd +$SIMULATOR $DSN/src/uut_stimulator.vhd +$SIMULATOR $DSN/src/ahb_components.vhd +$SIMULATOR $DSN/src/ahb_matrix.vhd +$SIMULATOR $DSN/src/ahb_system.vhd +$SIMULATOR $DSN/src/ahb_tb.vhd +if ($SIMULATOR == ncvhdl) then + ncelab work.ahb_tb:rtl -access r +else + vsim work.ahb_tb(rtl) -t 100 ps +endif Index: ahb_system_generator/trunk/src/ahb_components.vhd =================================================================== --- ahb_system_generator/trunk/src/ahb_components.vhd (nonexistent) +++ ahb_system_generator/trunk/src/ahb_components.vhd (revision 3) @@ -0,0 +1,148 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_arith.all; + +use work.ahb_package.all; +use work.ahb_funct.all; +use work.ahb_configure.all; + +package ahb_components is + +component fifo +generic ( + fifohempty_level: in integer:= 1; + fifohfull_level: in integer:= 3; + fifo_length: in integer:= 4); +port ( + hresetn: in std_logic; + clk: in std_logic; + fifo_reset: in std_logic; + fifo_write: in std_logic; + fifo_read: in std_logic; + fifo_count: out std_logic_vector(nb_bits(fifo_length)-1 downto 0); + fifo_full: out std_logic; + fifo_hfull: out std_logic; + fifo_empty: out std_logic; + fifo_hempty: out std_logic; + fifo_datain: in std_logic_vector(31 downto 0); + fifo_dataout: out std_logic_vector(31 downto 0) + ); +end component; + +component ahb_master +generic ( + fifohempty_level: in integer; + fifohfull_level: in integer; + fifo_length: in integer); +port ( + hresetn: in std_logic; + hclk: in std_logic; + mst_in: in mst_in_t; + mst_out: out mst_out_t; + dma_start: in start_type_t; + m_wrap_out: out wrap_out_t; + m_wrap_in: in wrap_in_t; + slv_running: in std_logic; + mst_running: out std_logic; + eot_int: out std_logic); +end component; + +component ahb_arbiter + generic( + num_arb: in integer; + num_arb_msts: in integer range 1 to 15; + def_arb_mst: in integer range 0 to 15; + num_slvs: in integer range 1 to 15; + alg_number: in integer range 0 to 5); + port( + hresetn: in std_logic; + hclk: in std_logic; + remap: in std_logic; + mst_in_v: in mst_out_v_t(num_arb_msts-1 downto 0); + mst_out_v: out mst_in_v_t(num_arb_msts-1 downto 0); + slv_out_v: out slv_in_v_t(num_slvs-1 downto 0); + slv_in_v: in slv_out_v_t(num_slvs-1 downto 0)); +end component; + +component ahb_slave_wait + generic ( + num_slv: in integer range 0 to 15:= 1; + fifohempty_level: in integer:= 2; + fifohfull_level: in integer:= 5; + fifo_length: in integer:= 8); + port( + hresetn: in std_logic; + hclk: in std_logic; + remap: in std_logic; + slv_in: in slv_in_t; + slv_out: out slv_out_t; + mst_running: in std_logic; + prior_in: in std_logic; + slv_running: out std_logic; + slv_err: out std_logic; + s_wrap_out: out wrap_out_t; + s_wrap_in: in wrap_in_t); +end component; + +component mst_wrap +generic ( +--synopsys translate_off +dump_file: in string:= "mst_wrap.log"; +dump_type: in integer; +--synopsys translate_on +ahb_max_addr: in integer:= 4; +m_const_lat_write: in integer; +m_const_lat_read: in integer; +m_write_burst: in integer; +m_read_burst: in integer); +port ( + hresetn: in std_logic; + clk: in std_logic; + conf: in conf_type_t; + dma_start: out start_type_t; + m_wrap_in: in wrap_out_t; + m_wrap_out: out wrap_in_t); +end component; + +component slv_mem +generic ( +--synopsys translate_off +dump_file: in string:= "slv_wrap.log"; +dump_type: in integer; +--synopsys translate_on +ahb_max_addr: in integer:= 8; +s_const_lat_write: in integer; +s_const_lat_read: in integer; +s_write_burst: in integer; +s_read_burst: in integer); +port ( + hresetn: in std_logic; + clk: in std_logic; + conf: in conf_type_t; + dma_start: out start_type_t; + s_wrap_in: in wrap_out_t; + s_wrap_out: out wrap_in_t + ); +end component; + +component uut_stimulator +generic ( +stim_type: in uut_params_t; +enable: in integer; +eot_enable: in integer); +port( + hclk : in std_logic; + hresetn : in std_logic; + amba_error: in std_logic; + eot_int: in std_logic; + conf: out conf_type_t; + sim_end: out std_logic); +end component; + +end; + +package body ahb_components is +end; + + + Index: ahb_system_generator/trunk/src/uut_stimulator.vhd =================================================================== --- ahb_system_generator/trunk/src/uut_stimulator.vhd (nonexistent) +++ ahb_system_generator/trunk/src/uut_stimulator.vhd (revision 3) @@ -0,0 +1,154 @@ +use STD.textio.all;--added for time and strings + +library ieee; +use ieee.std_logic_arith.all; +use ieee.std_logic_misc.all; +use ieee.std_logic_unsigned.all; +use ieee.std_logic_1164.all; +use IEEE.std_logic_textio.all;--added for time and strings + +-- Add your library and packages declaration here ... +use work.ahb_package.all; + +entity uut_stimulator is +generic ( +stim_type: in uut_params_t:= (bits32,retry,master,'0',single,2,4,hprot_posted,2048,1,0,'0'); +enable: in integer:= 0; +eot_enable: in integer:= 0); +port( + hclk : in std_logic; + hresetn : in std_logic; + amba_error: in std_logic; + eot_int: in std_logic; + conf: out conf_type_t; + sim_end: out std_logic +); +end uut_stimulator; + +--}} End of automatically maintained section + +architecture rtl of uut_stimulator is + +signal cycle : std_logic; +signal counter: integer range 0 to 127; + +begin + +process +begin + if hresetn = '0' then + counter <= 1; + else + if(counter > 15) then + assert false report "* Simulator Exit.." severity warning; + sim_end <= '1'; + wait; + else + sim_end <= '0'; + counter <= counter+1; + end if; + end if; + + if (eot_enable/=1) then + wait for 4000 ns; + else + wait until (eot_int='1' or amba_error='1');--write + wait until (eot_int='1' or amba_error='1');--read + end if; +end process; + +cycle_pr:process +begin + if cycle/='1' then + cycle <= '1'; + if (eot_enable/=1) then + wait for 2000 ns; + else + wait until (eot_int='1' or amba_error='1'); + end if; + else + cycle <= '0'; + if (eot_enable/=1) then + wait for 2000 ns; + else + wait until (eot_int='1' or amba_error='1'); + end if; + end if; +end process; + +process +variable hburst: std_logic_vector(2 downto 0); +begin +if (counter<=16) then + + conf.write <= '0'; + wait for 30 ns; + conf.write <= '1'; + + conf.addr <= dma_type_addr; + + case stim_type.hburst_cycle is + when '1' => + hburst := stim_type.hburst_tb; + when others => + hburst := conv_std_logic_vector(counter,3); + end case; + conf.wdata <= "000000000000000000"& + stim_type.split_tb&stim_type.prior_tb&stim_type.hsize_tb&hburst&stim_type.hprot_tb&cycle&stim_type.locked_request; + wait for 10 ns; + + conf.addr <= dma_extadd_addr; + --conf.wdata(31 downto 12)<=stim_type.high_addr_tb; + case stim_type.ext_addr_incr_tb is + when 1 =>--fixed ext addr + conf.wdata(31 downto 0)<= conv_std_logic_vector(stim_type.base_tb ,32); + when 2 =>--increasing by 4, page fault if base near end of slave address space + conf.wdata(31 downto 0)<= conv_std_logic_vector(stim_type.base_tb+(counter-1)*4 ,32); + when others =>--growing by incr_tb-4 (0,1,2,3,4,5, ETC.) + conf.wdata(31 downto 0)<= conv_std_logic_vector(stim_type.base_tb+(counter-1)*(stim_type.ext_addr_incr_tb-4) ,32); + end case; + wait for 10 ns;--external address + + conf.addr <= dma_intadd_addr; + case stim_type.int_addr_incr_tb is + when 1 =>--fixed int addr + conf.wdata(31 downto 0)<= conv_std_logic_vector(stim_type.int_base_tb,32); + when 2 =>--increasing by 4, page fault if base near end of slave address space + conf.wdata(31 downto 0)<= conv_std_logic_vector(stim_type.int_base_tb+(counter-1)*4 ,32); + when others =>--growing by incr_tb-4 (0,1,2,3,4,5, ETC.) + conf.wdata(31 downto 0)<= conv_std_logic_vector(stim_type.int_base_tb+(counter-1)*(stim_type.int_addr_incr_tb-4) ,32); + end case; + wait for 10 ns;--internal address + + conf.addr <= dma_intmod_addr; + conf.wdata <= conv_std_logic_vector(stim_type.intmod_tb ,32); + wait for 10 ns;--modifier + +if enable=1 then + conf.addr <= dma_count_addr; + conf.wdata <= conv_std_logic_vector(counter,32); + wait for 10 ns;--dma count +else + wait for 10 ns;--dma count +end if; + + conf.write <= '0'; + conf.addr <= "0000"; + conf.wdata <= (others => '-'); + + if (eot_enable/=1) then + wait until cycle'event; + else + wait until (eot_int='1' or amba_error='1'); + end if; +else + wait; +end if; +--if counter=16 then wait; end if; + +end process; + + +assert (amba_error/='1') report "###ERROR in AMBA operation!!!" severity error; + +end rtl; Index: ahb_system_generator/trunk/src/ahb_arbiter.vhd =================================================================== --- ahb_system_generator/trunk/src/ahb_arbiter.vhd (nonexistent) +++ ahb_system_generator/trunk/src/ahb_arbiter.vhd (revision 3) @@ -0,0 +1,447 @@ + +--******************************************************************* +--** **** +--** AHB system generator **** +--** **** +--** Author: Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--******************************************************************* +--** **** +--** Copyright (C) 2004 Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--** This source file may be used and distributed without **** +--** restriction provided that this copyright statement is not **** +--** removed from the file and that any derivative work contains **** +--** the original copyright notice and the associated disclaimer.**** +--** **** +--** THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY **** +--** EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED **** +--** TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS **** +--** FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR **** +--** OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, **** +--** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES **** +--** (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE **** +--** GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR **** +--** BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF **** +--** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT **** +--** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT **** +--** OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE **** +--** POSSIBILITY OF SUCH DAMAGE. **** +--** **** +--******************************************************************* +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_arith.all; +use ieee.std_logic_unsigned.all; + +use work.ahb_funct.all; +use work.ahb_package.all; +use work.ahb_configure.all; +--use work.ahb_matrix.all; + +entity ahb_arbiter is + generic( + num_arb: in integer:= 2; + num_arb_msts: in integer range 1 to 15:= 4; + def_arb_mst: in integer range 0 to 15:= 2; + num_slvs: in integer range 1 to 15:= 3; + alg_number: in integer range 0 to 5:= 2); + port( + hresetn: in std_logic; + hclk: in std_logic; + remap: in std_logic; + mst_in_v: in mst_out_v_t(num_arb_msts-1 downto 0); + mst_out_v: out mst_in_v_t(num_arb_msts-1 downto 0); + slv_out_v: out slv_in_v_t(num_slvs-1 downto 0); + slv_in_v: in slv_out_v_t(num_slvs-1 downto 0)); +end; + + +architecture rtl of ahb_arbiter is + +--******************************************************************* +--******************** SIGNAL DECLARATION *************************** +--******************************************************************* + +signal s_grant_master, grant_master: integer range 0 to 15; +signal s_master_sel, master_sel: std_logic_vector(3 downto 0); +signal s_r_master_sel, r_master_sel: std_logic_vector(3 downto 0); +signal r_master_busy: std_logic_vector(1 downto 0); + +signal turn, s_turn: integer range 0 to num_arb_msts-1; +signal random: integer range 0 to 2**(nb_bits(num_arb_msts)); +signal seed, s_seed: std_logic_vector(9 downto 0); + +type vecran is array (2**(nb_bits(num_arb_msts)) downto 0) of integer; +signal vect_ran: vecran; +signal vect_ran_round: vecran; + + +signal haddr_page: std_logic_vector(31 downto 0); +signal htrans_reg: std_logic_vector(1 downto 0);--"00"|"01"|"10" +signal hsel: std_logic_vector(num_slvs-1 downto 0); + + +signal s_dec_hready: std_logic; +signal req_ored: std_logic; +signal hbusreq_msk: std_logic_vector(num_arb_msts-1 downto 0); + +signal split_reg: std_logic_vector(num_arb_msts-1 downto 0); + +signal r_slv_in_v: slv_in_v_t(num_slvs-1 downto 0); +signal mst_in_sel: slv_in_t; +signal slv_in_sel: mst_in_t; + +--DEAFULT SLAVE BEHAVIOUR + +signal r_def_slave_hsel, def_slave_hsel: std_logic; +signal def_slave_hready: std_logic; + +signal addr_arb_matrix: addr_matrix_t(0 downto 0); + +--******************************************************************* +--***************** END OF SIGNAL DECLARATION ************************ +--******************************************************************* + +begin + +addr_arb_matrix(0)(num_slvs-1 downto 0) <= arb_matrix(num_arb)(num_slvs-1 downto 0) when (remap='0') else rarb_matrix(num_arb)(num_slvs-1 downto 0); + +req_ored_pr:process(hbusreq_msk) +variable v_req_ored: std_logic; +begin + v_req_ored := '0'; + for i in 0 to num_arb_msts-1 loop + v_req_ored := v_req_ored or hbusreq_msk(i); + end loop; + req_ored <= v_req_ored; +end process; + +bus_req_mask_pr:process(split_reg, grant_master, mst_in_v) +begin + for i in 0 to num_arb_msts-1 loop + if (mst_in_v(i).htrans=busy or split_reg(i)='1' or (grant_master/=num_arb_msts and grant_master/=i and mst_in_v(grant_master).hlock='1')) then + hbusreq_msk(i) <= '0'; + else + hbusreq_msk(i) <= mst_in_v(i).hbusreq; + end if; + end loop; +end process; + + +--******************************************************** +-- synchronization processes (flip flops) +--******************************************************** +s_master_sel <= conv_std_logic_vector(s_grant_master, 4) when (s_dec_hready='1') else master_sel; +s_r_master_sel <= master_sel when (s_dec_hready='1' and htrans_reg/=busy) else r_master_sel; + +master_pr:process(hresetn, hclk) +begin + if hresetn='0' then + grant_master <= def_arb_mst; + master_sel <= conv_std_logic_vector(def_arb_mst, 4); + r_master_sel <= conv_std_logic_vector(def_arb_mst, 4); + turn <= 0; + htrans_reg <= idle; + elsif hclk'event and hclk='1' then + grant_master <= s_grant_master after 1 ns; + master_sel <= s_master_sel after 1 ns; + r_master_sel <= s_r_master_sel after 1 ns; + turn <= s_turn after 1 ns; + if conv_integer(master_sel) /= num_arb_msts then + htrans_reg <= mst_in_sel.htrans after 1 ns; + else + htrans_reg <= idle; + end if; + end if; +end process; + +update_pr:process( +req_ored, +hbusreq_msk, +grant_master, +mst_in_v, +htrans_reg, +mst_in_sel, +slv_in_sel, +split_reg, +turn, +random) +variable t_turn, t_grant_master: integer; +begin + t_turn := turn; + t_grant_master := grant_master; + --nohready=> grant no change + --hready&busy(real master)=> grant no change + --hready&nobusy&req => arbitration + --hready&nobusy&noreq&default master not splitted => default master + --hready&nobusy&noreq&default master splitted => dummy master + if (slv_in_sel.hready='1') then + if ((grant_master/=num_arb_msts and mst_in_v(grant_master).htrans/=busy and htrans_reg/=busy) or (grant_master=num_arb_msts)) then + if (req_ored='1') then + case alg_number is + when 0 => --fixed + fixed_priority(t_turn, t_grant_master, hbusreq_msk, turn); + when 1 => --round robin + round_robin(def_arb_mst, t_turn, t_grant_master, hbusreq_msk, turn); + when 2 => --random + random_priority(def_arb_mst, t_turn, t_grant_master, random, hbusreq_msk, turn); + when 3 => --fair1 + if (grant_master/=num_arb_msts and hbusreq_msk(grant_master)='0') or (grant_master=num_arb_msts) then + fixed_priority(t_turn, t_grant_master, hbusreq_msk, turn); + end if; + when 4 => --fair2 + if (grant_master/=num_arb_msts and hbusreq_msk(grant_master)='0') or (grant_master=num_arb_msts) then + round_robin(def_arb_mst, t_turn, t_grant_master, hbusreq_msk, turn); + end if; + when 5 => --fair3 + if (grant_master/=num_arb_msts and hbusreq_msk(grant_master)='0') or (grant_master=num_arb_msts) then + random_priority(def_arb_mst, t_turn, t_grant_master, random, hbusreq_msk, turn); + end if; + when others => --NOT IMPLEMENTED + assert FALSE report "### NOT IMPLEMENTED!" severity FAILURE; + end case; + elsif (split_reg(def_arb_mst)='0') then--ready+no_busy+no_req=> default if not splitted!! + t_grant_master := def_arb_mst; + t_turn := def_arb_mst; + else--ready+no_busy+no_req+def_master splitted => dummy_master!! + t_grant_master := num_arb_msts; + end if; + --else (busy) then SAME MASTER + end if; + --else (no_ready) then SAME MASTER + end if; + s_grant_master <= t_grant_master; + s_turn <= t_turn; +end process; + +s_seed_pr:process(seed) +begin + for i in 9 downto 1 loop + s_seed(i) <= seed(i-1); + end loop; + s_seed(0) <= not(seed(9) xor seed(6)); +end process; + +seed_pr:process(hresetn, hclk) +variable v_random: integer range 0 to 2**(nb_bits(num_arb_msts)); +begin + if hresetn='0' then + seed <= (others => '0');--"1101010001"; + random <= 0; + --synopsys translate_off + for i in 0 to 2**(nb_bits(num_arb_msts)) loop + vect_ran(i) <= 0; + vect_ran_round(i) <= 0; + end loop; + --synopsys translate_on + elsif hclk'event and hclk='1' then + seed <= s_seed after 1 ns; + v_random := conv_integer(seed(nb_bits(num_arb_msts)+3 downto 4)); + if v_random < num_arb_msts then + random <= v_random after 1 ns; + else + random <= turn after 1 ns;--(v_random - num_arb_msts); + end if; + --synopsys translate_off + vect_ran(v_random) <= vect_ran(v_random) + 1; + vect_ran_round(random) <= vect_ran_round(random) + 1; + --synopsys translate_on + end if; +end process; + + + +--synopsys translate_off + assert not (hclk'event and hclk='1' and master_sel=num_arb_msts) report "DUMMY MASTER selection!!!" severity WARNING; + assert not (hclk'event and hclk='1' and master_sel=def_arb_mst) report "DEFAULT MASTER selection!!!" severity WARNING; + assert not (hclk'event and hclk='1' and (master_sel>num_arb_msts or r_master_sel>num_arb_msts)) report "####ERROR in MASTER selection!!!" severity FAILURE; +--synopsys translate_on + + +--********************************************************* +-- MASTER MUXES +--********************************************************* + +add_pr:process(master_sel, r_master_sel, mst_in_v) +variable def_addr: std_logic_vector(31 downto 0); +begin + + haddr_page(31 downto 10) <= mst_in_v(def_arb_mst).haddr(31 downto 10); + + mst_in_sel.hwdata <= mst_in_v(def_arb_mst).hwdata; + mst_in_sel.haddr <= mst_in_v(def_arb_mst).haddr; + mst_in_sel.hwrite <= mst_in_v(def_arb_mst).hwrite; + mst_in_sel.hsize <= mst_in_v(def_arb_mst).hsize; + mst_in_sel.hburst <= mst_in_v(def_arb_mst).hburst; + mst_in_sel.hprot <= mst_in_v(def_arb_mst).hprot; + mst_in_sel.htrans <= mst_in_v(def_arb_mst).htrans; + for i in 0 to num_arb_msts-1 loop + if i=conv_integer(r_master_sel) then + mst_in_sel.hwdata <= mst_in_v(i).hwdata; + end if; + if i=conv_integer(master_sel) then + haddr_page(31 downto 10) <= mst_in_v(i).haddr(31 downto 10); + mst_in_sel.haddr <= mst_in_v(i).haddr; + mst_in_sel.hwrite <= mst_in_v(i).hwrite; + mst_in_sel.hsize <= mst_in_v(i).hsize; + mst_in_sel.hburst <= mst_in_v(i).hburst; + mst_in_sel.hprot <= mst_in_v(i).hprot; + mst_in_sel.htrans <= mst_in_v(i).htrans; + end if; + end loop; + if master_sel=num_arb_msts then + mst_in_sel.htrans <= idle; + end if; +end process; + +process(slv_in_sel, s_grant_master)--N.B.: Request=>Grant comb. path! +begin + for i in 0 to num_arb_msts-1 loop + mst_out_v(i).hready <= slv_in_sel.hready; + mst_out_v(i).hresp <= slv_in_sel.hresp; + mst_out_v(i).hrdata <= slv_in_sel.hrdata; + if (s_grant_master=i) then + mst_out_v(i).hgrant <= '1'; + else + mst_out_v(i).hgrant <= '0'; + end if; + end loop; +end process; + +--********************************************************* +-- SLAVE MUXES +--********************************************************* + +process(hresetn, hclk) +variable v_hready: std_logic; +begin + if hresetn='0' then + for i in num_slvs-1 downto 0 loop + r_slv_in_v(i).hsel <= '0'; + end loop; + elsif hclk='1' and hclk'event then + if s_dec_hready='1' then + r_def_slave_hsel <= def_slave_hsel; + for i in num_slvs-1 downto 0 loop + r_slv_in_v(i).hsel <= hsel(i) after 1 ns; + end loop; + end if; + end if; +end process; + +process(r_slv_in_v, slv_in_v, def_slave_hready) +begin + s_dec_hready <= def_slave_hready; + for i in num_slvs-1 downto 0 loop + if(r_slv_in_v(i).hsel='1') then + s_dec_hready <= slv_in_v(i).hready; + end if; + end loop; +-- hready_t <= slv_in_v(num_slvs).hready;--ready .... + slv_in_sel.hready <= def_slave_hready; + slv_in_sel.hrdata <= (others => '-');--for LOW POWER!!! + slv_in_sel.hresp <= error_resp;--.... and ERROR .... + for i in num_slvs-1 downto 0 loop + if r_slv_in_v(i).hsel='1' then +-- hready_t <= slv_in_v(i).hready; + slv_in_sel.hready <= slv_in_v(i).hready; + slv_in_sel.hresp <= slv_in_v(i).hresp; + slv_in_sel.hrdata <= slv_in_v(i).hrdata; + end if; + end loop; +end process; + + +--********************************************************* +-- SPLIT handling +--********************************************************* + +process(hresetn, hclk) +variable v_split_reg: std_logic_vector(num_arb_msts-1 downto 0); +begin + if hresetn='0' then + split_reg <= (others => '0'); + elsif hclk'event and hclk='1' then + v_split_reg := split_reg; + for j in num_slvs-1 downto 0 loop + for i in num_arb_msts-1 downto 0 loop + v_split_reg(i) := v_split_reg(i) and not slv_in_v(j).hsplit(i); + end loop; + if (r_slv_in_v(j).hsel='1') then + if (slv_in_v(j).hready='1' and slv_in_v(j).hresp=split_resp and master_sel/=num_arb_msts) then + v_split_reg(conv_integer(master_sel)) := '1'; + end if; + end if; + end loop; + split_reg <= v_split_reg after 1 ns; + end if; +end process; + +--********************************************************* +-- AHB DECODER +--********************************************************* +-- min 1KB of address space for each slave: +process(haddr_page, master_sel, mst_in_v, mst_in_sel, s_dec_hready, addr_arb_matrix) + variable addr_low_std : std_logic_vector(31 downto 0); + variable addr_high_std : std_logic_vector(31 downto 0); + variable v_hmastlock: std_logic; +begin + v_hmastlock := '0'; + for i in num_arb_msts-1 downto 0 loop + if (v_hmastlock='0' and master_sel=conv_std_logic_Vector(i,4) and mst_in_v(i).hlock='1') then + v_hmastlock := '1'; + end if; + end loop; + def_slave_hsel <= '1'; --default slave selected + for i in num_slvs-1 downto 0 loop + slv_out_v(i).hmastlock <= v_hmastlock; + slv_out_v(i).haddr <= mst_in_sel.haddr; + slv_out_v(i).hmaster <= master_sel; + slv_out_v(i).hready <= s_dec_hready; + slv_out_v(i).hwrite <= mst_in_sel.hwrite; + slv_out_v(i).hwdata <= mst_in_sel.hwdata; + slv_out_v(i).hsize <= mst_in_sel.hsize; + slv_out_v(i).hburst <= mst_in_sel.hburst; + slv_out_v(i).hprot <= mst_in_sel.hprot; + slv_out_v(i).htrans <= mst_in_sel.htrans; + addr_low_std := conv_std_logic_vector(addr_arb_matrix(0)(i).low, 32); + addr_high_std := conv_std_logic_vector(addr_arb_matrix(0)(i).high, 32); + if (haddr_page(31 downto 10) >= addr_low_std(31 downto 10) and (haddr_page(31 downto 10) <= addr_high_std(31 downto 10))) then + hsel(i) <= '1'; + def_slave_hsel <= '0'; + slv_out_v(i).hsel <= '1'; + else + hsel(i) <= '0'; + slv_out_v(i).hsel <= '0'; + end if; + end loop; +end process; + + +--DEFAULT SLAVE BEHAVIOUR + +process(hresetn, hclk) +begin + if hresetn='0' then + def_slave_hready <= '1'; + elsif hclk'event and hclk='1' then + if (def_slave_hsel='1' and s_dec_hready='1' and mst_in_sel.htrans/=idle) then + def_slave_hready <= '0' after 1 ns; + else + def_slave_hready <= '1' after 1 ns; + end if; + end if; +end process; + + + +--synopsys translate_off + assert not(hclk'event and hclk='1' and r_def_slave_hsel='1') report "####ERROR: NO SLAVE SELECTED!!!" severity error; +--synopsys translate_on + +end rtl; + + Index: ahb_system_generator/trunk/src/slv_mem.vhd =================================================================== --- ahb_system_generator/trunk/src/slv_mem.vhd (nonexistent) +++ ahb_system_generator/trunk/src/slv_mem.vhd (revision 3) @@ -0,0 +1,229 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_unsigned.all; +use ieee.std_logic_misc.all; +use ieee.std_logic_arith.all; + +use std.textio.all; + +use work.ahb_package.all; + +entity slv_mem is +generic ( +--synopsys translate_off +dump_file: in string:= "slv_wrap.log"; +dump_type: in integer:= dump_no; +--synopsys translate_on +ahb_max_addr: in integer:= 8; +--*************************************************************** +--parameters for slave access +--*************************************************************** +s_const_lat_write: in integer:= 1;--1 cycle to save data +s_const_lat_read: in integer:= 2;--2 cycles to retreave data +s_write_burst: in integer := no_burst_support;--slave doesn't accept bursts in write!!! +s_read_burst: in integer:= no_burst_support--slave doesn't accept bursts in read!!! + ); +port ( + hresetn: in std_logic; + clk: in std_logic; + conf: in conf_type_t; + dma_start: out start_type_t; + s_wrap_in: in wrap_out_t; + s_wrap_out: out wrap_in_t); +end slv_mem; + +architecture rtl of slv_mem is + +--synopsys translate_off +--*************************************************************** +--**** DUMP OF MEMORY ******************************************* +--*************************************************************** +file file_descriptor : TEXT open write_mode is dump_file; +constant msg1: string(1 to 4):= "MEM "; +constant msg2: string(1 to 4):= "REG "; +constant msg3: string(1 to 5):= "DATA "; + +procedure Write_Message(msg1:string; addr:in integer; msg2:string; value:in integer) is +variable STR : line; + begin + write(STR,now); + write(STR,STRING'(" ")); + write (STR, msg1); + write (STR, addr); + write(STR,STRING'(" ")); + write (STR, msg2); + write (STR, value); + writeLine(file_descriptor, STR); + writeLine(OUTPUT, STR); +end Write_Message; +--*************************************************************** +--*************************************************************** +--synopsys translate_on + +--*************************************************************** +--configuration registers +--*************************************************************** +signal start_hprot: std_logic_vector(3 downto 0); +signal start_hsize: std_logic_Vector(2 downto 0); +signal start_hburst: std_logic_Vector(2 downto 0); +signal start_hwrite: std_logic; +signal start_hlocked: std_logic; +signal start_prior: std_logic; +signal hsize_reg: std_logic_Vector(2 downto 0); +signal priority_reg: std_logic; +signal hburst_reg: std_logic_Vector(2 downto 0); +signal hprot_reg: std_logic_Vector(3 downto 0); +signal hlock_reg: std_logic; +signal trx_dir_reg: std_logic; +signal extaddr: std_logic_Vector(31 downto 0); +signal intaddr: std_logic_Vector(15 downto 0); +signal intmod: std_logic_Vector(15 downto 0); +signal count_reg: std_logic_Vector(15 downto 0); +signal dma_go: std_logic; +--*************************************************************** +--*************************************************************** + +type vect_32 is array (2**ahb_max_addr-1 downto 0) of std_logic_vector (31 downto 0); +signal mem : vect_32; + + + +signal s_lat_write_ok, s_lat_read_ok: std_logic; +signal s_lat_write: integer range 0 to s_const_lat_write; +signal s_lat_read: integer range 0 to s_const_lat_read; +--*************************************************************** +--*************************************************************** + + +begin + + +--*************************************************************** +--*************************************************************** +--** slave part: could be a memory, fifo or register bank ******* +--** here it's only a configuration register bank *************** +--*************************************************************** + +process(clk, hresetn) +begin + if hresetn='0' then + for i in 0 to 2**ahb_max_addr-1 loop + mem(i) <= conv_std_logic_vector(i, 32); + end loop;--i + elsif clk'event and clk='1' then + if (s_wrap_in.take='1' and s_lat_write_ok='1') then + mem(conv_integer(s_wrap_in.addr(ahb_max_addr-1+2 downto 2))) <= s_wrap_in.wdata after 1 ns; +--synopsys translate_off +if dump_type/=dump_no then Write_Message(msg1, conv_integer(s_wrap_in.addr(ahb_max_addr-1+2 downto 2)), msg3, conv_integer(s_wrap_in.wdata)); end if; +--synopsys translate_on + end if; + end if; +end process; + +s_wrap_out.rdata <= mem(conv_integer(s_wrap_in.addr(ahb_max_addr-1+2 downto 2))) when (s_wrap_in.ask='1' and s_lat_read_ok='1') else (others => '-'); + + +process(clk, hresetn) +begin + if hresetn='0' then + s_lat_write <= s_const_lat_write; + elsif clk'event and clk='1' then + if (s_wrap_in.take='1') then + if (s_lat_write_ok='0') then + s_lat_write <= s_lat_write-1 after 1 ns; + elsif (s_write_burst=1) then--accepts bursts ..... + s_lat_write <= 0 after 1 ns; + else + s_lat_write <= s_const_lat_write after 1 ns; + end if; + else + s_lat_write <= s_const_lat_write after 1 ns; + end if; + end if; +end process; + +s_lat_write_ok <= '1' when (s_lat_write=0) else '0'; +s_wrap_out.take_ok <= '1' when (s_wrap_in.take='1' and s_lat_write_ok='1') else '0'; + +process(clk, hresetn) +begin + if hresetn='0' then + s_lat_read <= s_const_lat_read; + elsif clk'event and clk='1' then + if (s_wrap_in.ask='1') then + if (s_lat_read_ok='0') then + s_lat_read <= s_lat_read-1 after 1 ns; + elsif (s_read_burst=1) then--accepts bursts ..... + s_lat_read <= 0 after 1 ns; + else + s_lat_read <= s_const_lat_read after 1 ns; + end if; + else + s_lat_read <= s_const_lat_read after 1 ns; + end if; + end if; +end process; + +s_lat_read_ok <= '1' when (s_lat_read=0) else '0'; +s_wrap_out.ask_ok <= '1' when (s_wrap_in.ask='1' and s_lat_read_ok='1') else '0'; + +--************************************************************************** +-- configuration registers write +--************************************************************************** + +conf_reg_pr:process(hresetn, clk) +variable addr: std_logic_Vector(3 downto 0); +begin +if hresetn='0' then + hsize_reg <= bits32; + priority_reg <= slave; + hburst_reg <= incr; + hprot_reg <= "0011"; + trx_dir_reg <= '0'; + hlock_reg <= locked; + extaddr <= zeroes; + intaddr <= zeroes(15 downto 0); + intmod <= conv_std_logic_vector(4, intmod'length);--mod=+4(+1 word32) + count_reg <= zeroes(15 downto 0); + dma_go <= '0'; +elsif clk'event and clk='1' then + if (conf.write='1') then + case conf.addr is + when dma_extadd_addr => + extaddr <= conf.wdata; + when dma_intadd_addr => + intaddr <= conf.wdata(15 downto 0); + when dma_intmod_addr => + intmod <= conf.wdata(15 downto 0); + when dma_type_addr => + priority_reg <= conf.wdata(12); + hsize_reg <= conf.wdata(11 downto 9); + hburst_reg <= conf.wdata(8 downto 6); + hprot_reg <= conf.wdata(5 downto 2); + trx_dir_reg <= conf.wdata(1); + hlock_reg <= conf.wdata(0); + when dma_count_addr => + count_reg <= conf.wdata(15 downto 0); + when others => null; + end case; + end if; + if (conf.write='1' and conf.addr=dma_count_addr) then + dma_go <= '1'; + else + dma_go <= '0'; + end if; +end if; +end process; +--************************************************************************** +--************************************************************************** + +--************************************************************************** +--************************************************************************** + dma_start.extaddr <= extaddr; + dma_start.intaddr <= intaddr; + dma_start.intmod <= intmod; + dma_start.hparams <= "000"&priority_reg&hsize_reg&hburst_reg&hprot_reg&trx_dir_reg&hlock_reg; + dma_start.count <= count_reg; + dma_start.start <= dma_go; + +end rtl; Index: ahb_system_generator/trunk/src/fifo.vhd =================================================================== --- ahb_system_generator/trunk/src/fifo.vhd (nonexistent) +++ ahb_system_generator/trunk/src/fifo.vhd (revision 3) @@ -0,0 +1,85 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_unsigned.all; +use ieee.std_logic_misc.all; +use ieee.std_logic_arith.all; + +use work.ahb_funct.all; +use work.ahb_package.all; + +entity fifo is +generic ( + fifohempty_level: in integer:= 1; + fifohfull_level: in integer:= 3; + fifo_length: in integer:= 4); +port ( + hresetn: in std_logic; + clk: in std_logic; + fifo_reset: in std_logic; + fifo_write: in std_logic; + fifo_read: in std_logic; + fifo_count: out std_logic_vector(nb_bits(fifo_length)-1 downto 0); + fifo_full: out std_logic; + fifo_hfull: out std_logic; + fifo_empty: out std_logic; + fifo_hempty: out std_logic; + fifo_datain: in std_logic_vector(31 downto 0); + fifo_dataout: out std_logic_vector(31 downto 0) + ); +end fifo; + +architecture rtl of fifo is + + + +signal fifo_full_s, fifo_empty_s: std_logic; +signal fifo_count_s : std_logic_vector(nb_bits(fifo_length)-1 downto 0);--log2 fifo_length + 1 +signal rptr, wptr: std_logic_vector(nb_bits(fifo_length)-1 downto 0); +type vect_fifo_32 is array (fifo_length-1 downto 0) of std_logic_vector (31 downto 0); +signal fifo : vect_fifo_32; + + +begin + +fifo_wr_pr:process(clk, hresetn) +begin + if hresetn='0' then + wptr <= (others => '0'); + elsif clk'event and clk='1' then + if fifo_reset='1' then + wptr <= (others => '0') after 1 ns; + elsif (fifo_write='1') then + fifo(conv_integer(wptr(wptr'length-2 downto 0))) <= fifo_datain after 1 ns; + wptr <= wptr+1 after 1 ns; + end if; + end if; +end process; + +fifo_rd_pr:process(clk, hresetn) +begin + if hresetn='0' then + rptr <= (others => '0'); + elsif clk'event and clk='1' then + if fifo_reset='1' then + rptr <= (others => '0') after 1 ns; + elsif (fifo_read='1') then + rptr <= rptr+1 after 1 ns; + end if; + end if; +end process; + + +fifo_dataout <= fifo(conv_integer(rptr(rptr'length-2 downto 0)));--data from fifo visible + +fifo_count_s <= wptr(wptr'length-1 downto 0) - rptr(rptr'length-1 downto 0); + +fifo_full_s <= '1' when (fifo_count_s=fifo_length) else '0';--same value,/=msb +fifo_empty_s <= '1' when (fifo_count_s=0) else '0';--same value,==msb + +fifo_hfull <= '1' when (fifo_count_s>=fifohfull_level) else '0'; +fifo_hempty <= '1' when (fifo_count_s<=fifohempty_level) else '0'; +fifo_full <= fifo_full_s; +fifo_empty <= fifo_empty_s; +fifo_count <= fifo_count_s; + +end rtl; Index: ahb_system_generator/trunk/src/ahb_master.vhd =================================================================== --- ahb_system_generator/trunk/src/ahb_master.vhd (nonexistent) +++ ahb_system_generator/trunk/src/ahb_master.vhd (revision 3) @@ -0,0 +1,687 @@ + +--******************************************************************* +--** **** +--** AHB system generator **** +--** **** +--** Author: Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--******************************************************************* +--** **** +--** Copyright (C) 2004 Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--** This source file may be used and distributed without **** +--** restriction provided that this copyright statement is not **** +--** removed from the file and that any derivative work contains **** +--** the original copyright notice and the associated disclaimer.**** +--** **** +--** THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY **** +--** EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED **** +--** TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS **** +--** FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR **** +--** OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, **** +--** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES **** +--** (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE **** +--** GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR **** +--** BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF **** +--** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT **** +--** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT **** +--** OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE **** +--** POSSIBILITY OF SUCH DAMAGE. **** +--** **** +--******************************************************************* +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_unsigned.all; +use ieee.std_logic_misc.all; +use ieee.std_logic_arith.all; + +use work.ahb_funct.all; +use work.ahb_package.all; + +entity ahb_master is +generic ( + fifohempty_level: in integer:= 2; + fifohfull_level: in integer:= 6; + fifo_length: in integer:= 8); +port ( + --*********************************************** + --master ahb amba signals + --*********************************************** + hresetn: in std_logic; + hclk: in std_logic; + mst_in: in mst_in_t; + mst_out: out mst_out_t; + + --*********************************************** + --master<=>core interface: conf registers + --*********************************************** + dma_start: in start_type_t; + + --*********************************************** + --master<=>core interface: program/data memories + --*********************************************** + m_wrap_out: out wrap_out_t; + m_wrap_in: in wrap_in_t; + + --*********************************************** + --master/slave/core signals + --*********************************************** + slv_running: in std_logic; + mst_running: out std_logic; + eot_int: out std_logic + ); +end ahb_master; + +architecture rtl of ahb_master is + +--*************************************************************** +--component declaration +--*************************************************************** +component fifo +generic ( + fifohempty_level: in integer:= 1; + fifohfull_level: in integer:= 7; + fifo_length: in integer:= 8); +port ( + hresetn: in std_logic; + clk: in std_logic; + fifo_reset: in std_logic; + fifo_write: in std_logic; + fifo_read: in std_logic; + fifo_count: out std_logic_vector(nb_bits(fifo_length)-1 downto 0); + fifo_full: out std_logic; + fifo_hfull: out std_logic; + fifo_empty: out std_logic; + fifo_hempty: out std_logic; + fifo_datain: in std_logic_vector(31 downto 0); + fifo_dataout: out std_logic_vector(31 downto 0) + ); +end component; + + + +--*************************************************************** +--configuration registers +--*************************************************************** +signal start_hprot: std_logic_vector(3 downto 0); +signal start_hsize: std_logic_Vector(2 downto 0); +signal start_hburst: std_logic_Vector(2 downto 0); +signal start_hwrite: std_logic; +signal start_hlocked: std_logic; +signal start_prior: std_logic; + +signal hbusreq_t, hlock_t: std_logic; +--*************************************************************** +--*************************************************************** +signal r_mst_in, s_mst_in: mst_in_t; +signal r_mst_out, s_mst_out: mst_out_t; + + +type master_fsm is ( + idle_phase, + wait_phase, + req_phase, + addr, --A + addr_data,--A+D + data, --D + retry_phase, + error_phase, + be_phase); +signal mst_state, s_mst_state: master_fsm; + + +signal fifo_full, fifo_hfull, fifo_empty, fifo_hempty: std_logic; +signal fifo_count: std_logic_vector(nb_bits(fifo_length)-1 downto 0); +signal fifo_datain, fifo_dataout: std_logic_vector (31 downto 0); +signal fifo_hread, fifo_hwrite: std_logic; +signal fifo_read, fifo_write: std_logic; +signal fifo_reset: std_logic; +signal next_fifo_empty: std_logic; + +signal dma_count: std_logic_vector (15 downto 0); +signal dma_count_s : std_logic_vector (15 downto 0); +signal right_count: std_logic_vector(15 downto 0); +signal data_trx: std_logic; +signal tmp_htrans: std_logic_vector(1 downto 0); + + +signal next_fifo_full: std_logic; +signal next_fifo_he: std_logic; +signal next_fifo_hf: std_logic; + +signal mst_running_t:std_logic; +signal dma_restart: std_logic; +signal mst_req: std_logic; +signal granted: std_logic; + +signal eot_int_reg:std_logic; +signal prior_reg, prior_s: std_logic; + +signal int_addr, int_addr_s, int_addr_t : std_logic_vector (31 downto 0); +signal int_mod, int_mod_s : std_logic_vector (15 downto 0); +signal int_page_fault: std_logic; +signal int_addr_incr: std_logic; + +signal page_attention: std_logic; +signal page_fault: std_logic; +signal pf_incr, pf_wrap4, pf_wrap8, pf_wrap16: std_logic; + +signal haddr_t : std_logic_vector (31 downto 0); +signal haddr_incr: std_logic; + +signal old_page_attention: std_logic; +signal old_addr_incr: std_logic; +signal old_addr, old_addr_s: std_logic_vector (31 downto 0); +signal old_hburst, old_hburst_s: std_logic_Vector(2 downto 0); + +begin + +--*************************************************************** +--component instantiation +--*************************************************************** +fifo_inst: fifo +generic map( + fifohempty_level => fifohempty_level, + fifohfull_level => fifohfull_level, + fifo_length => fifo_length) +port map( + hresetn => hresetn, + clk => hclk, + fifo_reset => fifo_reset, + fifo_write => fifo_write, + fifo_read => fifo_read, + fifo_count => fifo_count, + fifo_full => fifo_full, + fifo_hfull => fifo_hfull, + fifo_empty => fifo_empty, + fifo_hempty => fifo_hempty, + fifo_datain => fifo_datain, + fifo_dataout => fifo_dataout + ); + + +--*************************** +--****** master state ******* +--*************************** +master_pr:process( +mst_state, +mst_req, +slv_running, +prior_reg, +dma_count, +hbusreq_t, +fifo_empty, +page_fault, +r_mst_out, +mst_in +) +begin + s_mst_state <= mst_state; + case mst_state is + when idle_phase => + if (dma_count>0 and (slv_running='0' or prior_reg=master)) then + s_mst_state <= wait_phase; + end if; + when wait_phase => + if mst_req='1' then + s_mst_state <= req_phase; + end if; + when req_phase => + if (hbusreq_t='1' and mst_in.hgrant='1' and mst_in.hready='1') then--master take bus ownership + s_mst_state <= addr; + end if; + when addr => + if (mst_in.hready='1') then + if (page_fault='1' or mst_in.hgrant='0' or dma_count=1) then + s_mst_state <= data; + else + s_mst_state <= addr_data; + end if; + end if; + when addr_data => + --end of transfer: ready+ok+no_busy_reg+count=1(idle/preidle or burstend) + --page fault:ready+ok+no_busy_reg+count>1 (page_fault) + --no_grant:ready+ok+busy+no_grant (page_fault) + --retry/split:no_ready+retry/split (retry) + --error:no_ready+error (error) + if (mst_in.hready='1') then + if (mst_in.hresp=ok_resp) then + if (r_mst_out.htrans/=busy) then + if (dma_count=1) then + if (r_mst_out.hwrite='1') then + s_mst_state <= data; + else --r_mst_out.hwrite='0', count>1 + s_mst_state <= data;--be_phase; + end if; + elsif (page_fault='1' or mst_in.hgrant='0') then + s_mst_state <= data; + end if; + else -- r_mst_out.htrans=busy + if (mst_in.hgrant='0') then + assert false report "Protocol error: GRANT deasserted during BUSY!!!" severity error; + s_mst_state <= data; + end if; + end if; + end if; + else--hready='0' + case mst_in.hresp is + when retry_resp|split_resp => + s_mst_state <= retry_phase; + when error_resp => + s_mst_state <= error_phase; + when others => + s_mst_state <= addr_data; + end case; + end if; + when data=> + if (mst_in.hready='1') then + if (mst_in.hresp=ok_resp and r_mst_out.htrans/=busy) then + if (dma_count=0) then + if (r_mst_out.hwrite='1') then + s_mst_state <= idle_phase; + else --r_mst_out.hwrite='0', count>1 + s_mst_state <= be_phase; + end if; + else--collapse all this 'if-else' + if (r_mst_out.hwrite='1') then + s_mst_state <= idle_phase; + else + s_mst_state <= be_phase; + end if; + end if; + end if; + else + case mst_in.hresp is + when retry_resp|split_resp => + s_mst_state <= retry_phase;--pay attention: grant removed and retry issued!!!!!! + when error_resp => + s_mst_state <= error_phase; + when others => + s_mst_state <= data; + end case; + end if; + when retry_phase => + if (mst_in.hready='1') then + s_mst_state <= idle_phase; + end if; + when error_phase => + if mst_in.hready='1' then + s_mst_state <= idle_phase; + end if; + when be_phase =>--one of more cycle to empty fifo, settling core internal state + if (fifo_empty ='1') then + s_mst_state <= idle_phase; + end if; + when others => null; + end case; +end process; + +--synopsys translate_off +assert not (hclk'event and hclk='1' and (mst_state=addr_data or mst_state=data) and (mst_in.hready='1' and mst_in.hresp/=ok_resp)) +report "####PROTOCOL ERROR: in addr_data error/retry/split&&ready!!!!!" +severity error; +--synopsys translate_on + +process(hresetn, hclk) +begin + if hresetn='0' then + mst_state <= idle_phase; + elsif hclk'event and hclk='1' then + mst_state <= s_mst_state after 1 ns; + end if; +end process; + + +start_hlocked <= dma_start.hparams(0); +start_hwrite <= dma_start.hparams(1); +start_hprot <= dma_start.hparams(5 downto 2); +start_hburst <= dma_start.hparams(8 downto 6); +start_hsize <= dma_start.hparams(11 downto 9); +start_prior <= dma_start.hparams(12); + +--*************************** +--********** htrans ********* +--*************************** +--busy if: +--write: +--count>1 and fifo=1 and trans_reg/=busy and addr_data +--count=1 and fifo_empty and addr_data +--read: +--fifo_hfull and addr_data +s_mst_out.htrans <= tmp_htrans; + +tmp_htrans <= +--busy when (mst_state=addr_data and granted='1' and page_fault='0' and dma_count>=2 and ((next_fifo_he='1' and r_mst_out.hwrite='1') or (next_fifo_hf='1' and r_mst_out.hwrite='0'))) else +busy when (mst_state=addr_data and ( +(dma_count>=2 and ((fifo_count<=1 and r_mst_out.hwrite='1') or (fifo_count>=fifo_length-1 and r_mst_out.hwrite='0'))) or +(dma_count=1 and ((fifo_count<=1 and r_mst_out.hwrite='1') or (fifo_count=fifo_length and r_mst_out.hwrite='0'))))) else +nonseq when (mst_state=addr) else +seq when (mst_state=addr_data) else +idle; + +--*************************** +--******** granted bus ****** +--*************************** +process(hclk, hresetn) +begin + if hresetn='0' then + granted <= '0'; + elsif hclk'event and hclk='1' then + granted <= '0' after 1 ns; + if (mst_in.hready='1' and mst_in.hgrant='1') then + granted <= '1' after 1 ns; + end if; + end if; +end process; + +next_fifo_empty <= '1' when ((fifo_count=0 and (fifo_write='0' or (fifo_write=fifo_read))) or (fifo_count=1 and fifo_read='1' and fifo_write='0')) else '0'; +next_fifo_full <= '1' when ((fifo_count=fifo_length and (fifo_read='0' or (fifo_write=fifo_read))) or (fifo_count=fifo_length-1 and fifo_read='0' and fifo_write='1')) else '0'; +next_fifo_he <= '1' when ((fifo_count<=1 and (fifo_write='0' or (fifo_write=fifo_read))) or (fifo_count=2 and fifo_read='1' and fifo_write='0')) else '0'; +next_fifo_hf <= '1' when ((fifo_count>=fifo_length-1 and (fifo_read='0' or (fifo_write=fifo_read))) or (fifo_count=fifo_length-2 and fifo_read='0' and fifo_write='1')) else '0'; +--next_count_ge2 <= '1' when ((dma_count_ge2='1' and fifo_hwrite='0' and fifo_hread='0') or (dma_count_ge3='1' and (fifo_hwrite='1' or fifo_hread='1'))) else '0'; + +--*************************** +--********* old_hburst ****** +--*************************** +process(hclk, hresetn) +begin + if hresetn='0' then + old_hburst <= incr; + prior_reg <= slave; + elsif hclk'event and hclk='1' then + old_hburst <= old_hburst_s after 1 ns; + prior_reg <= prior_s after 1 ns; + end if; +end process; +old_hburst_s <= start_hburst when (dma_start.start='1') else old_hburst; +prior_s <= start_prior when (dma_start.start='1') else prior_reg; + +--*************************** +--*************************** +process(hclk,hresetn) +begin + if hresetn='0' then + r_mst_out.haddr <= (others => '0'); + r_mst_out.htrans <= "00"; + r_mst_out.hlock <= '0'; + r_mst_out.hwrite <= '0'; + r_mst_out.hsize <= bits32; + r_mst_out.hburst <= incr; + r_mst_out.hprot <= "0011"; + elsif hclk'event and hclk='1' then + r_mst_out.haddr <= s_mst_out.haddr after 1 ns; + r_mst_out.htrans <= s_mst_out.htrans after 1 ns; + r_mst_out.hlock <= s_mst_out.hlock after 1 ns; + r_mst_out.hwrite <= s_mst_out.hwrite after 1 ns; + r_mst_out.hsize <= s_mst_out.hsize after 1 ns; + r_mst_out.hburst <= s_mst_out.hburst after 1 ns; + r_mst_out.hprot <= s_mst_out.hprot after 1 ns; + end if; +end process; + + +s_mst_out.hlock <= start_hlocked when (dma_start.start='1') else r_mst_out.hlock; +s_mst_out.hwrite <= start_hwrite when (dma_start.start='1') else r_mst_out.hwrite; +s_mst_out.hsize <= start_hsize when (dma_start.start='1') else r_mst_out.hsize; +s_mst_out.hburst <= start_hburst when (dma_start.start='1') else incr when (dma_restart='1') else r_mst_out.hburst; +s_mst_out.hprot <= start_hprot when (dma_start.start='1') else r_mst_out.hprot; + +mst_out.hlock <= hlock_t; +mst_out.hwrite <= r_mst_out.hwrite; +mst_out.hsize <= r_mst_out.hsize; +mst_out.hburst <= r_mst_out.hburst; +mst_out.hprot <= r_mst_out.hprot; + +mst_out.haddr <= r_mst_out.haddr; +mst_out.hwdata <= fifo_dataout;--not retimed! +mst_out.hbusreq <= hbusreq_t; +mst_out.htrans <= s_mst_out.htrans; + + +--*************************** +--********** haddr ********** +--*************************** +old_addr_pr:process(hclk, hresetn) +begin + if hresetn='0' then + old_addr <= (others => '0'); + elsif hclk'event and hclk='1' then + old_addr <= old_addr_s after 1 ns; + end if; +end process; + +old_addr_move:process(mst_state, mst_in, tmp_htrans, r_mst_out) +begin + if ((mst_state=addr or mst_state=addr_data or mst_state=data) and mst_in.hready='1' and tmp_htrans/=busy and r_mst_out.htrans/=busy) then + old_addr_incr <= '1'; + else + old_addr_incr <= '0'; + end if; +end process; + +old_addr_s <= r_mst_out.haddr when (old_addr_incr='1') else +dma_start.extaddr when (dma_start.start='1') else +old_addr; + +page_fault <= '1' when (page_attention='1' and (pf_incr='1' or pf_wrap4='1' or pf_wrap8='1' or pf_wrap16='1')) else '0'; + +pf_incr <= '1' when (haddr_t(9 downto 2)=0) else '0'; +pf_wrap4 <= '1' when (haddr_t(3 downto 2)=0 and old_hburst=wrap4) else '0'; +pf_wrap8 <= '1' when (haddr_t(4 downto 2)=0 and old_hburst=wrap8) else '0'; +pf_wrap16 <= '1' when (haddr_t(5 downto 2)=0 and old_hburst=wrap16) else '0'; + +with r_mst_out.hburst select +page_attention <= +'1' when incr|incr4|incr8|incr16, +'0' when others; + +with old_hburst select +old_page_attention <= +'1' when incr|incr4|incr8|incr16, +'0' when others; + +with r_mst_out.hburst select +haddr_t(9 downto 2) <= +r_mst_out.haddr(9 downto 2)+1 when incr|incr4|incr8|incr16, +r_mst_out.haddr(9 downto 4)&(r_mst_out.haddr(3 downto 2)+"01") when wrap4, +r_mst_out.haddr(9 downto 5)&(r_mst_out.haddr(4 downto 2)+"001") when wrap8, +r_mst_out.haddr(9 downto 6)&(r_mst_out.haddr(5 downto 2)+"0001") when wrap16, +r_mst_out.haddr(9 downto 2) when others;--"000", + +--page increment if: +--page fault and incr/incr4/incr8/incr16 and old_burst incr/incr4/incr8/incr16 +s_mst_out.haddr(31 downto 10) <= +dma_start.extaddr(31 downto 10) when (dma_start.start='1') else +old_addr(31 downto 10) when (mst_state=retry_phase or mst_state=idle_phase) else +(r_mst_out.haddr(31 downto 10)+1) when (page_attention='1' and old_page_attention='1' and pf_incr='1' and haddr_incr='1') else +r_mst_out.haddr(31 downto 10); + +s_mst_out.haddr(1 downto 0) <= dma_start.extaddr(1 downto 0) when (dma_start.start='1') else r_mst_out.haddr(1 downto 0); + +s_mst_out.haddr(9 downto 2) <= +dma_start.extaddr(9 downto 2) when (dma_start.start='1') else +old_addr(9 downto 2) when (mst_state=retry_phase or mst_state=idle_phase) else +r_mst_out.haddr(9 downto 4)&"00" when (page_fault='1' and pf_wrap4='1' and haddr_incr='1') else +r_mst_out.haddr(9 downto 5)&"000" when (page_fault='1' and pf_wrap8='1' and haddr_incr='1') else +r_mst_out.haddr(9 downto 6)&"0000" when (page_fault='1' and pf_wrap16='1' and haddr_incr='1') else +haddr_t(9 downto 2) when (haddr_incr='1') else +r_mst_out.haddr(9 downto 2); + +--haddr_incr_pr:process(mst_state, mst_in, tmp_htrans, r_mst_out) +--begin +-- if ((mst_state=addr or mst_state=addr_data) and mst_in.hready='1' and tmp_htrans/=busy and r_mst_out.htrans/=busy) then-- or mst_state=data +-- haddr_incr <= '1'; +-- else +-- haddr_incr <= '0'; +-- end if; +--end process; + +--haddr_incr <= '1' when +--(mst_in.hready='1' and +--(tmp_htrans=nonseq or +--((tmp_htrans=seq or tmp_htrans=busy) and r_mst_out.htrans/=busy))) else '0'; +haddr_incr <= '1' when +(mst_in.hready='1' and (tmp_htrans=nonseq or tmp_htrans=seq or tmp_htrans=busy) and r_mst_out.htrans/=busy) else '0'; + +--*************************** +--********* hbusreq ********* +--*************************** + +hbusreq_t <= '1' when +( +(dma_count>0 and mst_state=req_phase) or +(dma_count>1 and (mst_state=addr or mst_state=addr_data)) +) else '0'; + +mst_req <= '1' when (r_mst_out.hwrite='0' or fifo_empty='0') else '0'; +--start new master if: +--read or +--write and fifo_count>=2 or +--write and fifo_count=1 and dma_count=1 + +--*************************** +--********** hlock ********* +--*************************** +hlock_t <= hbusreq_t and r_mst_out.hlock;--for hlock behaviour different wrt hbusreq change ONLY here!! + + +--*************************** +--********* eot_int ********* +--*************************** +int_gen:process(hclk, hresetn) +begin + if hresetn='0' then + eot_int_reg <= '0'; + elsif hclk'event and hclk='1' then + if (mst_state=idle_phase) then + eot_int_reg <= '0' after 1 ns; + elsif + (s_mst_state=idle_phase and mst_running_t='1' and dma_count_s=0) then + eot_int_reg <= '1' after 1 ns; + end if; + end if; +end process; + +eot_int <= eot_int_reg; + + +--*************************** +--****** mst_running ***** +--*************************** +mst_running_t <= '0' when (mst_state=idle_phase or mst_state=wait_phase or mst_state=req_phase) else '1'; +mst_running <= mst_running_t; + + +--*************************** +--******** dma_count ******** +--*************************** +dma_count_pr:process(hclk, hresetn) +begin + if hresetn='0' then + dma_count <= (others => '0'); + elsif hclk'event and hclk='1' then + dma_count <= dma_count_s after 1 ns; + end if; +end process; + +process(dma_start, start_hburst) +begin + if dma_start.start='1' then + case start_hburst is + when single => + right_count(15 downto 0) <= "0000000000000001"; + when incr => + right_count(15 downto 0) <= dma_start.count; + when wrap4|incr4 => + right_count(15 downto 0) <= "0000000000000100"; + when wrap8|incr8 => + right_count(15 downto 0) <= "0000000000001000" ; + when others =>--wrap16|incr16 + right_count(15 downto 0) <= "0000000000010000"; + end case; + else + right_count(15 downto 0) <= (others => '-'); + end if; +end process; + +dma_count_s <= + (others=>'0') when fifo_reset='1' else +-- dma_count-1 when (r_mst_out.hwrite='1' and fifo_hread='1') or (r_mst_out.hwrite='0' and fifo_hwrite='1') else + dma_count-1 when ((mst_state=addr or mst_state=addr_data) and haddr_incr='1') else + dma_count+1 when (mst_state=retry_phase and mst_in.hready='1') else + right_count when (dma_start.start='1') else + dma_count; + +dma_restart <= '1' when (mst_state=retry_phase or mst_state=data) else '0'; + +fifo_reset <= '1' when ( +(mst_state=error_phase) or +(mst_in.hresp=ok_resp and r_mst_out.htrans/=busy and r_mst_out.hwrite='1' and mst_in.hready='1' and mst_state=data and dma_count=0) +) else '0'; + + +--*************************** +--***** fifo interface ****** +--*************************** +fifo_write <= fifo_hwrite or m_wrap_in.ask_ok; +fifo_read <= fifo_hread or m_wrap_in.take_ok; + +fifo_datain <= mst_in.hrdata when (fifo_hwrite='1') else m_wrap_in.rdata; +m_wrap_out.wdata <= fifo_dataout; + +--transfer master => fifo +fifo_hwrite <= '1' when (r_mst_out.hwrite='0' and data_trx='1' and fifo_full='0') else '0'; + +--transfer fifo => master +fifo_hread <= '1' when (r_mst_out.hwrite='1' and data_trx='1' and fifo_empty='0') else '0'; + + +data_trx <= '1' when (mst_in.hready='1' and mst_in.hresp=ok_resp and r_mst_out.htrans/=busy and (mst_state=addr_data or mst_state=data)) else '0'; + +--*********************************************** +--master<=>core interface: program/data memories +--*********************************************** + +--transfer fifo => core +m_wrap_out.take <= '1' when (r_mst_out.hwrite='0' and fifo_empty='0') else '0'; + +--transfer core => fifo +m_wrap_out.ask <= '1' when (r_mst_out.hwrite='1' and fifo_full='0' and (mst_running_t='1' or dma_count/=0)) else '0'; + +m_wrap_out.addr <= int_addr; + + +process(hclk, hresetn) +begin + if hresetn='0' then + int_addr <= (others => '0'); + int_mod <= (others => '0'); + elsif hclk'event and hclk='1' then + int_addr <= int_addr_s after 1 ns; + int_mod <= int_mod_s after 1 ns; + end if; +end process; + +int_mod_s <= dma_start.intmod when (dma_start.start='1') else int_mod; + +int_page_fault <= '1' when (int_addr_t(9 downto 2)=0 and page_attention='1') else '0'; + +with r_mst_out.hburst select +int_addr_t(9 downto 2) <= +int_addr(9 downto 2)+int_mod(9 downto 2) when incr|incr4|incr8|incr16, +int_addr(9 downto 4)&(int_addr(3 downto 2)+"01") when wrap4, +int_addr(9 downto 5)&(int_addr(4 downto 2)+"001") when wrap8, +int_addr(9 downto 6)&(int_addr(5 downto 2)+"0001") when wrap16, +int_addr(9 downto 2) when others;--"000", + +int_addr_incr <= '1' when ((r_mst_out.hwrite='0' and m_wrap_in.take_ok='1') or (r_mst_out.hwrite='1' and m_wrap_in.ask_ok='1')) else '0'; + +int_addr_s(31 downto 16) <= (others => '0'); +int_addr_s(15 downto 10) <= (int_addr(15 downto 10)+1) when (int_page_fault='1' and int_addr_incr='1') else dma_start.intaddr(15 downto 10) when (dma_start.start='1') else int_addr(15 downto 10); +int_addr_s(1 downto 0) <= dma_start.intaddr(1 downto 0) when (dma_start.start='1') else int_addr(1 downto 0); +int_addr_s(9 downto 2) <= int_addr_t(9 downto 2) when (int_addr_incr='1') else dma_start.intaddr(9 downto 2) when (dma_start.start='1') else int_addr(9 downto 2); + + +end rtl; Index: ahb_system_generator/trunk/src/ahb_package.vhd =================================================================== --- ahb_system_generator/trunk/src/ahb_package.vhd (nonexistent) +++ ahb_system_generator/trunk/src/ahb_package.vhd (revision 3) @@ -0,0 +1,320 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_arith.all; + +package ahb_package is + +----------------------------------------------------------------------------- +-- Generic contants +----------------------------------------------------------------------------- +--*************************************************************** +constant dump_no: integer := 0;--no dump on memory write +constant dump_end: integer := 1;--memory dump at end of test +constant dump_all: integer := 2;--continuous memory dump +--*************************************************************** +constant zeroes: std_logic_vector(31 downto 0):= (others => '0'); +constant tie_zero: std_logic:= '0'; +constant ones: std_logic_vector(31 downto 0):= (others => '1'); +constant tie_one: std_logic:= '1'; +--*************************************************************** + +----------------------------------------------------------------------------- +-- AHB system: for every slave define LOW and HIGH address +----------------------------------------------------------------------------- +type addr_t is + record + high: integer; + low: integer; + end record; + +----------------------------------------------------------------------------- +-- AHB Master +----------------------------------------------------------------------------- +-- AHB master inputs +type mst_in_t is + record + hgrant: std_logic; + hready: std_logic; + hresp: std_logic_vector(1 downto 0); + hrdata: std_logic_vector(31 downto 0); + end record; + +-- AHB master outputs +type mst_out_t is + record + hbusreq: std_logic; + hlock: std_logic; + htrans: std_logic_vector(1 downto 0); + haddr: std_logic_vector(31 downto 0); + hwrite: std_logic; + hsize: std_logic_vector(2 downto 0); + hburst: std_logic_vector(2 downto 0); + hprot: std_logic_vector(3 downto 0); + hwdata: std_logic_vector(31 downto 0); + end record; + +----------------------------------------------------------------------------- +-- AHB Slave +----------------------------------------------------------------------------- +-- AHB slave inputs +type slv_in_t is + record + hsel: std_logic; + haddr: std_logic_vector(31 downto 0); + hwrite: std_logic; + htrans: std_logic_vector(1 downto 0); + hsize: std_logic_vector(2 downto 0); + hburst: std_logic_vector(2 downto 0); + hwdata: std_logic_vector(31 downto 0); + hprot: std_logic_vector(3 downto 0); + hready: std_logic; + hmaster: std_logic_vector(3 downto 0); + hmastlock: std_logic; + end record; + +-- AHB slave outputs +type slv_out_t is + record + hready: std_logic; + hresp: std_logic_vector(1 downto 0); + hrdata: std_logic_vector(31 downto 0); + hsplit: std_logic_vector(15 downto 0); + end record; + +----------------------------------------------------------------------------- +-- Definitions for AMBA APB Slaves constants and types +----------------------------------------------------------------------------- +constant apb_addr: integer range 8 to 32 := 32;-- address width +constant apb_data: integer range 8 to 32 := 32;-- data width + +-- APB slave inputs +type apb_in_t is + record + psel: std_logic; + penable: std_logic; + paddr: std_logic_vector(apb_addr-1 downto 0); + pwrite: std_logic; + pwdata: std_logic_vector(apb_data-1 downto 0); + end record; + +-- APB slave outputs +type apb_out_t is + record + prdata: std_logic_vector(apb_addr-1 downto 0); + end record; + +----------------------------------------------------------------------------- +-- Definitions for AMBA AHB Arbiter/Decoder/Bridges +----------------------------------------------------------------------------- +-- supporting array types + +type addr_in_v_t is array (15 downto 0) of addr_t; +type addr_matrix_t is array (natural range <> ) of addr_in_v_t; + +type mst_in_v_t is array (natural Range <> ) of mst_in_t; +type mst_out_v_t is array (natural Range <> ) of mst_out_t; + +type slv_in_v_t is array (natural Range <> ) of slv_in_t; +type slv_out_v_t is array (natural Range <> ) of slv_out_t; + +type apb_in_v_t is array (natural range <> ) of apb_in_t; +type apb_out_v_t is array (natural range <> ) of apb_out_t; + + +--*************************************************************** +-- definition of amba AHB protocol constants +--*************************************************************** + +--*************************************************************** +--configuration register space addresses +--*************************************************************** +constant dma_extadd_addr: std_logic_vector(3 downto 0):= "0000"; +constant dma_intadd_addr: std_logic_vector(3 downto 0):= "0001"; +constant dma_intmod_addr: std_logic_vector(3 downto 0):= "0010"; +constant dma_type_addr: std_logic_vector(3 downto 0):= "0011"; +constant dma_count_addr: std_logic_vector(3 downto 0):= "0100"; +constant dma_go_addr: std_logic_vector(3 downto 0):= "0101"; + +--*************************************************************** +-- hprot values +--*************************************************************** +--constant opcode_fetch: std_logic_vector(3 downto 0):= "---0"; +--constant data_access: std_logic_vector(3 downto 0):= "---1"; +--constant user_access: std_logic_vector(3 downto 0):= "--0-"; +--constant privileged_access: std_logic_vector(3 downto 0):= "--1-"; +--constant not_bufferable: std_logic_vector(3 downto 0):= "-0--"; +--constant bufferable: std_logic_vector(3 downto 0):= "-1--"; +--constant not_cacheable: std_logic_vector(3 downto 0):= "0---"; +--constant cacheable: std_logic_vector(3 downto 0):= "1---"; + +--*************************************************************** +-- hburst values +--*************************************************************** +constant single: std_logic_vector(2 downto 0):= "000"; +constant incr: std_logic_vector(2 downto 0):= "001"; +constant wrap4: std_logic_vector(2 downto 0):= "010"; +constant incr4: std_logic_vector(2 downto 0):= "011"; +constant wrap8: std_logic_vector(2 downto 0):= "100"; +constant incr8: std_logic_vector(2 downto 0):= "101"; +constant wrap16: std_logic_vector(2 downto 0):= "110"; +constant incr16: std_logic_vector(2 downto 0):= "111"; + +--*************************************************************** +-- hsize values +--*************************************************************** +constant bits8: std_logic_vector(2 downto 0):= "000"; +constant bits16: std_logic_vector(2 downto 0):= "001"; +constant bits32: std_logic_vector(2 downto 0):= "010"; +constant bits64: std_logic_vector(2 downto 0):= "011"; +constant bits128: std_logic_vector(2 downto 0):= "100"; +constant bits256: std_logic_vector(2 downto 0):= "101"; +constant bits512: std_logic_vector(2 downto 0):= "110"; +constant bits1024: std_logic_vector(2 downto 0):= "111"; + +--*************************************************************** +-- htrans values +--*************************************************************** +constant idle: std_logic_vector(1 downto 0):= "00"; +constant busy: std_logic_vector(1 downto 0):= "01"; +constant nonseq: std_logic_vector(1 downto 0):= "10"; +constant seq: std_logic_vector(1 downto 0):= "11"; + +--*************************************************************** +-- hresp values +--*************************************************************** +constant ok_resp: std_logic_vector(1 downto 0):= "00"; +constant error_resp: std_logic_vector(1 downto 0):= "01"; +constant retry_resp: std_logic_vector(1 downto 0):= "10"; +constant split_resp: std_logic_vector(1 downto 0):= "11"; + +----------------------------------------------------------------------------- +-- AHB system constants +----------------------------------------------------------------------------- + +--*************************************************************** +-- priority values +--*************************************************************** +constant master: std_logic:= '1'; +constant slave: std_logic:= '0'; + +--*************************************************************** +-- split retry programmable slave response values +--*************************************************************** +constant retry: std_logic:= '0'; +constant split: std_logic:= '1'; + +--*************************************************************** +-- locked/non locked ahb bus request programmable +--*************************************************************** +constant nonlocked: std_logic:='0'; +constant locked: std_logic:='1'; + +--*************************************************************** +-- burst capability for masters and slaves +--*************************************************************** +constant burst_support: integer:= 1; +constant no_burst_support: integer:= 0; + +--*************************************************************** +-- hprot values +--*************************************************************** +constant hprot_posted: std_logic_vector(3 downto 0):= "1111"; +constant hprot_nonposted: std_logic_vector(3 downto 0):= "0000"; + +----------------------------------------------------------------------------- +-- Definitions for test ports +----------------------------------------------------------------------------- +type conf_type_t is + record + write: std_logic; + addr: std_logic_vector(3 downto 0); + wdata: std_logic_vector(31 downto 0); + end record; + +----------------------------------------------------------------------------- +-- Definitions for ahb master dma parameters passing +----------------------------------------------------------------------------- +type start_type_t is + record + start: std_logic; + extaddr: std_logic_vector(31 downto 0); + intaddr: std_logic_vector(15 downto 0); + intmod: std_logic_vector(15 downto 0); + count: std_logic_vector(15 downto 0); + hparams: std_logic_vector(15 downto 0); + end record; + +----------------------------------------------------------------------------- +-- Handshake signals and data between master/slave and internal memories/registers +----------------------------------------------------------------------------- +type wrap_out_t is + record + addr: std_logic_vector(31 downto 0); + take: std_logic; + wdata: std_logic_vector(31 downto 0); + ask: std_logic; + end record; + +type wrap_in_t is + record + take_ok: std_logic; + ask_ok: std_logic; + rdata: std_logic_vector(31 downto 0); + end record; + +----------------------------------------------------------------------------- +-- Parameters for defining AHB STIMULATOR behaviour +----------------------------------------------------------------------------- +type uut_params_t is + record + hsize_tb: std_logic_vector(2 downto 0); + split_tb: std_logic; + prior_tb: std_logic; + hburst_cycle: std_logic; + hburst_tb: std_logic_vector(2 downto 0); +-- high_addr_tb:std_logic_vector(19 downto 0); + ext_addr_incr_tb: integer; + intmod_tb: integer; + hprot_tb: std_logic_vector(3 downto 0); + base_tb: integer; + int_addr_incr_tb: integer; + int_base_tb: integer; + locked_request: std_logic; + end record; + +----------------------------------------------------------------------------- +-- Vector types (aggregates) of previous types +----------------------------------------------------------------------------- +type conf_type_v is array (Natural Range <> ) of conf_type_t; + +type start_type_v is array (Natural Range <> ) of start_type_t; + +type wrap_out_v is array (Natural Range <> ) of wrap_out_t; +type wrap_in_v is array (Natural Range <> ) of wrap_in_t; + +type uut_params_v_t is array (Natural Range <> ) of uut_params_t; + +--*************************************************************** + + +--*************************************************************** +--*************************************************************** +--uut#0 +--signal stim_0: uut_params_t:= (bits32,retry,master,'0',wrap4,"00000000000000000000",2,4,hprot_nonposted,2048,1,0,'1'); +--uut#1 +--signal stim_1: uut_params_t:= (bits32,retry,slave,'0',wrap4,"00000000000000000000",2,4,hprot_posted,2048+128,1,0,'1'); +--uut#2 +--signal stim_2: uut_params_t:= (bits32,retry,master,'0',wrap4,"00000000000000000000",2,4,hprot_posted,2048+256,1,0,'0'); +--uut#3 +--signal stim_3: uut_params_t:= (bits32,retry,master,'0',wrap4,"00010000001000000000",2,4,hprot_posted,2048,1,0,'0'); + +--signal stim_v: uut_params_v_t(3 downto 0) := (stim_3, stim_2, stim_1, stim_0); +--*************************************************************** +--*************************************************************** +end; + +package body ahb_package is +end; + + + Index: ahb_system_generator/trunk/src/ahb_slave_wait.vhd =================================================================== --- ahb_system_generator/trunk/src/ahb_slave_wait.vhd (nonexistent) +++ ahb_system_generator/trunk/src/ahb_slave_wait.vhd (revision 3) @@ -0,0 +1,301 @@ + +--******************************************************************* +--** **** +--** AHB system generator **** +--** **** +--** Author: Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--******************************************************************* +--** **** +--** Copyright (C) 2004 Federico Aglietti **** +--** federico.aglietti\@opencores.org **** +--** **** +--** This source file may be used and distributed without **** +--** restriction provided that this copyright statement is not **** +--** removed from the file and that any derivative work contains **** +--** the original copyright notice and the associated disclaimer.**** +--** **** +--** THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY **** +--** EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED **** +--** TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS **** +--** FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR **** +--** OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, **** +--** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES **** +--** (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE **** +--** GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR **** +--** BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF **** +--** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT **** +--** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT **** +--** OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE **** +--** POSSIBILITY OF SUCH DAMAGE. **** +--** **** +--******************************************************************* +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_arith.all; +use ieee.std_logic_unsigned.all; + +use work.ahb_funct.all; +use work.ahb_package.all; +use work.ahb_configure.all; + +entity ahb_slave_wait is + generic ( + num_slv: in integer range 0 to 15:= 1; + fifohempty_level: in integer:= 2; + fifohfull_level: in integer:= 5; + fifo_length: in integer:= 8); + port( + hresetn: in std_logic; + hclk: in std_logic; + remap: in std_logic; + slv_in: in slv_in_t; + slv_out: out slv_out_t; + slv_err: out std_logic; + mst_running: in std_logic; + prior_in: in std_logic; + slv_running: out std_logic; + s_wrap_out: out wrap_out_t; + s_wrap_in: in wrap_in_t); +end ahb_slave_wait; + + +architecture rtl of ahb_slave_wait is + +--parameters fixed for single-wait slave +constant num_slvs: integer:= 1; +constant num_ahb: integer:= 0; +constant def_slv: integer:= 0; +constant alg_number: integer range 0 to 2:= 0; + + +type slv_fsm is (data_cycle,error_cycle); +signal slv_state, s_slv_state: slv_fsm; + +signal r_slv_in_v, s_slv_in_v: slv_in_v_t(num_slvs-1 downto 0); + +signal hready_t, r_hready: std_logic; +signal hresp_t: std_logic_vector(1 downto 0); +signal dec_error: std_logic; + +--*************************************************************** +--arbitration signals +--*************************************************************** +signal s_grant_slave, grant_slave: integer range 0 to num_slvs-1; +signal s_turn, turn: integer range 0 to num_slvs-1; +signal req_ored: std_logic; + +signal slv_req: std_logic_vector(num_slvs-1 downto 0); + +signal addr_slv_matrix: addr_matrix_t(0 downto 0); + +begin + +addr_slv_matrix(0)(num_slvs-1 downto 0) <= slv_matrix(0)(num_slv downto num_slv) when (remap='0') else slv_matrix(1)(num_slv downto num_slv); + +--*************************** +--******* slave state ******* +--*************************** +process(slv_state, dec_error) +begin + s_slv_state <= slv_state; + case slv_state is + when data_cycle => + if (dec_error='1') then + s_slv_state <= error_cycle; + end if; + when error_cycle => + s_slv_state <= data_cycle; + when others => + end case; +end process; + +process(hresetn, hclk) +begin + if hresetn='0' then + r_hready <= '1'; + elsif hclk'event and hclk='1' then + r_hready <= hready_t after 1 ns; + end if; +end process; + +process(hresetn, hclk) +begin + if hresetn='0' then + slv_state <= data_cycle; + elsif hclk'event and hclk='1' then + slv_state <= s_slv_state after 1 ns; + end if; +end process; + + +process(addr_slv_matrix, r_slv_in_v, grant_slave) +variable v_error: std_logic; +begin + v_error:= '0'; + if (r_slv_in_v(grant_slave).hsel='1') then + if (r_slv_in_v(grant_slave).hsize/=bits32) then + v_error:= '1'; + end if; + if (r_slv_in_v(grant_slave).haddr(1 downto 0)/="00") then + v_error:= '1'; + end if; + if (r_slv_in_v(grant_slave).haddr(31 downto 10)conv_std_logic_vector(addr_slv_matrix(num_ahb)(grant_slave).high, 32)(31 downto 10)) then + v_error:= '1'; + end if; + end if; + dec_error <= v_error; +end process; + +--*************************** +--********** hready ********* +--*************************** + +hready_t <= '1' when +(slv_state=error_cycle or +r_slv_in_v(grant_slave).htrans=idle or +r_slv_in_v(grant_slave).htrans=busy or +((r_slv_in_v(grant_slave).htrans=nonseq or r_slv_in_v(grant_slave).htrans=seq) and dec_error='0' and +((r_slv_in_v(grant_slave).hwrite='1' and s_wrap_in.take_ok='1') or (r_slv_in_v(grant_slave).hwrite='0' and s_wrap_in.ask_ok='1')))) else '0'; + +--*************************** +--********** hresp ********** +--*************************** + +hresp_t <= error_resp when (dec_error='1' or slv_state=error_cycle) else ok_resp; +slv_err <= '1' when (slv_state=error_cycle) else '0'; + +--*************************** +--******* s_wrap_out ******** +--*************************** +process(r_slv_in_v, slv_in, slv_state, grant_slave, dec_error) +begin + s_wrap_out.addr <= r_slv_in_v(grant_slave).haddr;--to improve for LOW POWER!! + s_wrap_out.wdata <= slv_in.hwdata;--to improve for LOW POWER!! + s_wrap_out.take <= '0'; + s_wrap_out.ask <= '0'; + if (slv_state=data_cycle and dec_error='0' and slv_in.htrans/=busy and r_slv_in_v(grant_slave).hsel='1' and (r_slv_in_v(grant_slave).htrans=nonseq or r_slv_in_v(grant_slave).htrans=seq)) then + s_wrap_out.take <= r_slv_in_v(grant_slave).hwrite; + s_wrap_out.ask <= not r_slv_in_v(grant_slave).hwrite; + end if; +end process; + + +--*************************** +--********** output ********* +--*************************** +process(s_wrap_in, hready_t, hresp_t, grant_slave, r_slv_in_v) +begin + for i in num_slvs-1 downto 0 loop + slv_out.hsplit <= (others => '0'); + slv_out.hrdata <= s_wrap_in.rdata; + slv_out.hresp <= ok_resp; + slv_out.hready <= '1'; + if (i=grant_slave) then + slv_out.hresp <= hresp_t; + slv_out.hready <= hready_t; + --easiest behaviour: wait for granting!! + elsif (r_slv_in_v(i).hsel='1' and r_slv_in_v(i).htrans/=idle and r_slv_in_v(i).htrans/=busy) then + slv_out.hready <= '0'; + end if; + end loop; +end process; + +--*************************** +--********** input ********** +--*************************** +process(hresetn, hclk) +begin + if hresetn='0' then + for i in num_slvs-1 downto 0 loop + r_slv_in_v(i).hsel <= '0'; + r_slv_in_v(i).hready <= '0'; + r_slv_in_v(i).haddr <= (others=>'0'); + r_slv_in_v(i).hwrite <= '0'; + r_slv_in_v(i).htrans <= idle; + r_slv_in_v(i).hsize <= bits32; + r_slv_in_v(i).hburst <= incr; + r_slv_in_v(i).hprot <= "0011"; + end loop; + elsif hclk'event and hclk='1' then + for i in num_slvs-1 downto 0 loop + r_slv_in_v(i).hready <= slv_in.hready after 1 ns; + if (slv_in.hready='1') then-- and slv_in.hsel='1' + r_slv_in_v(i).hsel <= slv_in.hsel after 1 ns; + r_slv_in_v(i).hburst <= slv_in.hburst after 1 ns; + r_slv_in_v(i).hprot <= slv_in.hprot after 1 ns; + r_slv_in_v(i).hsize <= slv_in.hsize after 1 ns; + r_slv_in_v(i).hwrite <= slv_in.hwrite after 1 ns; + end if; + if (slv_in.hready='1' and r_slv_in_v(i).htrans/=busy) then-- and slv_in.hsel='1' + r_slv_in_v(i).haddr <= slv_in.haddr after 1 ns; + end if; + if (slv_in.hready='1') then-- and slv_in.hsel='1' + r_slv_in_v(i).htrans <= slv_in.htrans after 1 ns; + end if; + end loop; + end if; +end process; + +-------------------------------------------------------------------------- +-- SLAVES RESPONSES AND ARBITRATION +-------------------------------------------------------------------------- + +process(r_slv_in_v) +begin + for i in num_slvs-1 downto 0 loop + slv_req(i) <= '0'; + if (r_slv_in_v(i).hsel='1' and (r_slv_in_v(i).htrans=nonseq or r_slv_in_v(i).htrans=seq)) then + slv_req(i) <= '1'; + end if; + end loop; +end process; + +process(slv_req) +variable v_req_ored: std_logic; +begin + v_req_ored := '0'; + for i in num_slvs-1 downto 0 loop + v_req_ored := v_req_ored or slv_req(i); + end loop; + req_ored <= v_req_ored; +end process; + +update_pr:process(turn, grant_slave, r_hready, req_ored, slv_req, r_slv_in_v) +variable t_turn, t_grant_slave: integer; +begin + t_turn := turn; + t_grant_slave := grant_slave; + if (r_hready='1' and req_ored='1' and r_slv_in_v(grant_slave).htrans/=busy and not(slv_req(grant_slave) and r_slv_in_v(grant_slave).hmastlock)='1') then + case alg_number is + when 0 => --fixed + fixed_priority(t_turn, t_grant_slave, slv_req, turn); +-- when 1 => --round robin +-- round_robin(def_slv, t_turn, t_grant_slave, slv_req, turn); + when others => --NOT IMPLEMENTED + assert FALSE report "### NOT IMPLEMENTED!" severity FAILURE; + end case; + --else (no_ready) then SAME SLAVE + end if; + s_turn <= t_turn; + s_grant_slave <= t_grant_slave; +end process; + +process(hresetn, hclk) +begin + if hresetn='0' then + grant_slave <= 0; + turn <= 0; + elsif hclk'event and hclk='1' then + grant_slave <= s_grant_slave after 1 ns; + turn <= s_turn after 1 ns; + end if; +end process; + +end rtl; + + Index: ahb_system_generator/trunk/src/ahb_funct.vhd =================================================================== --- ahb_system_generator/trunk/src/ahb_funct.vhd (nonexistent) +++ ahb_system_generator/trunk/src/ahb_funct.vhd (revision 3) @@ -0,0 +1,147 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_arith.all; + +package ahb_funct is + +function nb_bits (A : std_logic_vector) return NATURAL; +function nb_bits (A : INTEGER) return NATURAL; + +procedure fixed_priority( +t_turn: out integer; +t_grant: out integer; +req: in std_logic_vector; +turn: in integer); +procedure round_robin( +def_elem: in integer; +t_turn: out integer; +t_grant: out integer; +req: in std_logic_vector; +turn: in integer); +procedure random_priority( +def_elem: in integer; +t_turn: out integer; +t_grant: out integer; +random: in integer; +req: in std_logic_vector; +turn: in integer); + +end ahb_funct; + +package body ahb_funct is + + function nb_bits (A : std_logic_vector) return NATURAL is + variable logres : NATURAL ; + begin + logres := 1; + for i in A'length-1 downto 0 loop + if A(i) = '1' then + logres := i; + exit; + end if; + end loop; + return logres; + end nb_bits; + + function nb_bits (A : INTEGER) return NATURAL is + variable logres : NATURAL ; + begin + logres := 1; + for i in 0 to 30 loop + if 2**i <= A then + logres := i+1; + end if; + end loop; + return logres; + end nb_bits; + +procedure fixed_priority( +t_turn: out integer;-- range 0 to num_elem-1; +t_grant: out integer; +req: in std_logic_vector; +turn: in integer-- range 0 to num_elem-1 +) is +begin + t_grant := 0; + t_turn := 0; + req_for:for i in req'length-1 downto 0 loop + if req(i) = '1' then + t_grant := i; + end if; + end loop; +end fixed_priority; + +procedure round_robin( +def_elem: in integer; +t_turn: out integer;-- range 0 to num_elem-1; +t_grant: out integer;-- range 0 to num_elem-1; +req: in std_logic_vector; +turn: in integer-- range 0 to num_elem-1 +) is +constant req_size: integer:= req'length; +variable v_req: std_logic_vector(req_size*2-1 downto 0); +type turn_array is array (req_size-1 downto 0) of std_logic_vector(req_size-1 downto 0); +variable v_turn: turn_array; +begin + t_grant := def_elem; + t_turn := turn; + v_req := req&req;--concatenation + for i in 0 to req_size-1 loop + v_turn(i) := v_req(i+req_size-1 downto i); + end loop; + for j in 0 to req_size-1 loop + if j=turn then + for jj in 0 to req_size-1 loop + if v_turn(j)(jj)='1' then + if turn+jj >=req'length then + t_turn := turn+jj-req_size; + t_grant := turn+jj-req_size; + else + t_turn := turn+jj; + t_grant := turn+jj; + end if; + end if; + end loop; -- jj + end if; + end loop; -- j +end round_robin; + + +procedure random_priority( +def_elem: in integer; +t_turn: out integer;-- range 0 to num_elem-1; +t_grant: out integer;-- range 0 to num_elem-1; +random: in integer;-- range 0 to 2**(nb_bits(num_elem)); +req: in std_logic_vector; +turn: in integer-- range 0 to num_elem-1 +) is +constant req_size: integer:= req'length; +variable j, v_turn, upper_limit: integer; +begin + t_grant := def_elem; + upper_limit := 2**(nb_bits(req_size))-1; + v_turn := turn; + req_for:for i in upper_limit downto 0 loop + if ((i >= random) and (i <= random+upper_limit)) then + j := i mod req_size; + if req(j) = '1' then + t_grant := j; + if turn=req_size-1 then + v_turn := 0; + else + v_turn := turn+1; + end if; + end if; + t_turn := v_turn; + --synopsys translate_off + assert (v_turn>=0 and v_turn '-'); + + +process(clk, hresetn) +begin + if hresetn='0' then + m_lat_read <= m_const_lat_read; + elsif clk'event and clk='1' then + if (m_wrap_in.ask='1') then + if (m_lat_read_ok='0') then + m_lat_read <= m_lat_read-1 after 1 ns; + elsif (m_read_burst=1) then--accepts bursts ..... + m_lat_read <= 0 after 1 ns; + else + m_lat_read <= m_const_lat_read after 1 ns; + end if; + else + m_lat_read <= m_const_lat_read after 1 ns; + end if; + end if; +end process; + +m_lat_read_ok <= '1' when (m_lat_read=0) else '0'; +m_wrap_out.ask_ok <= '1' when (m_wrap_in.ask='1' and m_lat_read_ok='1') else '0'; + + + + +--************************************************************************** +-- configuration registers write +--************************************************************************** + + +conf_reg_pr:process(hresetn, clk) +variable addr: std_logic_Vector(3 downto 0); +begin +if hresetn='0' then + hsize_reg <= bits32; + priority_reg <= slave; + hburst_reg <= incr; + hprot_reg <= "0011"; + trx_dir_reg <= '0'; + hlock_reg <= locked; + extaddr <= zeroes; + intaddr <= zeroes(15 downto 0); + intmod <= conv_std_logic_vector(4, intmod'length);--mod=+4(+1 word32) + count_reg <= zeroes(15 downto 0); + dma_go <= '0'; +elsif clk'event and clk='1' then + if (conf.write='1') then + case conf.addr is + when dma_extadd_addr => + extaddr <= conf.wdata; + when dma_intadd_addr => + intaddr <= conf.wdata(15 downto 0); + when dma_intmod_addr => + intmod <= conf.wdata(15 downto 0); + when dma_type_addr => + priority_reg <= conf.wdata(12); + hsize_reg <= conf.wdata(11 downto 9); + hburst_reg <= conf.wdata(8 downto 6); + hprot_reg <= conf.wdata(5 downto 2); + trx_dir_reg <= conf.wdata(1); + hlock_reg <= conf.wdata(0); + when dma_count_addr => + count_reg <= conf.wdata(15 downto 0); + when others => null; + end case; + end if; + if (conf.write='1' and conf.addr=dma_count_addr) then + dma_go <= '1'; + else + dma_go <= '0'; + end if; + end if; +end process; +--************************************************************************** +--************************************************************************** + + +--************************************************************************** +--************************************************************************** + dma_start.extaddr <= extaddr; + dma_start.intaddr <= intaddr; + dma_start.intmod <= intmod; + dma_start.hparams <= "000"&priority_reg&hsize_reg&hburst_reg&hprot_reg&trx_dir_reg&hlock_reg; + dma_start.count <= count_reg; + dma_start.start <= dma_go; + +end rtl; Index: ahb_system_generator/trunk/docs/ahb_generator.pdf =================================================================== Cannot display: file marked as a binary type. svn:mime-type = application/octet-stream Index: ahb_system_generator/trunk/docs/ahb_generator.pdf =================================================================== --- ahb_system_generator/trunk/docs/ahb_generator.pdf (nonexistent) +++ ahb_system_generator/trunk/docs/ahb_generator.pdf (revision 3)
ahb_system_generator/trunk/docs/ahb_generator.pdf Property changes : Added: svn:mime-type ## -0,0 +1 ## +application/octet-stream \ No newline at end of property Index: ahb_system_generator/trunk =================================================================== --- ahb_system_generator/trunk (nonexistent) +++ ahb_system_generator/trunk (revision 3)
ahb_system_generator/trunk Property changes : Added: svn:mergeinfo ## -0,0 +0,0 ## Index: ahb_system_generator/web_uploads =================================================================== --- ahb_system_generator/web_uploads (nonexistent) +++ ahb_system_generator/web_uploads (revision 3)
ahb_system_generator/web_uploads Property changes : Added: svn:mergeinfo ## -0,0 +0,0 ## Index: ahb_system_generator/branches =================================================================== --- ahb_system_generator/branches (nonexistent) +++ ahb_system_generator/branches (revision 3)
ahb_system_generator/branches Property changes : Added: svn:mergeinfo ## -0,0 +0,0 ## Index: ahb_system_generator/tags =================================================================== --- ahb_system_generator/tags (nonexistent) +++ ahb_system_generator/tags (revision 3)
ahb_system_generator/tags Property changes : Added: svn:mergeinfo ## -0,0 +0,0 ##

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.