summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorbd <bdunahu@operationnull.com>2025-04-12 00:44:29 -0400
committerbd <bdunahu@operationnull.com>2025-04-12 00:44:29 -0400
commit28a2788e2c59357d9269e558b0bd45db3241c42d (patch)
tree5e001355106684d514dcb96afcec2ad102513a33
parent1fb7a9bd5eb41e87871bcbb3423caaabdd8ce1d9 (diff)
Rewrite utils functions as macros
-rw-r--r--.clang-format3
-rw-r--r--CMakeLists.txt33
-rw-r--r--inc/definitions.h61
-rw-r--r--inc/dram.h7
-rw-r--r--inc/utils.h39
-rw-r--r--src/cache.cc5
-rw-r--r--src/dram.cc8
-rw-r--r--src/utils.cc42
-rw-r--r--tests/utils.cc65
9 files changed, 57 insertions, 206 deletions
diff --git a/.clang-format b/.clang-format
index 39ed432..30fe2e7 100644
--- a/.clang-format
+++ b/.clang-format
@@ -1,11 +1,12 @@
---
Language: Cpp
+AlwaysBreakAfterDefinitionReturnType: All
AlignAfterOpenBracket: AlwaysBreak
AllowAllParametersOfDeclarationOnNextLine: true
BinPackParameters: false
BreakBeforeBraces: Linux
PointerAlignment: Right
-ColumnLimit: 80
+ColumnLimit: 100
IndentWidth: 4
TabWidth: 4
UseTab: Always \ No newline at end of file
diff --git a/CMakeLists.txt b/CMakeLists.txt
index f8ec7be..661e45c 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -1,7 +1,8 @@
cmake_minimum_required(VERSION 3.5)
-set(CMAKE_CXX_COMPILER "g++")
project(ram)
+option(RAM_TESTS "Enable creation of a memory-subsystem test binary." ON)
+
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
add_compile_options(-Wall -lstdc++ -g -O0)
@@ -11,28 +12,26 @@ add_compile_options(-Wextra -Wpedantic)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
-# header files
-include_directories(
- ${PROJECT_SOURCE_DIR}/inc
-)
-
# gather source files
file(GLOB_RECURSE SRCS "src/*.cc")
# binary executable
add_library(${PROJECT_NAME}_lib ${SRCS})
-target_link_libraries(${PROJECT_NAME}_lib)
+target_include_directories(${PROJECT_NAME}_lib PUBLIC ${PROJECT_SOURCE_DIR}/inc)
-find_package(Catch2 REQUIRED)
+if(RAM_TESTS)
+ find_package(Catch2 REQUIRED)
-#gather test files
-file(GLOB_RECURSE TESTS "tests/*.cc")
+ #gather test files
+ file(GLOB_RECURSE TESTS "tests/*.cc")
-# test executable
-add_executable(tests ${SRCS} ${TESTS})
-target_link_libraries(tests PRIVATE Catch2::Catch2WithMain PRIVATE)
+ # test executable
+ add_executable(tests ${SRCS} ${TESTS})
+ target_include_directories(tests PUBLIC ${PROJECT_SOURCE_DIR}/inc)
+ target_link_libraries(tests PRIVATE Catch2::Catch2WithMain PRIVATE)
-# test discovery
-include(CTest)
-include(Catch)
-catch_discover_tests(tests)
+ # test discovery
+ include(CTest)
+ include(Catch)
+ catch_discover_tests(tests)
+endif()
diff --git a/inc/definitions.h b/inc/definitions.h
index 6fa29ee..94414a4 100644
--- a/inc/definitions.h
+++ b/inc/definitions.h
@@ -31,8 +31,7 @@
* The total number of lines in l1 cache
*/
#define L1_CACHE_WORD_SPEC 7
-#define L1_CACHE_LINE_SPEC \
- static_cast<unsigned int>(L1_CACHE_WORD_SPEC - LINE_SPEC)
+#define L1_CACHE_LINE_SPEC static_cast<unsigned int>(L1_CACHE_WORD_SPEC - LINE_SPEC)
#define L1_CACHE_LINES static_cast<int>(pow(2, L1_CACHE_LINE_SPEC))
/**
@@ -46,42 +45,6 @@
#define L1_CACHE_DELAY 0
/**
- * The number of general purpose registers
- */
-#define GPR_NUM 16
-
-/**
- * The number of vector registers
- */
-#define V_NUM 8
-
-/**
- * The number of bits to specify an instruction type
- */
-#define TYPE_SIZE 2
-
-/**
- * The number of bits to specify a register
- */
-#define REG_SIZE 5
-
-/**
- * The number of bits to specify an R-Type opcode.
- */
-#define R_OPCODE_SIZE 5
-
-/**
- * The number of bits to specify an opcode.
- */
-#define OPCODE_SIZE 4
-
-/**
- * The maximum value an integer can hold.
- * The minimum is always this number plus one negated.
- */
-#define MAX_INT 2147483647
-
-/**
* Return the N least-significant bits from integer K using a bit mask
* @param the integer to be parsed
* @param the number of bits to be parsed
@@ -98,4 +61,26 @@
*/
#define GET_MID_BITS(k, m, n) GET_LS_BITS((k) >> (m), ((n) - (m)))
+/**
+ * Parse an address into a tag, index into the cache table, and a line
+ * offset.
+ * @param the address to be parsed
+ * @param the resulting tag
+ * @param the resulting index
+ * @param the resulting offset
+ */
+// clang-format off
+#define GET_FIELDS(a, t, i, o) \
+ *(t) = GET_MID_BITS(a, L1_CACHE_LINE_SPEC + LINE_SPEC, MEM_WORD_SPEC); \
+ *(i) = GET_MID_BITS(a, LINE_SPEC, L1_CACHE_LINE_SPEC + LINE_SPEC); \
+ *(o) = GET_LS_BITS(a, LINE_SPEC); \
+
+/**
+ * Ensures address is within the current memory size using a clean wrap.
+ * @param an address
+ */
+#define WRAP_ADDRESS(a) \
+ ((a < 0) ? ((a % MEM_WORDS) + MEM_WORDS) % MEM_WORDS : a % MEM_WORDS) \
+// clang-format on
+
#endif /* DEFINITIONS_H_INCLUDED */
diff --git a/inc/dram.h b/inc/dram.h
index c6c3159..140cbb1 100644
--- a/inc/dram.h
+++ b/inc/dram.h
@@ -52,6 +52,13 @@ class Dram : public Storage
*/
int
is_access_cleared(void *id);
+ /**
+ * Given `address`, returns the line and word it is in.
+ * @param an address
+ * @param the line (row) `address` is in
+ * @param the word (column) `address` corresponds to
+ */
+ void get_memory_index(int address, int &line, int &word);
};
#endif /* DRAM_H_INCLUDED */
diff --git a/inc/utils.h b/inc/utils.h
deleted file mode 100644
index a375b68..0000000
--- a/inc/utils.h
+++ /dev/null
@@ -1,39 +0,0 @@
-#ifndef UTILS_H
-#define UTILS_H
-#include <string>
-
-/**
- * Parse an address into a tag, index into the cache table, and a line
- * offset.
- * @param the address to be parsed
- * @param the resulting tag
- * @param the resulting index
- * @param the resulting offset
- */
-void get_cache_fields(int address, int *tag, int *index, int *offset);
-
-/**
- * Formats a string using snprintf.
- * @param an object that represents the format string
- * @param arguments to be formatted
- * @return a string object holding the formatted result
- */
-const std::string string_format(const char *const zcFormat, ...);
-
-/**
- * Given `address`, returns an address that is within the current memory size
- * using a clean wrap.
- * @param an address
- * @return an address guaranteed to be within range.
- */
-int wrap_address(int address);
-
-/**
- * Given `address`, returns the line and word it is in.
- * @param an address
- * @param the line (row) `address` is in
- * @param the word (column) `address` corresponds to
- */
-void get_memory_index(int address, int &line, int &word);
-
-#endif /* UTILS_H_INCLUDED */
diff --git a/src/cache.cc b/src/cache.cc
index bbb90b4..acbabcf 100644
--- a/src/cache.cc
+++ b/src/cache.cc
@@ -1,6 +1,5 @@
#include "cache.h"
#include "definitions.h"
-#include "utils.h"
#include <bits/stdc++.h>
#include <iterator>
@@ -60,7 +59,7 @@ Cache::process(void *id, int address, std::function<void(int index, int offset)>
r = this->is_access_cleared(id, address);
if (r) {
int tag, index, offset;
- get_cache_fields(address, &tag, &index, &offset);
+ GET_FIELDS(address, &tag, &index, &offset);
request_handler(index, offset);
}
return r;
@@ -95,7 +94,7 @@ Cache::is_address_missing(int expected)
std::array<signed int, LINE_SIZE> *actual;
std::array<int, 2> *meta;
- get_cache_fields(expected, &tag, &index, &offset);
+ GET_FIELDS(expected, &tag, &index, &offset);
r = 0;
meta = &this->meta.at(index);
actual = &this->data->at(index);
diff --git a/src/dram.cc b/src/dram.cc
index d81e2d2..2fd8a91 100644
--- a/src/dram.cc
+++ b/src/dram.cc
@@ -4,7 +4,6 @@
#include <bits/stdc++.h>
#include <bitset>
#include <iterator>
-#include <utils.h>
Dram::Dram(int delay) : Storage(delay) { this->data->resize(MEM_LINES); }
@@ -85,3 +84,10 @@ Dram::is_access_cleared(void *id)
}
return 0;
}
+
+void
+Dram::get_memory_index(int address, int &line, int &word)
+{
+ line = WRAP_ADDRESS(address) / LINE_SIZE;
+ word = address % LINE_SIZE;
+}
diff --git a/src/utils.cc b/src/utils.cc
deleted file mode 100644
index e12a0e0..0000000
--- a/src/utils.cc
+++ /dev/null
@@ -1,42 +0,0 @@
-#include "utils.h"
-#include "definitions.h"
-#include <cstdarg>
-#include <string>
-#include <vector>
-
-void get_cache_fields(int address, int *tag, int *index, int *offset)
-{
- *tag = GET_MID_BITS(address, L1_CACHE_LINE_SPEC + LINE_SPEC, MEM_WORD_SPEC);
- *index = GET_MID_BITS(address, LINE_SPEC, L1_CACHE_LINE_SPEC + LINE_SPEC);
- *offset = GET_LS_BITS(address, LINE_SPEC);
-}
-
-const std::string string_format(const char *const zcFormat, ...)
-{
- va_list vaArgs;
- va_start(vaArgs, zcFormat);
-
- va_list vaArgsCopy;
- va_copy(vaArgsCopy, vaArgs);
- const int iLen = std::vsnprintf(NULL, 0, zcFormat, vaArgsCopy);
- va_end(vaArgsCopy);
-
- std::vector<char> zc(iLen + 1);
- std::vsnprintf(zc.data(), zc.size(), zcFormat, vaArgs);
- va_end(vaArgs);
- return std::string(zc.data(), iLen);
-}
-
-int wrap_address(int address)
-{
- if (address < 0) {
- return ((address % MEM_WORDS) + MEM_WORDS) % MEM_WORDS;
- }
- return address % MEM_WORDS;
-}
-
-void get_memory_index(int address, int &line, int &word)
-{
- line = wrap_address(address) / LINE_SIZE;
- word = address % LINE_SIZE;
-}
diff --git a/tests/utils.cc b/tests/utils.cc
deleted file mode 100644
index 2e0e934..0000000
--- a/tests/utils.cc
+++ /dev/null
@@ -1,65 +0,0 @@
-#include "utils.h"
-#include "definitions.h"
-#include <catch2/catch_test_macros.hpp>
-
-TEST_CASE("Parse arbitrary fields # one", "[utils]")
-{
- int tag, index, offset;
- int address = 0b0001010101;
- get_cache_fields(address, &tag, &index, &offset);
- CHECK(tag == 0b000);
- CHECK(index == 0b10101);
- CHECK(offset == 0b01);
-}
-
-TEST_CASE("Parse arbitrary fields # two", "[utils]")
-{
- int tag, index, offset;
- int address = 0b0100111011;
- get_cache_fields(address, &tag, &index, &offset);
- CHECK(tag == 0b010);
- CHECK(index == 0b01110);
- CHECK(offset == 0b11);
-}
-
-TEST_CASE("wrap address outside upper bound", "[utils]")
-{
- int address = MEM_WORDS + 25;
- int wrapped = wrap_address(address);
- REQUIRE(wrapped == 25);
-}
-
-TEST_CASE("wrap address inside upper bound", "[utils]")
-{
- int address = MEM_WORDS - 25;
- int wrapped = wrap_address(address);
- REQUIRE(wrapped == MEM_WORDS - 25);
-}
-
-TEST_CASE("wrap address at upper bound", "[utils]")
-{
- int address = MEM_WORDS;
- int wrapped = wrap_address(address);
- REQUIRE(wrapped == 0);
-}
-
-TEST_CASE("wrap address lower than 0 with magnitude lesser than mem size", "[utils]")
-{
- int address = -10;
- int wrapped = wrap_address(address);
- REQUIRE(wrapped == MEM_WORDS - 10);
-}
-
-TEST_CASE("wrap address lower than 0 but with magnitude greater than mem size", "[utils]")
-{
- int address = -(MEM_WORDS + 10);
- int wrapped = wrap_address(address);
- REQUIRE(wrapped == MEM_WORDS - 10);
-}
-
-TEST_CASE("wrap address at 0", "[utils]")
-{
- int address = 0;
- int wrapped = wrap_address(address);
- REQUIRE(wrapped == 0);
-}