-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Implement simple linear allocator (#57)
Closes #50
- Loading branch information
Showing
20 changed files
with
223 additions
and
13 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -7,5 +7,5 @@ build/ | |
|
||
# ide stuff | ||
.idea | ||
cmake-build-debug | ||
cmake-build* | ||
include/ChaiVM/interpreter/autogen |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
#pragma once | ||
|
||
#include <cstdlib> | ||
|
||
namespace chai::memory { | ||
|
||
template <class T> class IAllocator { | ||
public: | ||
using value_type = T; | ||
IAllocator() noexcept = default; | ||
virtual T *allocate(size_t n) = 0; | ||
virtual void deallocate(T *p, size_t n) = 0; | ||
virtual ~IAllocator() {} | ||
}; | ||
|
||
} // namespace chai::memory |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
#pragma once | ||
|
||
#include <cstdlib> | ||
#include <new> | ||
#include <numeric> | ||
|
||
#include "ChaiVM/memory/allocator.hpp" | ||
#include "ChaiVM/memory/linear-buffer.hpp" | ||
#include "ChaiVM/utils/non-copyable.hpp" | ||
|
||
namespace chai::memory { | ||
|
||
template <class T> class LinearAllocator : IAllocator<T> { | ||
public: | ||
using value_type = T; | ||
|
||
explicit LinearAllocator(LinearBuffer &buffer) : buffer_(buffer) {} | ||
|
||
T *allocate(std::size_t n) override { | ||
if (n > (buffer_.size() - buffer_.offset()) / sizeof(T)) { | ||
throw std::bad_array_new_length(); | ||
} | ||
void *current = buffer_.currentPosition(); | ||
buffer_.shiftOffset(n * sizeof(T)); | ||
return reinterpret_cast<T *>(current); | ||
} | ||
#pragma GCC diagnostic push | ||
#pragma GCC diagnostic ignored "-Wunused-parameter" | ||
void deallocate(T *p, std::size_t n) override {} | ||
#pragma GCC diagnostic pop | ||
|
||
private: | ||
LinearBuffer &buffer_; | ||
}; | ||
|
||
} // namespace chai::memory |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
#pragma once | ||
|
||
#include <cstdlib> | ||
#include <iostream> | ||
|
||
#include "ChaiVM/utils/non-copyable.hpp" | ||
|
||
namespace chai::memory { | ||
|
||
class LinearBuffer final : public INonCopyable { | ||
public: | ||
explicit LinearBuffer(size_t sz); | ||
LinearBuffer(LinearBuffer &&other) noexcept; | ||
LinearBuffer &operator=(LinearBuffer &&other) noexcept; | ||
~LinearBuffer(); | ||
|
||
size_t size() const; | ||
size_t offset() const; | ||
void *currentPosition() const; | ||
void shiftOffset(size_t n); | ||
|
||
private: | ||
size_t size_ = 0; | ||
size_t offset_ = 0; | ||
char *buf_ = nullptr; | ||
}; | ||
|
||
} // namespace chai::memory |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,8 +1,10 @@ | ||
#pragma once | ||
|
||
class INonCopyable { | ||
protected: | ||
INonCopyable() {} | ||
|
||
public: | ||
INonCopyable(const INonCopyable &rhs) = delete; | ||
INonCopyable &operator=(const INonCopyable &rhs) = delete; | ||
virtual ~INonCopyable() = 0; | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,4 @@ | ||
set(DIRS interpreter utils) | ||
set(DIRS interpreter utils memory) | ||
foreach(DIR ${DIRS}) | ||
add_subdirectory(${DIR}) | ||
endforeach() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
add_library(chai_memory STATIC) | ||
target_sources(chai_memory PRIVATE | ||
./linear-buffer.cpp | ||
) | ||
target_link_libraries(chai_memory | ||
PRIVATE | ||
chai_include | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
#include "ChaiVM/memory/linear-buffer.hpp" | ||
|
||
namespace chai::memory { | ||
|
||
LinearBuffer::LinearBuffer(size_t sz) : size_(sz), buf_(new char[size_]) {} | ||
LinearBuffer::LinearBuffer(LinearBuffer &&other) noexcept { | ||
std::swap(size_, other.size_); | ||
std::swap(buf_, other.buf_); | ||
} | ||
LinearBuffer &LinearBuffer::operator=(LinearBuffer &&other) noexcept { | ||
std::swap(size_, other.size_); | ||
std::swap(buf_, other.buf_); | ||
return *this; | ||
} | ||
LinearBuffer::~LinearBuffer() { delete[] buf_; } | ||
|
||
size_t LinearBuffer::size() const { return size_; } | ||
size_t LinearBuffer::offset() const { return offset_; } | ||
void *LinearBuffer::currentPosition() const { return buf_ + offset_; } | ||
void LinearBuffer::shiftOffset(size_t n) { offset_ += n; } | ||
|
||
} // namespace chai::memory |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,3 @@ | ||
|
||
add_library(chai_utils STATIC) | ||
target_sources(chai_utils PRIVATE | ||
./instr2Raw.cpp | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,4 @@ | ||
set(DIRS interpreter utils) | ||
set(DIRS interpreter utils memory) | ||
foreach(DIR ${DIRS}) | ||
add_subdirectory(${DIR}) | ||
endforeach() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
chai_test(./linear-allocator-test.cpp) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,84 @@ | ||
#include "ChaiVM/memory/linear-allocator.hpp" | ||
#include <gtest/gtest.h> | ||
|
||
using namespace chai::memory; | ||
|
||
class LinearAllocatorTest : public ::testing::Test { | ||
protected: | ||
static constexpr size_t BUFFER_SIZE = 1024; | ||
LinearBuffer buffer_ = LinearBuffer(BUFFER_SIZE); | ||
}; | ||
|
||
class Stub { | ||
public: | ||
static constexpr int DFT = -1; | ||
explicit Stub(int num) : stub(num) {} | ||
Stub() {} | ||
int stub = DFT; | ||
}; | ||
|
||
TEST_F(LinearAllocatorTest, Primitives) { | ||
size_t n = 5; | ||
LinearAllocator<int> allocator{buffer_}; | ||
int *buf = allocator.allocate(n); | ||
int *arr = new (buf) int[n]; | ||
for (size_t i = 0; i < n; ++i) { | ||
arr[i] = i; | ||
} | ||
for (size_t i = 0; i < n; ++i) { | ||
EXPECT_EQ(arr[i], i); | ||
} | ||
} | ||
TEST_F(LinearAllocatorTest, Classes) { | ||
size_t n = 1; | ||
LinearAllocator<Stub> allocator{buffer_}; | ||
Stub *buf = allocator.allocate(n); | ||
Stub *inst = new (buf) Stub; | ||
inst->stub = 10; | ||
EXPECT_EQ(inst->stub, 10); | ||
inst->~Stub(); | ||
} | ||
TEST_F(LinearAllocatorTest, StdContainersDefault) { | ||
size_t n = 10; | ||
LinearAllocator<Stub> allocator{buffer_}; | ||
std::vector<Stub, decltype(allocator)> vec(n, allocator); | ||
for (auto &e : vec) { | ||
EXPECT_EQ(e.stub, Stub::DFT); | ||
} | ||
} | ||
TEST_F(LinearAllocatorTest, StdContainers) { | ||
size_t n = 10; | ||
LinearAllocator<Stub> allocator{buffer_}; | ||
std::vector<Stub, decltype(allocator)> vec(n, allocator); | ||
for (auto &e : vec) { | ||
e = Stub(42); | ||
} | ||
for (auto &e : vec) { | ||
EXPECT_EQ(e.stub, 42); | ||
} | ||
} | ||
|
||
TEST_F(LinearAllocatorTest, PrimitiveAllocation) { | ||
size_t n = 42; | ||
LinearAllocator<int> allocator{buffer_}; | ||
allocator.allocate(n); | ||
EXPECT_EQ(buffer_.offset(), n * sizeof(int)); | ||
} | ||
TEST_F(LinearAllocatorTest, ClassAllocation) { | ||
size_t n = 80; | ||
LinearAllocator<Stub> allocator{buffer_}; | ||
allocator.allocate(n); | ||
EXPECT_EQ(buffer_.offset(), n * sizeof(Stub)); | ||
} | ||
TEST_F(LinearAllocatorTest, StdContainersAllocation) { | ||
size_t n = 23; | ||
LinearAllocator<Stub> allocator{buffer_}; | ||
std::vector<Stub, decltype(allocator)> vec(n, allocator); | ||
EXPECT_EQ(buffer_.offset(), n * sizeof(Stub)); | ||
} | ||
|
||
TEST_F(LinearAllocatorTest, BadArrayNewLength) { | ||
size_t n = BUFFER_SIZE / sizeof(Stub) + 1; | ||
LinearAllocator<Stub> allocator{buffer_}; | ||
EXPECT_THROW(allocator.allocate(n), std::bad_array_new_length); | ||
} |