Skip to content

Commit

Permalink
i#4842 drcachesim: Add unit tests for FIFO cache simulator (#5454)
Browse files Browse the repository at this point in the history
Adds get_next_way_to_replace() helper method that just returns the victim way
without a side effect on the cache state. This makes unit testing the cache
replacement policies convenient and avoids unexpected behavior during testing.

Adds cache_policy_test_t class template for testing multiple cache replacement policies.

Adds get_block_index() method that returns the block index for a given address.

Issue: #4842, #5456
  • Loading branch information
bete0 committed May 25, 2022
1 parent 726ca9b commit a2fece6
Show file tree
Hide file tree
Showing 7 changed files with 223 additions and 61 deletions.
27 changes: 21 additions & 6 deletions clients/drcachesim/simulator/cache_fifo.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -70,17 +70,32 @@ cache_fifo_t::access_update(int block_idx, int way)
return;
}

// This method replaces the current victim way and returns the next victim way
// to be replaced. As opposed to get_next_way_to_replace() which just returns the
// next way to be replaced without updating the cache state, replace_which_way()
// updates the cache state.
int
cache_fifo_t::replace_which_way(int block_idx)
{
// We replace the block whose counter is 1.
int victim_way = get_next_way_to_replace(block_idx);
if (victim_way == -1)
return -1;
// clear the counter of the victim block
get_caching_device_block(block_idx, victim_way).counter_ = 0;
// set the next block as victim
get_caching_device_block(block_idx, (victim_way + 1) & (associativity_ - 1))
.counter_ = 1;
return victim_way;
}

// This method just returns the next way to be replaced without actually
// replacing it, hence doesn't have a side-effect.
int
cache_fifo_t::get_next_way_to_replace(const int block_idx) const
{
for (int i = 0; i < associativity_; i++) {
// We return the block whose counter is 1.
if (get_caching_device_block(block_idx, i).counter_ == 1) {
// clear the counter of the victim block
get_caching_device_block(block_idx, i).counter_ = 0;
// set the next block as victim
get_caching_device_block(block_idx, (i + 1) & (associativity_ - 1)).counter_ =
1;
return i;
}
}
Expand Down
6 changes: 4 additions & 2 deletions clients/drcachesim/simulator/cache_fifo.h
Original file line number Diff line number Diff line change
Expand Up @@ -49,9 +49,11 @@ class cache_fifo_t : public cache_t {

protected:
void
access_update(int line_idx, int way) override;
access_update(int block_idx, int way) override;
int
replace_which_way(int line_idx) override;
replace_which_way(int block_idx) override;
int
get_next_way_to_replace(const int block_idx) const override;
};

#endif /* _CACHE_FIFO_H_ */
24 changes: 15 additions & 9 deletions clients/drcachesim/simulator/cache_lru.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -63,34 +63,40 @@ cache_lru_t::init(int associativity, int block_size, int total_size,
}

void
cache_lru_t::access_update(int line_idx, int way)
cache_lru_t::access_update(int block_idx, int way)
{
int cnt = get_caching_device_block(line_idx, way).counter_;
int cnt = get_caching_device_block(block_idx, way).counter_;
// Optimization: return early if it is a repeated access.
if (cnt == 0)
return;
// We inc all the counters that are not larger than cnt for LRU.
for (int i = 0; i < associativity_; ++i) {
if (i != way && get_caching_device_block(line_idx, i).counter_ <= cnt)
get_caching_device_block(line_idx, i).counter_++;
if (i != way && get_caching_device_block(block_idx, i).counter_ <= cnt)
get_caching_device_block(block_idx, i).counter_++;
}
// Clear the counter for LRU.
get_caching_device_block(line_idx, way).counter_ = 0;
get_caching_device_block(block_idx, way).counter_ = 0;
}

int
cache_lru_t::replace_which_way(int line_idx)
cache_lru_t::replace_which_way(int block_idx)
{
return get_next_way_to_replace(block_idx);
}

int
cache_lru_t::get_next_way_to_replace(int block_idx) const
{
// We implement LRU by picking the slot with the largest counter value.
int max_counter = 0;
int max_way = 0;
for (int way = 0; way < associativity_; ++way) {
if (get_caching_device_block(line_idx, way).tag_ == TAG_INVALID) {
if (get_caching_device_block(block_idx, way).tag_ == TAG_INVALID) {
max_way = way;
break;
}
if (get_caching_device_block(line_idx, way).counter_ > max_counter) {
max_counter = get_caching_device_block(line_idx, way).counter_;
if (get_caching_device_block(block_idx, way).counter_ > max_counter) {
max_counter = get_caching_device_block(block_idx, way).counter_;
max_way = way;
}
}
Expand Down
6 changes: 4 additions & 2 deletions clients/drcachesim/simulator/cache_lru.h
Original file line number Diff line number Diff line change
Expand Up @@ -49,9 +49,11 @@ class cache_lru_t : public cache_t {

protected:
void
access_update(int line_idx, int way) override;
access_update(int block_idx, int way) override;
int
replace_which_way(int line_idx) override;
replace_which_way(int block_idx) override;
int
get_next_way_to_replace(const int block_idx) const override;
};

#endif /* _CACHE_LRU_H_ */
11 changes: 9 additions & 2 deletions clients/drcachesim/simulator/caching_device.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -256,6 +256,15 @@ caching_device_t::access_update(int block_idx, int way)

int
caching_device_t::replace_which_way(int block_idx)
{
int min_way = get_next_way_to_replace(block_idx);
// Clear the counter for LFU.
get_caching_device_block(block_idx, min_way).counter_ = 0;
return min_way;
}

int
caching_device_t::get_next_way_to_replace(const int block_idx) const
{
// The base caching device class only implements LFU.
// A subclass can override this and access_update() to implement
Expand All @@ -272,8 +281,6 @@ caching_device_t::replace_which_way(int block_idx)
min_way = way;
}
}
// Clear the counter for LFU.
get_caching_device_block(block_idx, min_way).counter_ = 0;
return min_way;
}

Expand Down
15 changes: 12 additions & 3 deletions clients/drcachesim/simulator/caching_device.h
Original file line number Diff line number Diff line change
Expand Up @@ -115,28 +115,37 @@ class caching_device_t {
}
use_tag2block_table_ = use_hashtable;
}
int
get_block_index(const addr_t addr) const
{
addr_t tag = compute_tag(addr);
int block_idx = compute_block_idx(tag);
return block_idx;
}

protected:
virtual void
access_update(int block_idx, int way);
virtual int
replace_which_way(int block_idx);
virtual int
get_next_way_to_replace(const int block_idx) const;
virtual void
record_access_stats(const memref_t &memref, bool hit,
caching_device_block_t *cache_block);

inline addr_t
compute_tag(addr_t addr)
compute_tag(addr_t addr) const
{
return addr >> block_size_bits_;
}
inline int
compute_block_idx(addr_t tag)
compute_block_idx(addr_t tag) const
{
return (tag & blocks_per_set_mask_) << assoc_bits_;
}
inline caching_device_block_t &
get_caching_device_block(int block_idx, int way)
get_caching_device_block(int block_idx, int way) const
{
return *(blocks_[block_idx + way]);
}
Expand Down
Loading

0 comments on commit a2fece6

Please sign in to comment.