Skip to content

Commit

Permalink
nop
Browse files Browse the repository at this point in the history
  • Loading branch information
Perchik71 committed Sep 26, 2024
1 parent db43234 commit 4e1bc8e
Show file tree
Hide file tree
Showing 12 changed files with 354 additions and 72 deletions.
2 changes: 1 addition & 1 deletion depends/vmm/source/vmapper.cpp
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Copyright Š 2024 aka perchik71. All rights reserved.
// Copyright © 2024 aka perchik71. All rights reserved.
// Contacts: <email:timencevaleksej@gmail.com>
// License: https://www.gnu.org/licenses/lgpl-3.0.html

Expand Down
68 changes: 34 additions & 34 deletions depends/vmm/source/vmapper.h
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Copyright © 2024 aka perchik71. All rights reserved.
// Copyright © 2024 aka perchik71. All rights reserved.
// Contacts: <email:timencevaleksej@gmail.com>
// License: https://www.gnu.org/licenses/lgpl-3.0.html

Expand All @@ -10,68 +10,68 @@ namespace voltek
{
namespace core
{
// Карта памяти, заранее зарезервированная, для конкретного пула,
// чтобы быстро получить нужную память для страницы.
// Факт: ускорение 2%... заброшено.
// Карта памяти, заранее зарезервированная, для конкретного пула,
// чтобы быстро получить нужную память для страницы.
// Факт: ускорение 2%... заброшено.
class mapper : public base
{
public:
// Размер по умолчанию.
// Размер по умолчанию.
inline static constexpr size_t DEFAULT_SIZE = 256 * 1024 * 1024;
// Размер одного блока по умолчанию.
// Размер одного блока по умолчанию.
inline static constexpr size_t DEFAULT_BLOCKSIZE = DEFAULT_SIZE / 65536;
// Конструктор по умолчанию.
// Конструктор по умолчанию.
mapper();
// Конструктор.
// В качестве параметра указывается желаемый размер в мб.
// И размер одного блока в байтах.
// Конструктор.
// В качестве параметра указывается желаемый размер в мб.
// И размер одного блока в байтах.
mapper(size_t size, size_t blocksize);
// Конструктор копий.
// Конструктор копий.
mapper(const bits& ob);
// Деструктор.
// Деструктор.
virtual ~mapper();
// Оператор присвоения
// Оператор присвоения
mapper& operator=(const mapper& ob);
// Функция возвращает если объект класса пуст и нет памяти.
// Функция возвращает если объект класса пуст и нет памяти.
inline bool empty() const { return !_size; }
// Освобождение памяти.
// Освобождение памяти.
inline void clear() { resize(0, 0); }
// Возвращает размер допустимой памяти.
// Возвращает размер допустимой памяти.
inline size_t size() const { return _size; }
// Возвращает размер свободной памяти.
// Возвращает размер свободной памяти.
inline size_t free_size() const { return _freesize; }
// Возвращает размер одного блока.
// Возвращает размер одного блока.
inline size_t block_size() const { return _blocksize; }
// Возвращает кол-во всего допустимых блоков.
// Возвращает кол-во всего допустимых блоков.
inline size_t count_blocks() const { return _size / _blocksize; }
// Возвращает кол-во свободных блоков.
// Возвращает кол-во свободных блоков.
inline size_t free_blocks() const { return _freesize / _blocksize; }
// Возвращает указатель на память, константа.
// Возвращает указатель на память, константа.
inline const char* c_data() const { return _mem; }
// Возвращает указатель на память, не константа.
// Возвращает указатель на память, не константа.
inline char* data() { return _mem; }
// Возвращает указатель на память свободного блока.
// Возвращает указатель на память свободного блока.
void* block_alloc();
// Освобождает память блока по указателю на память.
// Освобождает память блока по указателю на память.
bool block_free(const void* ptr);
private:
// Изменяет размер памяти.
// В качестве параметра указывается желаемый размер в байтах.
// Если указать 0, то будет освобождена память.
// И размер одного блока в байтах.
// Изменяет размер памяти.
// В качестве параметра указывается желаемый размер в байтах.
// Если указать 0, то будет освобождена память.
// И размер одного блока в байтах.
void resize(size_t size, size_t blocksize);
// Возвращает истину если указатель принадлежит классу.
// Возвращает истину если указатель принадлежит классу.
bool is_valid_ptr(const void* ptr) const;
private:
// Память.
// Память.
char* _mem;
// Допустимый размер.
// Допустимый размер.
size_t _size;
// Свободно.
// Свободно.
size_t _freesize;
// Размер одного блока.
// Размер одного блока.
size_t _blocksize;
// Битовая карта для быстрого поиска.
// Битовая карта для быстрого поиска.
bits* _mask;
};
}
Expand Down
57 changes: 29 additions & 28 deletions depends/vmm/source/vmmmain.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -30,34 +30,35 @@ namespace voltek

constexpr size_t MAX_BLOCK_SIZE = 128ull * 1024 * 1024;

typedef pool_t<block8_t> pool8_t;
typedef pool_t<block16_t> pool16_t;
typedef pool_t<block32_t> pool32_t;
typedef pool_t<block64_t> pool64_t;
typedef pool_t<block128_t> pool128_t;
typedef pool_t<block256_t> pool256_t;
typedef pool_t<block512_t> pool512_t;
typedef pool_t<block1024_t> pool1024_t;
typedef pool_t<block4096_t> pool4096_t;
typedef pool_t<block8192_t> pool8192_t;
typedef small_pool_t<block16384_t> pool16384_t;
typedef small_pool_t<block32768_t> pool32768_t;
typedef low_pool_t<block65536_t> pool65536_t;
typedef low_pool_t<block131072_t> pool131072_t;
typedef pool8_t::pageobj_t page8_t;
typedef pool16_t::pageobj_t page16_t;
typedef pool32_t::pageobj_t page32_t;
typedef pool64_t::pageobj_t page64_t;
typedef pool128_t::pageobj_t page128_t;
typedef pool256_t::pageobj_t page256_t;
typedef pool512_t::pageobj_t page512_t;
typedef pool1024_t::pageobj_t page1024_t;
typedef pool4096_t::pageobj_t page4096_t;
typedef pool8192_t::pageobj_t page8192_t;
typedef pool16384_t::pageobj_t page16384_t;
typedef pool32768_t::pageobj_t page32768_t;
typedef pool65536_t::pageobj_t page65536_t;
typedef pool131072_t::pageobj_t page131072_t;
typedef page_t<block8_t> page8_t;
typedef page_t<block16_t> page16_t;
typedef page_t<block32_t> page32_t;
typedef page_t<block64_t> page64_t;
typedef page_t<block128_t> page128_t;
typedef page_t<block256_t> page256_t;
typedef page_t<block512_t> page512_t;
typedef page_t<block1024_t> page1024_t;
typedef page_t<block4096_t> page4096_t;
typedef page_t<block8192_t> page8192_t;
typedef page_t<block16384_t, __VMM_PAGE_CONFIG_SMALL_SIZE> page16384_t;
typedef page_t<block32768_t, __VMM_PAGE_CONFIG_SMALL_SIZE> page32768_t;
typedef page_t<block65536_t, __VMM_PAGE_CONFIG_LOW_SIZE> page65536_t;
typedef page_t<block131072_t, __VMM_PAGE_CONFIG_LOW_SIZE> page131072_t;
typedef pool_t<block8_t, page8_t> pool8_t;
typedef pool_t<block16_t, page16_t> pool16_t;
typedef pool_t<block32_t, page32_t> pool32_t;
typedef pool_t<block64_t, page64_t> pool64_t;
typedef pool_t<block128_t, page128_t> pool128_t;
typedef pool_t<block256_t, page256_t> pool256_t;
typedef pool_t<block512_t, page512_t> pool512_t;
typedef pool_t<block1024_t, page1024_t> pool1024_t;
typedef pool_t<block4096_t, page4096_t> pool4096_t;
typedef pool_t<block8192_t, page8192_t> pool8192_t;
typedef pool_t<block16384_t, page16384_t, __VMM_POOL_CONFIG_SMALL_SIZE> pool16384_t;
typedef pool_t<block32768_t, page32768_t, __VMM_POOL_CONFIG_SMALL_SIZE> pool32768_t;
typedef pool_t<block65536_t, page65536_t, __VMM_POOL_CONFIG_LOW_SIZE> pool65536_t;
typedef pool_t<block131072_t, page131072_t, __VMM_POOL_CONFIG_LOW_SIZE> pool131072_t;


// Проверка на допустимость памяти
// Только Windows: Если произошло исключение, то вернёт false, иначе true.
Expand Down
137 changes: 135 additions & 2 deletions depends/vmm/source/vmmpage.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,11 @@
#include "vassert.h"
#include "vmapper.h"
#include "vio.h"
#include "vstack.h"

#define __VMM_PAGE_CONFIG_NORMAL_SIZE voltek::core::bits_regions
#define __VMM_PAGE_CONFIG_SMALL_SIZE voltek::core::bits
#define __VMM_PAGE_CONFIG_LOW_SIZE __VMM_PAGE_CONFIG_SMALL_SIZE

namespace voltek
{
Expand All @@ -17,7 +22,7 @@ namespace voltek
// Является хранилищем блоков, но при этом нет жёсткой зависимости от каких блоков.
// Служит только в качестве помечания свободный или занятый блок, а также быстрого
// нахождения свободного блока, при помощи битовой карты.
template<typename _type, typename _map = voltek::core::bits_regions, size_t _blocks_in_page = 64ull * 1024>
template<typename _type, typename _map = __VMM_PAGE_CONFIG_NORMAL_SIZE>
class page_t : public voltek::core::base
{
public:
Expand Down Expand Up @@ -128,7 +133,7 @@ namespace voltek
{
#ifndef VMMDLL_EXPORTS
voltek::core::_internal::memory_to_file(filename, (void*)_blocks,
voltek::core::_internal::aligned_msize(_blocks), _blocks_in_page >> 3);
voltek::core::_internal::aligned_msize(_blocks), _size >> 3);
#endif // !VMMDLL_EXPORTS
}
private:
Expand All @@ -154,5 +159,133 @@ namespace voltek
voltek::core::mapper* _mapper;
#endif
};


// Шаблонный класс страницы памяти (на базе стека)
// Является хранилищем блоков, но при этом нет жёсткой зависимости от каких блоков.
// Служит только в качестве помечания свободный или занятый блок, а также быстрого
// нахождения свободного блока, при помощи битовой карты.
template<typename _type, typename _map = __VMM_PAGE_CONFIG_NORMAL_SIZE>
class page2_t : public voltek::core::base
{
public:
// Конструктор по умолчанию.
page2_t() : _blocks(nullptr), _size(0), _user_data(0)
{}
// Конструктор.
// Внимание размер будет округлён до кратности 256.
page2_t(size_t new_size) : _blocks(nullptr), _size(0), _user_data(0)
{
set_size(new_size);
}
// Деструктор
virtual ~page2_t()
{
if (_blocks)
{
voltek::core::_internal::aligned_free(_blocks);

_blocks = nullptr;
_size = 0;
}
}
// Задаёт размер страницы.
// Одноразовая, не для расширения страницы.
// Внимание размер будет округлён до кратности 256.
void set_size(size_t new_size)
{
// Число должно быть кратное 256, округляем в меньшую сторону.
// Это необходимо, учитывая, что bits_regions размер минимум от 65536.
// Использование SIMD инструкций является приоритетом, а "хвоста" должно
// быть немного, а лучше небыло вовсе.
new_size = (new_size << 8) >> 8;

_stack.clear();
_stack.resize(new_size);
_blocks = voltek::core::_internal::aligned_talloc<_type>(new_size, 0x10);

if (!_blocks)
{
_stack.clear();
_vassert(!_blocks);
}
else
{
_size = new_size;
// Заполняем стек указателями на свободные блоки.
_stack.push_array(_blocks, _size);
}
}
// Возвращает допольнительную информацию, что привязана к странице.
inline uintptr_t get_user_data() const { return _user_data; }
// Устанавливает дополнительную информацию к странице.
inline void set_user_data(uintptr_t user_data) { _user_data = user_data; }
// Возвращает истину, если страница не инициализирована.
inline bool empty() const { return !_size; }
// Возвращает истину, если все блоки свободны.
inline bool is_all_blocks_free() const { return _stack.overflowing(); }
// Возвращает истину, если все блоки заняты.
inline bool is_all_blocks_busy() const { return _stack.empty(); }
// Помечает, что данный блок за указанным индексом - свободен.
inline bool set_block_free(size_t index)
{
if (index >= _size) return false;
_stack.push((_type*)(((char*)_blocks) + (index * (sizeof(_type)))));
return true;
}
// Помечает, что данный блок за указанным индексом - занят.
inline bool set_block_busy(size_t index)
{
// Нет возможности это сделать.
return true;
}
// Возвращает истину, в случае, нахождения первого попавшегося свободного блока.
// Его индекс будет передан в "index".
inline bool get_first_free_block_index(size_t& index)
{
if (_stack.empty()) return false;
auto addr = _stack.pop();
index = ((size_t)(addr - _blocks)) / sizeof(_type);
return true;
}
// Возвращает кол-во допустимых блоков.
inline size_t count() const { return _size; }
// Возвращает кол-во свободных блоков.
inline size_t free_count() const { return _stack.empty() ? 0 : _stack.caret(); }
// Возвращает кол-во знятых блоков.
inline size_t busy_count() const { return _stack.empty() ? _size : _size - _stack.caret(); }
// Возвращает блок за указанным индексом. Константа.
inline const _type c_at(size_t index) const { return _blocks[index]; }
// Возвращает блок за указанным индексом.
inline _type& at(size_t index) { return _blocks[index]; }
// Оператор обращения к объекту класса в качестве массива.
// Возвращает блок за указанным индексом. Константа.
inline const _type operator[](size_t index) const { return c_at(index); }
// Оператор обращения к объекту класса в качестве массива.
// Возвращает блок за указанным индексом.
inline _type& operator[](size_t index) { return at(index); }
// Вывод дампа битовой карты страницы в файл.
inline void dump_map(const char* filename) const {}
// Вывод дампа памяти страницы в файл.
void dump(const char* filename) const {}
private:
// Конструктор копий - НЕДОСТУПЕН.
// Страница одна и уникальна.
page2_t(const page2_t& page) : _blocks(nullptr), _size(0), _user_data(0)
{}
// Оператор присвоения - НЕДОСТУПЕН.
// Страница одна и уникальна.
page2_t& operator=(const page2_t& page)
{}
private:
// Блоки.
_type* _blocks;
// Кол-во доступных блоков.
size_t _size;
// Дополнительная информация.
uintptr_t _user_data;
// Стек.
core::stack<_type> _stack;
};
}
}
13 changes: 6 additions & 7 deletions depends/vmm/source/vmmpool.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,17 +6,21 @@

#include "vmmpage.h"

#define __VMM_POOL_CONFIG_NORMAL_SIZE 64ull * 1024
#define __VMM_POOL_CONFIG_SMALL_SIZE 4ull * 1024
#define __VMM_POOL_CONFIG_LOW_SIZE 2ull * 1024

namespace voltek
{
namespace memory_manager
{
// Шаблонный класс пула страниц памяти.
template<typename _type, typename _blocks_map = voltek::core::bits_regions, size_t _blocks_in_page = 64ull * 1024>
template<typename _type, typename _page, size_t _blocks_in_page = __VMM_POOL_CONFIG_NORMAL_SIZE>
class pool_t : public voltek::core::base
{
public:
// Тип страницы.
using pageobj_t = page_t<_type, _blocks_map, _blocks_in_page>;
using pageobj_t = _page;
// Тип указателя на страницу.
using pageptr_t = pageobj_t*;
// Конструктор по умолчанию.
Expand Down Expand Up @@ -239,10 +243,5 @@ namespace voltek
voltek::core::mapper* _mapper;
#endif
};

template<typename _type, typename _blocks_map = voltek::core::bits, size_t _blocks_in_page = 4ull * 1024>
using small_pool_t = pool_t<_type, _blocks_map, _blocks_in_page>;
template<typename _type, typename _blocks_map = voltek::core::bits, size_t _blocks_in_page = 2ull * 1024>
using low_pool_t = pool_t<_type, _blocks_map, _blocks_in_page>;
}
}
Loading

0 comments on commit 4e1bc8e

Please sign in to comment.