Skip to content
Projects
Groups
Snippets
Help
Loading...
Sign in
Toggle navigation
P
Platform-independent core collection
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
18
Issues
18
List
Board
Labels
Milestones
Merge Requests
5
Merge Requests
5
Wiki
Wiki
image/svg+xml
Discourse
Discourse
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Commits
Issue Boards
Open sidebar
Projects
Platform-independent core collection
Commits
c0614a39
Commit
c0614a39
authored
Feb 20, 2017
by
Grzegorz Daniluk
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'greg_ram_init' into proposed_master
parents
b833b5d8
0973db51
Hide whitespace changes
Inline
Side-by-side
Showing
7 changed files
with
293 additions
and
214 deletions
+293
-214
genram_pkg.vhd
modules/genrams/genram_pkg.vhd
+11
-0
memory_loader_pkg.vhd
modules/genrams/memory_loader_pkg.vhd
+17
-153
Manifest.py
modules/genrams/xilinx/Manifest.py
+1
-0
generic_dpram.vhd
modules/genrams/xilinx/generic_dpram.vhd
+58
-2
generic_dpram_sameclock.vhd
modules/genrams/xilinx/generic_dpram_sameclock.vhd
+0
-12
generic_dpram_split.vhd
modules/genrams/xilinx/generic_dpram_split.vhd
+206
-0
xwb_dpram.vhd
modules/wishbone/wb_dpram/xwb_dpram.vhd
+0
-47
No files found.
modules/genrams/genram_pkg.vhd
View file @
c0614a39
...
...
@@ -45,6 +45,7 @@ package genram_pkg is
function
f_log2_size
(
A
:
natural
)
return
natural
;
function
f_gen_dummy_vec
(
val
:
std_logic
;
size
:
natural
)
return
std_logic_vector
;
function
f_zeros
(
size
:
integer
)
return
std_logic_vector
;
function
f_check_bounds
(
x
:
integer
;
minx
:
integer
;
maxx
:
integer
)
return
integer
;
type
t_generic_ram_init
is
array
(
integer
range
<>
,
integer
range
<>
)
of
std_logic
;
...
...
@@ -244,5 +245,15 @@ package body genram_pkg is
return
std_logic_vector
(
to_unsigned
(
0
,
size
));
end
f_zeros
;
function
f_check_bounds
(
x
:
integer
;
minx
:
integer
;
maxx
:
integer
)
return
integer
is
begin
if
(
x
<
minx
)
then
return
minx
;
elsif
(
x
>
maxx
)
then
return
maxx
;
else
return
x
;
end
if
;
end
f_check_bounds
;
end
genram_pkg
;
modules/genrams/memory_loader_pkg.vhd
View file @
c0614a39
...
...
@@ -12,10 +12,6 @@ package memory_loader_pkg is
subtype
t_meminit_array
is
t_generic_ram_init
;
function
f_hexchar_to_slv
(
c
:
character
)
return
std_logic_vector
;
function
f_hexstring_to_slv
(
s
:
string
;
n_digits
:
integer
)
return
std_logic_vector
;
function
f_get_token
(
s
:
string
;
n
:
integer
)
return
string
;
function
f_load_mem_from_file
(
file_name
:
string
;
mem_size
:
integer
;
...
...
@@ -27,128 +23,22 @@ end memory_loader_pkg;
package
body
memory_loader_pkg
is
function
f_hexchar_to_slv
(
c
:
character
)
return
std_logic_vector
is
variable
t
:
std_logic_vector
(
3
downto
0
);
begin
case
c
is
when
'0'
=>
t
:
=
x"0"
;
when
'1'
=>
t
:
=
x"1"
;
when
'2'
=>
t
:
=
x"2"
;
when
'3'
=>
t
:
=
x"3"
;
when
'4'
=>
t
:
=
x"4"
;
when
'5'
=>
t
:
=
x"5"
;
when
'6'
=>
t
:
=
x"6"
;
when
'7'
=>
t
:
=
x"7"
;
when
'8'
=>
t
:
=
x"8"
;
when
'9'
=>
t
:
=
x"9"
;
when
'a'
=>
t
:
=
x"a"
;
when
'A'
=>
t
:
=
x"a"
;
when
'b'
=>
t
:
=
x"b"
;
when
'B'
=>
t
:
=
x"b"
;
when
'c'
=>
t
:
=
x"c"
;
when
'C'
=>
t
:
=
x"c"
;
when
'd'
=>
t
:
=
x"d"
;
when
'D'
=>
t
:
=
x"d"
;
when
'e'
=>
t
:
=
x"e"
;
when
'E'
=>
t
:
=
x"e"
;
when
'f'
=>
t
:
=
x"f"
;
when
'F'
=>
t
:
=
x"f"
;
when
others
=>
report
"f_hexchar_to_slv(): unrecognized character '"
&
c
&
" in hex text string"
severity
failure
;
end
case
;
return
t
;
end
f_hexchar_to_slv
;
function
f_hexstring_to_slv
(
s
:
string
;
n_digits
:
integer
)
return
std_logic_vector
is
variable
tmp
:
std_logic_vector
(
255
downto
0
)
:
=
(
others
=>
'0'
);
begin
if
s
'length
>
tmp
'length
then
report
"f_hexstring_to_slv(): string length exceeds the limit"
severity
failure
;
end
if
;
for
i
in
0
to
s
'length
-1
loop
tmp
(
4
*
(
s
'length
-
i
)
-
1
downto
4
*
(
s
'length
-
1
-
i
))
:
=
f_hexchar_to_slv
(
s
(
i
+
1
));
end
loop
;
-- i
return
tmp
(
n_digits
*
4
-
1
downto
0
);
end
f_hexstring_to_slv
;
function
f_get_token
(
s
:
string
;
n
:
integer
)
return
string
is
variable
cur_pos
:
integer
;
variable
tmp
:
string
(
1
to
128
);
variable
cur_token
:
integer
;
variable
tmp_pos
:
integer
;
begin
cur_pos
:
=
1
;
cur_token
:
=
1
;
tmp_pos
:
=
1
;
loop
if
(
cur_pos
>=
s
'length
)
then
return
""
;
end
if
;
while
cur_pos
<=
s
'length
and
(
s
(
cur_pos
)
=
' '
or
s
(
cur_pos
)
=
character
'val
(
9
)
or
s
(
cur_pos
)
=
character
'val
(
0
))
loop
cur_pos
:
=
cur_pos
+
1
;
end
loop
;
if
(
cur_pos
>=
s
'length
)
then
return
""
;
end
if
;
while
(
cur_pos
<=
s
'length
and
s
(
cur_pos
)
/=
' '
and
s
(
cur_pos
)
/=
character
'val
(
9
)
and
s
(
cur_pos
)
/=
character
'val
(
0
))
loop
if
(
cur_token
=
n
)
then
tmp
(
tmp_pos
)
:
=
s
(
cur_pos
);
tmp_pos
:
=
tmp_pos
+
1
;
end
if
;
cur_pos
:
=
cur_pos
+
1
;
end
loop
;
if
(
cur_token
=
n
)
then
return
tmp
(
1
to
tmp_pos
-1
);
end
if
;
cur_token
:
=
cur_token
+
1
;
if
(
cur_pos
>=
s
'length
)
then
return
""
;
end
if
;
end
loop
;
return
""
;
end
f_get_token
;
function
f_load_mem_from_file
(
file_name
:
string
;
mem_size
:
integer
;
mem_width
:
integer
;
(
file_name
:
in
string
;
mem_size
:
in
in
teger
;
mem_width
:
in
in
teger
;
fail_if_notfound
:
boolean
)
return
t_meminit_array
is
file
f_in
:
text
;
variable
l
:
line
;
variable
ls
:
string
(
1
to
128
);
variable
cmd
:
string
(
1
to
128
);
variable
line_len
:
integer
;
FILE
f_in
:
text
;
variable
l
:
line
;
variable
tmp_bv
:
bit_vector
(
mem_width
-1
downto
0
);
variable
tmp_sv
:
std_logic_vector
(
mem_width
-1
downto
0
);
variable
mem
:
t_meminit_array
(
0
to
mem_size
-1
,
mem_width
-1
downto
0
)
;
variable
status
:
file_open_status
;
variable
mem
:
t_meminit_array
(
0
to
mem_size
-1
,
mem_width
-1
downto
0
);
variable
i
:
integer
;
variable
c
:
character
;
variable
good
:
boolean
;
variable
addr
:
integer
;
variable
data_tmp
:
unsigned
(
mem_width
-1
downto
0
);
variable
data_int
:
integer
;
begin
if
(
file_name
=
""
or
file_name
=
"none"
)
then
mem
:
=
(
others
=>
(
others
=>
'0'
));
mem
:
=
(
others
=>
(
others
=>
'0'
));
return
mem
;
end
if
;
...
...
@@ -162,44 +52,18 @@ package body memory_loader_pkg is
end
if
;
end
if
;
while
true
loop
i
:
=
0
;
while
(
i
<
4096
)
loop
-- stupid ISE restricts the loop length
readline
(
f_in
,
l
);
line_len
:
=
0
;
loop
read
(
l
,
ls
(
line_len
+
1
),
good
);
exit
when
good
=
false
;
line_len
:
=
line_len
+
1
;
end
loop
;
if
(
line_len
/=
0
and
f_get_token
(
ls
,
1
)
=
"write"
)
then
addr
:
=
to_integer
(
unsigned
(
f_hexstring_to_slv
(
f_get_token
(
ls
,
2
),
8
)));
data_tmp
:
=
resize
(
unsigned
(
f_hexstring_to_slv
(
f_get_token
(
ls
,
3
),
8
)),
mem_width
);
data_int
:
=
to_integer
(
data_tmp
);
-- report "addr: " & integer'image(addr) & " data: " & integer'image(data_int);
for
i
in
0
to
mem_width
-1
loop
mem
(
addr
,
i
)
:
=
std_logic
(
data_tmp
(
i
));
end
loop
;
-- i in 0 to mem_width-1
-- report "addr: " & integer'image(addr) & " data: " & integer'image(data_int);
end
if
;
if
endfile
(
f_in
)
then
file_close
(
f_in
);
return
mem
;
end
if
;
i
:
=
i
+
1
;
for
I
in
0
to
mem_size
-1
loop
readline
(
f_in
,
l
);
-- read function gives us bit_vector
read
(
l
,
tmp_bv
);
tmp_sv
:
=
to_stdlogicvector
(
tmp_bv
);
for
J
in
0
to
mem_width
-1
loop
mem
(
i
,
j
)
:
=
tmp_sv
(
j
);
end
loop
;
end
loop
;
file_close
(
f_in
);
return
mem
;
end
f_load_mem_from_file
;
end
memory_loader_pkg
;
modules/genrams/xilinx/Manifest.py
View file @
c0614a39
...
...
@@ -3,6 +3,7 @@ files = [
"generic_dpram_sameclock.vhd"
,
"generic_dpram_dualclock.vhd"
,
"generic_simple_dpram.vhd"
,
"generic_dpram_split.vhd"
,
"generic_spram.vhd"
,
"gc_shiftreg.vhd"
]
modules/genrams/xilinx/generic_dpram.vhd
View file @
c0614a39
...
...
@@ -76,6 +76,33 @@ end generic_dpram;
architecture
syn
of
generic_dpram
is
constant
c_gen_split
:
boolean
:
=
(
g_dual_clock
=
false
and
g_data_width
=
32
and
g_with_byte_enable
=
true
and
(
g_addr_conflict_resolution
=
"dont_care"
or
g_addr_conflict_resolution
=
"read_first"
));
constant
c_gen_sc
:
boolean
:
=
(
not
c_gen_split
)
and
(
not
g_dual_clock
);
constant
c_gen_dc
:
boolean
:
=
g_dual_clock
;
component
generic_dpram_split
generic
(
g_size
:
natural
;
g_addr_conflict_resolution
:
string
:
=
"dont_care"
;
g_init_file
:
string
:
=
"none"
;
g_fail_if_file_not_found
:
boolean
:
=
true
);
port
(
rst_n_i
:
in
std_logic
:
=
'1'
;
clk_i
:
in
std_logic
;
bwea_i
:
in
std_logic_vector
(
3
downto
0
);
wea_i
:
in
std_logic
;
aa_i
:
in
std_logic_vector
(
f_log2_size
(
g_size
)
-1
downto
0
);
da_i
:
in
std_logic_vector
(
31
downto
0
);
qa_o
:
out
std_logic_vector
(
31
downto
0
);
bweb_i
:
in
std_logic_vector
(
3
downto
0
);
web_i
:
in
std_logic
;
ab_i
:
in
std_logic_vector
(
f_log2_size
(
g_size
)
-1
downto
0
);
db_i
:
in
std_logic_vector
(
31
downto
0
);
qb_o
:
out
std_logic_vector
(
31
downto
0
));
end
component
;
component
generic_dpram_sameclock
generic
(
g_data_width
:
natural
;
...
...
@@ -125,7 +152,36 @@ architecture syn of generic_dpram is
begin
gen_single_clk
:
if
(
g_dual_clock
=
false
)
generate
-- generic_dpram_split is like generic_dpram_sameclock, but hardcoded to
-- 32-bit data width and split into 4 BRAMs, each of them 8-bit wide. It's
-- better for Xilinx ISE, because it's unable to infer DPRAM with byte-write
-- enables without using huge number of LUTs.
-- Since it's hardcoded to 32-bits data width, we need to keep
-- generic_dpram_sameclock as well. For reasons why generic_dpram_split is
-- hardcoded to 32-bits please check the Note in generic_dpram_split.vhd.
gen_splitram
:
if
c_gen_split
generate
U_RAM_SPLIT
:
generic_dpram_split
generic
map
(
g_size
=>
g_size
,
g_addr_conflict_resolution
=>
g_addr_conflict_resolution
,
g_init_file
=>
g_init_file
,
g_fail_if_file_not_found
=>
g_fail_if_file_not_found
)
port
map
(
rst_n_i
=>
rst_n_i
,
clk_i
=>
clka_i
,
bwea_i
=>
bwea_i
,
wea_i
=>
wea_i
,
aa_i
=>
aa_i
,
da_i
=>
da_i
,
qa_o
=>
qa_o
,
bweb_i
=>
bweb_i
,
web_i
=>
web_i
,
ab_i
=>
ab_i
,
db_i
=>
db_i
,
qb_o
=>
qb_o
);
end
generate
gen_splitram
;
gen_single_clk
:
if
c_gen_sc
generate
U_RAM_SC
:
generic_dpram_sameclock
generic
map
(
g_data_width
=>
g_data_width
,
...
...
@@ -151,7 +207,7 @@ begin
end
generate
gen_single_clk
;
gen_dual_clk
:
if
(
g_dual_clock
=
true
)
generate
gen_dual_clk
:
if
c_gen_dc
generate
U_RAM_DC
:
generic_dpram_dualclock
generic
map
(
g_data_width
=>
g_data_width
,
...
...
modules/genrams/xilinx/generic_dpram_sameclock.vhd
View file @
c0614a39
...
...
@@ -117,20 +117,8 @@ architecture syn of generic_dpram_sameclock is
signal
s_we_b
:
std_logic_vector
(
c_num_bytes
-1
downto
0
);
signal
s_ram_in_b
:
std_logic_vector
(
g_data_width
-1
downto
0
);
signal
wea_rep
,
web_rep
:
std_logic_vector
(
c_num_bytes
-1
downto
0
);
function
f_check_bounds
(
x
:
integer
;
minx
:
integer
;
maxx
:
integer
)
return
integer
is
begin
if
(
x
<
minx
)
then
return
minx
;
elsif
(
x
>
maxx
)
then
return
maxx
;
else
return
x
;
end
if
;
end
f_check_bounds
;
begin
wea_rep
<=
(
others
=>
wea_i
);
...
...
modules/genrams/xilinx/generic_dpram_split.vhd
0 → 100644
View file @
c0614a39
-------------------------------------------------------------------------------
-- Title : Dual-port synchronous RAM with byte-write for Xilinx
-------------------------------------------------------------------------------
-- File : generic_dpram_split.vhd
-- Author : Grzegorz Daniluk
-- Company : CERN BE-CO-HT
-- Created : 2017-02-13
-- Last update: 2017-02-13
-- Platform :
-- Standard : VHDL'93
-------------------------------------------------------------------------------
-- Description:
-- This module is 32-bit RAM with byte-write enables. It was created for Xilinx
-- FPGAs, since Xilinx ISE is unable to infer dual-port block-RAM with
-- byte-writes (e.g. based on generic_dpram_sameclock.vhd module). When
-- synthesizing generic_dpram_sameclock with g_with_byte_enable, ISE uses a lot
-- of LUTs to get the byte-write behavior (instead of using the features of BRAM
-- blocks).
--
-- Note:
-- This module is hardcoded to 32-bits and 4 ram modules (ram0-3). It would be
-- much cleaner to have a generic code and using ram(0 to g_data_width/8-1).
-- However, it looks that ISE is not able to initialize 3-d array that would be
-- needed in this case.
-- I.e. this works:
-- shared variable ram0 : t_split_ram := f_memarray_to_ramtype(f_file_contents, 0);
-- shared variable ram1 : t_split_ram := f_memarray_to_ramtype(f_file_contents, 1);
-- shared variable ram2 : t_split_ram := f_memarray_to_ramtype(f_file_contents, 2);
-- shared variable ram3 : t_split_ram := f_memarray_to_ramtype(f_file_contents, 3);
--
-- but this doesn't:
-- type t_split_ram_array is array(0 to 3) of t_split_ram;
-- shared variable ram : t_split_ram_array := (f_memarray_to_ramtype(f_file_contents, 0),
-- f_memarray_to_ramtype(f_file_contents, 1),f_memarray_to_ramtype(f_file_contents, 2),
-- f_memarray_to_ramtype(f_file_contents, 3));
--
-- By "doesn't work" I mean that ISE does not fail during the synthesis, but RAM
-- does not get initialized.
-------------------------------------------------------------------------------
-- Copyright (c) 2017 CERN
--
-- This source file is free software; you can redistribute it
-- and/or modify it under the terms of the GNU Lesser General
-- Public License as published by the Free Software Foundation;
-- either version 2.1 of the License, or (at your option) any
-- later version.
--
-- This source is distributed in the hope that it will be
-- useful, but WITHOUT ANY WARRANTY; without even the implied
-- warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
-- PURPOSE. See the GNU Lesser General Public License for more
-- details.
--
-- You should have received a copy of the GNU Lesser General
-- Public License along with this source; if not, download it
-- from http://www.gnu.org/licenses/lgpl-2.1.html
--
-------------------------------------------------------------------------------
library
ieee
;
use
ieee
.
std_logic_1164
.
all
;
use
ieee
.
numeric_std
.
all
;
library
work
;
use
work
.
genram_pkg
.
all
;
use
work
.
memory_loader_pkg
.
all
;
entity
generic_dpram_split
is
generic
(
g_size
:
natural
:
=
16384
;
g_addr_conflict_resolution
:
string
:
=
"read_first"
;
g_init_file
:
string
:
=
""
;
g_fail_if_file_not_found
:
boolean
:
=
true
);
port
(
rst_n_i
:
in
std_logic
:
=
'1'
;
clk_i
:
in
std_logic
;
-- Port A
bwea_i
:
in
std_logic_vector
(
3
downto
0
);
wea_i
:
in
std_logic
;
aa_i
:
in
std_logic_vector
(
f_log2_size
(
g_size
)
-1
downto
0
);
da_i
:
in
std_logic_vector
(
31
downto
0
);
qa_o
:
out
std_logic_vector
(
31
downto
0
);
-- Port B
bweb_i
:
in
std_logic_vector
(
3
downto
0
);
web_i
:
in
std_logic
;
ab_i
:
in
std_logic_vector
(
f_log2_size
(
g_size
)
-1
downto
0
);
db_i
:
in
std_logic_vector
(
31
downto
0
);
qb_o
:
out
std_logic_vector
(
31
downto
0
));
end
generic_dpram_split
;
architecture
syn
of
generic_dpram_split
is
constant
c_data_width
:
integer
:
=
32
;
constant
c_num_bytes
:
integer
:
=
(
c_data_width
+
7
)
/
8
;
type
t_split_ram
is
array
(
0
to
g_size
-1
)
of
std_logic_vector
(
7
downto
0
);
function
f_memarray_to_ramtype
(
arr
:
t_meminit_array
;
idx
:
integer
)
return
t_split_ram
is
variable
tmp
:
t_split_ram
;
variable
n
,
pos
:
integer
;
begin
pos
:
=
0
;
while
(
pos
<
g_size
)
loop
n
:
=
0
;
-- avoid ISE loop iteration limit
while
(
pos
<
g_size
and
n
<
4096
)
loop
for
i
in
0
to
7
loop
tmp
(
pos
)(
i
)
:
=
arr
(
pos
,
i
+
idx
*
8
);
end
loop
;
n
:
=
n
+
1
;
pos
:
=
pos
+
1
;
end
loop
;
end
loop
;
return
tmp
;
end
f_memarray_to_ramtype
;
function
f_file_contents
return
t_meminit_array
is
begin
return
f_load_mem_from_file
(
g_init_file
,
g_size
,
c_data_width
,
g_fail_if_file_not_found
);
end
f_file_contents
;
shared
variable
ram0
:
t_split_ram
:
=
f_memarray_to_ramtype
(
f_file_contents
,
0
);
shared
variable
ram1
:
t_split_ram
:
=
f_memarray_to_ramtype
(
f_file_contents
,
1
);
shared
variable
ram2
:
t_split_ram
:
=
f_memarray_to_ramtype
(
f_file_contents
,
2
);
shared
variable
ram3
:
t_split_ram
:
=
f_memarray_to_ramtype
(
f_file_contents
,
3
);
signal
s_we_a
:
std_logic_vector
(
c_num_bytes
-1
downto
0
);
signal
s_we_b
:
std_logic_vector
(
c_num_bytes
-1
downto
0
);
signal
wea_rep
:
std_logic_vector
(
c_num_bytes
-1
downto
0
);
signal
web_rep
:
std_logic_vector
(
c_num_bytes
-1
downto
0
);
begin
assert
(
g_addr_conflict_resolution
=
"read_first"
or
g_addr_conflict_resolution
=
"dont_care"
)
report
"generic_dpram_split: only read_first and dont_care supported for now"
severity
failure
;
-- combine byte-write enable with write signals
wea_rep
<=
(
others
=>
wea_i
);
web_rep
<=
(
others
=>
web_i
);
s_we_a
<=
bwea_i
and
wea_rep
;
s_we_b
<=
bweb_i
and
web_rep
;
--------------------------------------------------
-- yes, I know this is 4 times exactly the same code for ram0,1,2,3,
-- but ISE fails to initialize BRAM when ram is an array (check Note
-- in the header of this file).
GEN_RAM0
:
process
(
clk_i
)
begin
if
rising_edge
(
clk_i
)
then
qa_o
(
7
downto
0
)
<=
ram0
(
f_check_bounds
(
to_integer
(
unsigned
(
aa_i
)),
0
,
g_size
-1
));
qb_o
(
7
downto
0
)
<=
ram0
(
f_check_bounds
(
to_integer
(
unsigned
(
ab_i
)),
0
,
g_size
-1
));
if
s_we_a
(
0
)
=
'1'
then
ram0
(
f_check_bounds
(
to_integer
(
unsigned
(
aa_i
)),
0
,
g_size
-1
))
:
=
da_i
(
7
downto
0
);
end
if
;
if
s_we_b
(
0
)
=
'1'
then
ram0
(
f_check_bounds
(
to_integer
(
unsigned
(
ab_i
)),
0
,
g_size
-1
))
:
=
db_i
(
7
downto
0
);
end
if
;
end
if
;
end
process
;
GEN_RAM1
:
process
(
clk_i
)
begin
if
rising_edge
(
clk_i
)
then
qa_o
(
15
downto
8
)
<=
ram1
(
f_check_bounds
(
to_integer
(
unsigned
(
aa_i
)),
0
,
g_size
-1
));
qb_o
(
15
downto
8
)
<=
ram1
(
f_check_bounds
(
to_integer
(
unsigned
(
ab_i
)),
0
,
g_size
-1
));
if
s_we_a
(
1
)
=
'1'
then
ram1
(
f_check_bounds
(
to_integer
(
unsigned
(
aa_i
)),
0
,
g_size
-1
))
:
=
da_i
(
15
downto
8
);
end
if
;
if
s_we_b
(
1
)
=
'1'
then
ram1
(
f_check_bounds
(
to_integer
(
unsigned
(
ab_i
)),
0
,
g_size
-1
))
:
=
db_i
(
15
downto
8
);
end
if
;
end
if
;
end
process
;
GEN_RAM2
:
process
(
clk_i
)
begin
if
rising_edge
(
clk_i
)
then
qa_o
(
23
downto
16
)
<=
ram2
(
f_check_bounds
(
to_integer
(
unsigned
(
aa_i
)),
0
,
g_size
-1
));
qb_o
(
23
downto
16
)
<=
ram2
(
f_check_bounds
(
to_integer
(
unsigned
(
ab_i
)),
0
,
g_size
-1
));
if
s_we_a
(
2
)
=
'1'
then
ram2
(
f_check_bounds
(
to_integer
(
unsigned
(
aa_i
)),
0
,
g_size
-1
))
:
=
da_i
(
23
downto
16
);
end
if
;
if
s_we_b
(
2
)
=
'1'
then
ram2
(
f_check_bounds
(
to_integer
(
unsigned
(
ab_i
)),
0
,
g_size
-1
))
:
=
db_i
(
23
downto
16
);
end
if
;
end
if
;
end
process
;
GEN_RAM3
:
process
(
clk_i
)
begin
if
rising_edge
(
clk_i
)
then
qa_o
(
31
downto
24
)
<=
ram3
(
f_check_bounds
(
to_integer
(
unsigned
(
aa_i
)),
0
,
g_size
-1
));
qb_o
(
31
downto
24
)
<=
ram3
(
f_check_bounds
(
to_integer
(
unsigned
(
ab_i
)),
0
,
g_size
-1
));
if
s_we_a
(
3
)
=
'1'
then
ram3
(
f_check_bounds
(
to_integer
(
unsigned
(
aa_i
)),
0
,
g_size
-1
))
:
=
da_i
(
31
downto
24
);
end
if
;
if
s_we_b
(
3
)
=
'1'
then
ram3
(
f_check_bounds
(
to_integer
(
unsigned
(
ab_i
)),
0
,
g_size
-1
))
:
=
db_i
(
31
downto
24
);
end
if
;
end
if
;
end
process
;
end
syn
;
modules/wishbone/wb_dpram/xwb_dpram.vhd
View file @
c0614a39
...
...
@@ -55,13 +55,6 @@ end xwb_dpram;
architecture
struct
of
xwb_dpram
is
function
f_zeros
(
size
:
integer
)
return
std_logic_vector
is
begin
return
std_logic_vector
(
to_unsigned
(
0
,
size
));
end
f_zeros
;
signal
s_wea
:
std_logic
;
signal
s_web
:
std_logic
;
signal
s_bwea
:
std_logic_vector
(
3
downto
0
);
...
...
@@ -72,9 +65,6 @@ architecture struct of xwb_dpram is
signal
slave2_in
:
t_wishbone_slave_in
;
signal
slave2_out
:
t_wishbone_slave_out
;
begin
U_Adapter1
:
wb_slave_adapter
generic
map
(
...
...
@@ -108,11 +98,6 @@ begin
master_i
=>
slave2_out
,
master_o
=>
slave2_in
);
GEN_INITF
:
if
g_init_file
/=
""
and
g_init_file
/=
"none"
generate
-- Unfortunately stupid ISE has problem with understanding bytesel
-- description in generic_dpram so it instantiates this using numerous LUTs
-- for connecting BRAMs and supporting bytesel. When initialization with
-- file is not needed it's better to use GEN_NO_INITF.
U_DPRAM
:
generic_dpram
generic
map
(
-- standard parameters
...
...
@@ -140,38 +125,6 @@ begin
db_i
=>
slave2_in
.
dat
,
qb_o
=>
slave2_out
.
dat
);
end
generate
;
GEN_NO_INITF
:
if
g_init_file
=
""
or
g_init_file
=
"none"
generate
-- This trick splits ram into four 8-bit blocks of RAM. Now the problem ISE
-- has with understanding correctly bytesel is bypassed and the
-- implementation takes almost none LUTs, just BRAMs.
GEN_BYTESEL
:
for
i
in
0
to
3
generate
U_DPRAM
:
generic_dpram
generic
map
(
g_data_width
=>
8
,
g_size
=>
g_size
,
g_with_byte_enable
=>
false
,
g_addr_conflict_resolution
=>
"dont_care"
,
g_init_file
=>
""
,
g_dual_clock
=>
false
)
port
map
(
rst_n_i
=>
rst_n_i
,
-- Port A
clka_i
=>
clk_sys_i
,
wea_i
=>
s_bwea
(
i
),
aa_i
=>
slave1_in
.
adr
(
f_log2_size
(
g_size
)
-1
downto
0
),
da_i
=>
slave1_in
.
dat
((
i
+
1
)
*
8-1
downto
i
*
8
),
qa_o
=>
slave1_out
.
dat
((
i
+
1
)
*
8-1
downto
i
*
8
),
-- Port B
clkb_i
=>
clk_sys_i
,
web_i
=>
s_bweb
(
i
),
ab_i
=>
slave2_in
.
adr
(
f_log2_size
(
g_size
)
-1
downto
0
),
db_i
=>
slave2_in
.
dat
((
i
+
1
)
*
8-1
downto
i
*
8
),
qb_o
=>
slave2_out
.
dat
((
i
+
1
)
*
8-1
downto
i
*
8
)
);
end
generate
;
end
generate
;
-- I know this looks weird, but otherwise ISE generates distributed RAM instead of block
-- RAM
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment