-
Notifications
You must be signed in to change notification settings - Fork 8
/
Copy pathmemory_base.svh
108 lines (95 loc) · 2.9 KB
/
memory_base.svh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
`ifndef MEMORY_BASE_SVH
`define MEMORY_BASE_SVH
class memory_base #(
int ADDRESS_WIDTH = 32,
int DATA_WIDTH = 32
)extends uvm_object;
typedef bit [ADDRESS_WIDTH-1:0] memory_address;
typedef bit [DATA_WIDTH-1:0] memory_data;
typedef bit [DATA_WIDTH/8-1:0] memory_strobe;
logic [DATA_WIDTH-1:0] default_data;
protected int byte_width;
protected byte memory[memory_address];
function new(string name="memory_base", int data_width=DATA_WIDTH);
super.new(name);
default_data = '0;
byte_width = data_width/8;
endfunction : new
virtual function void put(
memory_data data,
memory_strobe strobe,
int byte_size,
memory_address base,
int word_index
);
memory_address start_address;
memory_address mem_address;
int byte_index;
start_address = get_start_address(byte_size, base, word_index);
for (int i=0; i<byte_size; i++) begin
mem_address = start_address + i;
byte_index = mem_address % byte_width;
memory[mem_address] = data[8*byte_index +: 8];
end
endfunction : put
virtual function memory_data get(
int byte_size,
memory_address base,
int word_index
);
memory_data data;
memory_address start_address;
memory_address mem_address;
int byte_index;
start_address = get_start_address(byte_size, base, word_index);
for (int i=0; i<byte_size; i++) begin
mem_address = start_address + i;
byte_index = mem_address % byte_width;
if (memory.exists(mem_address)) begin
data[8*byte_index +: 8] = memory[mem_address];
end
else begin
data[8*byte_index +: 8] = get_default_data(byte_index);
end
end
return data;
endfunction : get
virtual function bit exists(
int byte_size,
memory_address base,
int word_index
);
memory_address start_address;
memory_address mem_address;
start_address = get_start_address(byte_size, base, word_index);
for (int i=0; i<byte_size; i++) begin
mem_address = start_address + i;
if (memory.exists(mem_address)) begin
return 1;
end
end
return 0;
endfunction : exists
protected function memory_address get_start_address(
int byte_size,
memory_address base,
int word_index
);
return (base&get_address_mask(byte_size)) + byte_size*word_index;
endfunction : get_start_address
protected function memory_address get_address_mask(int byte_size);
memory_address mask;
mask = byte_size - 1;
mask = ~mask;
return mask;
endfunction : get_address_mask
protected function byte get_default_data(int byte_index);
if ($isunknown(default_data[8*byte_index +: 8])) begin
return $urandom_range(255);
end
else begin
return default_data[8*byte_index +: 8];
end
endfunction : get_default_data
endclass : memory_base
`endif