KLDR done (i think)

This commit is contained in:
Shr3dd3r 2023-08-19 21:42:21 +03:00
parent c3d4762213
commit 786460d41b
10 changed files with 512 additions and 1 deletions

34
Makefile Normal file
View File

@ -0,0 +1,34 @@
# libstadium makefile
CC = g++
CFLAGS_DEFAULT = -Wall -Wpedantic -Wno-uninitialized -std=c++23 -static-libgcc -static-libstdc++ -static
CFLAGS_DEBUG = -Og -fanalyzer -ggdb
CFLAGS_RELEASE = -Ofast -fdevirtualize-speculatively -fdata-sections -ffunction-sections -Wl,-gc-sections -Wl,-strip-all -Wl,-strip-discarded -flto -s
SOURCES = src/stadium.hpp src/stadium.cpp src/kldr.hpp
SOURCES_TEST = src/test.cpp
#LINKED_LIBS = -l
OUTPUT_LIB = libstadium.so
OUTPUT_TEST_BIN = libstadiumtest
default: clean debug_test
debug_test: $(SOURCES) $(SOURCES_TEST)
$(CC) $(CFLAGS_DEFAULT) $(CFLAGS_DEBUG) $(SOURCES) $(SOURCES_TEST) -o $(OUTPUT_TEST_BIN)
#$(LINKED_LIBS)
debug: $(SOURCES)
echo "NYI"
release_test: $(SOURCES)
echo "NYI"
release: $(SOURCES)
echo "NYI"
clean:
rm -f $(OUTPUT_LIB)
rm -f $(OUTPUT_TEST_BIN)

View File

@ -3,3 +3,8 @@
_Эталонная имплементация библиотеки с реализацией протокола Stadium на языке C++._ _Эталонная имплементация библиотеки с реализацией протокола Stadium на языке C++._
**В процессе активной разработки!/Under active development!** **В процессе активной разработки!/Under active development!**
## Пространства имён
`Stadium::Base`: базовые инструменты, не подлежащие принципиальному изменению в будущем.

102
src/_trash/kldr.cpp Normal file
View File

@ -0,0 +1,102 @@
/*
* kldr.cpp
* Copyright (c) 2023 Cyclone Team. Licensed under GNU GPLv3-only terms.
*
*/
#include "kldr.hpp"
namespace Stadium {
namespace Base {
// Destructor
template <typename KeyT, typename LengthT>
KLDRArray<KeyT, LengthT>::~KLDRArray () {
// Freeing all pointers if vector is not empty
for (size_t i = 0; i < this->Values.size(); i++) {
operator delete(this->Values[i]);
}
}
// Print all contents of array to stdout
template <typename KeyT, typename LengthT>
void KLDRArray<KeyT, LengthT>::Print () {
for (size_t i = 0; i < this->Keys.size(); i++) {
std::cout << "Key: " << std::hex << std::setw(sizeof(KeyT) * 2) << this->Keys[i] << "; ";
std::cout << "Length: " << std::dec << this->Lengths[i] << "; ";
std::cout << "Value: " << std::hex << std::setfill('0') << std::setw(2);
for (LengthT j = 0; j < this->Lengths[i]; j++)
std::cout << this->Values[j] << " ";
std::cout << std::dec << std::endl;
}
}
// Add new cell to array
template <typename KeyT, typename LengthT>
void KLDRArray<KeyT, LengthT>::Add (KeyT key, LengthT length, void* data) {
this->Keys.push_back(key);
this->Lengths.push_back(length);
void* newData = operator new(length); // Yes, allocating memory for void pointer really looks like this
std::copy(data, data + length, newData); // ATTENTION: may be we should not copy, but rather use pointer to already allocated mem
this->Values.push_back(std::move(newData)); // NOTICE: move or not to move...
// NOTICE: there is `std::is_pod<SomeType>()`, so may be we can use one more template to make this a little more safe
}
// Get just value from array by key
template <typename KeyT, typename LengthT>
void* KLDRArray<KeyT, LengthT>::Get (KeyT key) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
return this->Values[i];
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Get value and length from array by key
template <typename KeyT, typename LengthT>
void* KLDRArray<KeyT, LengthT>::Get (KeyT key, LengthT* length) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
*length = this->Lengths[i];
return this->Values[i];
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Delete cell from array by key
template <typename KeyT, typename LengthT>
void KLDRArray<KeyT, LengthT>::Del (KeyT key) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
this->Keys.erase(this->Keys.begin() + i);
this->Lengths.erase(this->Lengths.begin() + i);
this->Values.erase(this->Values.begin() + i);
return;
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Shuffle array
template <typename KeyT, typename LengthT>
void KLDRArray<KeyT, LengthT>::Shuffle () {
std::random_device seed;
std::mt19937 gen{seed()};
std::uniform_int_distribution<size_t> dist{0, this->Keys.size()};
size_t pickedIndex = 0;
for (size_t i = 0; i < this->Keys.size(); i++) {
do
pickedIndex = dist(gen);
while (pickedIndex == i);
std::swap(this->Keys[i], this->Keys[pickedIndex]);
std::swap(this->Lengths[i], this->Length[pickedIndex]);
std::swap(this->Values[i], this->Values[pickedIndex]);
}
}
}
}

128
src/_trash/kldr.hpp Normal file
View File

@ -0,0 +1,128 @@
/*
* kldr.hpp
* Copyright (c) 2023 Cyclone Team. Licensed under GNU GPLv3-only terms.
*
*/
#ifndef LIBSTADIUM_KLDR_HPP
#define LIBSTADIUM_KLDR_HPP
#include <cstdio>
#include <iomanip>
#include <vector>
#include <random>
#include <exception>
namespace Stadium {
namespace Base {
// NOTICE: This can be more optimized
template <typename KeyT = uint8_t, typename LengthT = uint16_t>
class KLDRArray {
protected:
std::vector<KeyT> Keys;
std::vector<LengthT> Lengths;
std::vector<void*> Values; // We should use void* as it is more abstract, BUT! Then we need to deal with schizophrenical errors, like segfault when valid void pointer is freed
public:
//KLDRArray (); // TODO: check used types
// Destructor
~KLDRArray () {
// Freeing all pointers if vector is not empty
for (size_t i = 0; i < this->Keys.size(); i++) {
operator delete(this->Values[i]);
}
}
// Print all contents of array to stdout
void Print () {
printf("Elements amount: %lu\n", this->Keys.size());
for (size_t i = 0; i < this->Keys.size(); i++) {
printf("Key: 0x%.2X; ", (KeyT)this->Keys[i]);
printf("Length: %u; ", (LengthT)this->Lengths[i]);
printf("Value: ");
for (LengthT j = 0; j < this->Lengths[i]; j++)
printf("%.2X ", ((uint8_t*)this->Values[i])[j]);
printf("\n");
// std::cout << "Key: " << std::hex << std::setw(sizeof(KeyT) * 2) << this->Keys[i] << "; ";
// std::cout << "Length: " << std::dec << this->Lengths[i] << "; ";
// std::cout << "Value: " << std::hex;
// for (LengthT j = 0; j < this->Lengths[i]; j++)
// std::cout << std::setfill('0') << std::setw(2) << this->Values[j] << " ";
// std::cout << std::dec << std::endl;
}
}
// Add new cell to array
// WARNING: pointer supplied as "data" may be invalid after this function call
void Add (KeyT key, LengthT length, void* data) {
this->Keys.push_back(key);
this->Lengths.push_back(length);
//void* newData = operator new(length); // Yes, allocating memory for void pointer really looks like this
//std::copy(data, data + length, newData);
this->Values.push_back(std::move(data)); // NOTICE: move or not to move...
// NOTICE: there is `std::is_pod<SomeType>()`, so may be we can use one more template to make this a little more safe
}
// Get just value from array by key
void* Get (KeyT key) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
return this->Values[i];
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Get value and length from array by key
void* Get (KeyT key, LengthT* length) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
*length = this->Lengths[i];
return this->Values[i];
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Delete cell from array by key
void Del (KeyT key) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
this->Keys.erase(this->Keys.begin() + i);
this->Lengths.erase(this->Lengths.begin() + i);
this->Values.erase(this->Values.begin() + i);
return;
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Shuffle array
void Shuffle () {
std::random_device seed;
std::mt19937 gen{seed()};
std::uniform_int_distribution<size_t> dist{0, this->Keys.size()};
size_t pickedIndex = 0;
for (size_t i = 0; i < this->Keys.size(); i++) {
do
pickedIndex = dist(gen);
while (pickedIndex == i);
std::swap(this->Keys[i], this->Keys[pickedIndex]);
std::swap(this->Lengths[i], this->Length[pickedIndex]);
std::swap(this->Values[i], this->Values[pickedIndex]);
}
}
};
}
}
#endif

10
src/event.cpp Normal file
View File

@ -0,0 +1,10 @@
/*
* event.cpp
* Copyright (c) 2023 Cyclone Team. Licensed under GNU GPLv3-only terms.
*
*/
#include "event.hpp"

32
src/event.hpp Normal file
View File

@ -0,0 +1,32 @@
/*
* event.hpp
* Copyright (c) 2023 Cyclone Team. Licensed under GNU GPLv3-only terms.
*
*/
#ifndef LIBSTADIUM_EVENT_HPP
#define LIBSTADIUM_EVENT_HPP
namespace Stadium {
namespace Base {
template <typename CategoryT = uint8_t, typename SubcategoryT = uint8_t>
class Event {
public:
struct {
CategoryT Category;
SubcategoryT Subcategory;
} Type; // ???
uint32_t ServerSession;
// TODO: payload hash
// TODO: payload
};
}
}
#endif

131
src/kldr.hpp Normal file
View File

@ -0,0 +1,131 @@
/*
* kldr.hpp
* Copyright (c) 2023 Cyclone Team. Licensed under GNU GPLv3-only terms.
*
*/
#ifndef LIBSTADIUM_KLDR_HPP
#define LIBSTADIUM_KLDR_HPP
#include <cstdio>
#include <iomanip>
#include <vector>
#include <random>
#include <exception>
namespace Stadium {
namespace Base {
// NOTICE: This can be more optimized
template <typename KeyT = uint8_t, typename LengthT = uint16_t>
class KLDRArray {
protected:
std::vector<KeyT> Keys;
std::vector<LengthT> Lengths;
std::vector<void*> Values;
public:
//KLDRArray (); // TODO: check used types
// Destructor
~KLDRArray () {
// Freeing all pointers if vector is not empty
for (size_t i = 0; i < this->Keys.size(); i++) {
operator delete(this->Values[i]);
}
}
// Print all contents of array to stdout
void Print () {
printf("Elements amount: %lu\n", this->Keys.size());
for (size_t i = 0; i < this->Keys.size(); i++) {
printf("Key: 0x%.2X; ", (KeyT)this->Keys[i]);
printf("Length: %u; ", (LengthT)this->Lengths[i]);
printf("Value: ");
for (LengthT j = 0; j < this->Lengths[i]; j++)
printf("%.2X ", ((uint8_t*)this->Values[i])[j]);
printf("\n");
}
}
// Add new cell to array, fast version without keys check
void AddF (KeyT key, LengthT length, void* data) {
this->Keys.push_back(key);
this->Lengths.push_back(length);
void* newData = operator new(length); // Yes, allocating memory for void pointer really looks like this
std::copy((uint8_t*)data, (uint8_t*)data + length, (uint8_t*)newData); // Dirty hacks, YES!
this->Values.push_back(newData);
// NOTICE: there is `std::is_pod<SomeType>()`, so may be we can use one more template to make this a little more safe (may be)
}
void Add (KeyT key, LengthT length, void* data) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
throw std::invalid_argument("supplied key already exist");
}
}
this->AddF(key, length, data);
}
// Get just value from array by key
void* Get (KeyT key) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
return this->Values[i];
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Get value and length from array by key
void* Get (KeyT key, LengthT* length) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
*length = this->Lengths[i];
return this->Values[i];
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Delete cell from array by key
void Del (KeyT key) {
for (size_t i = 0; i < this->Keys.size(); i++) {
if (this->Keys[i] == key) {
this->Keys.erase(this->Keys.begin() + i);
this->Lengths.erase(this->Lengths.begin() + i);
this->Values.erase(this->Values.begin() + i);
return;
}
}
throw std::invalid_argument("invalid KLDRArray key");
}
// Shuffle array
void Shuffle () {
size_t elements = this->Keys.size();
std::random_device seed;
std::mt19937 gen{seed()};
std::uniform_int_distribution<size_t> dist{0, elements-1};
size_t pickedIndex = 0;
for (size_t i = 0; i < elements; i++) {
do
pickedIndex = dist(gen);
while (pickedIndex == i);
std::swap(this->Keys[i], this->Keys[pickedIndex]);
std::swap(this->Lengths[i], this->Lengths[pickedIndex]);
std::swap(this->Values[i], this->Values[pickedIndex]);
}
}
};
}
}
#endif

17
src/stadium.cpp Normal file
View File

@ -0,0 +1,17 @@
/*
* stadium.cpp
* Copyright (c) 2023 Cyclone Team. Licensed under GNU GPLv3-only terms.
*
* -> [ Incoming Events Queue ] --> [ Base Event Handlers ]
* / \-> [ Custom Event Handlers ]
* [ Transport ] <-> [ StadiumCrypto (optional) ] <- -> [ Expected Event Handlers ]
* \
* <- [ Outcoming Events Queue ] <--- [ Base Methods ]
* \
* <- [ Custom Methods ]
*/
#include "stadium.hpp"

30
src/stadium.hpp Normal file
View File

@ -0,0 +1,30 @@
/*
* stadium.hpp
* Copyright (c) 2023 Cyclone Team. Licensed under GNU GPLv3-only terms.
*
*/
#ifndef LIBSTADIUM_HPP
#define LIBSTADIUM_HPP
#include "kldr.hpp"
namespace Stadium {
namespace v1 {
// class EventsQueue {
// public:
// void Add (); // TODO
// void Pop (); // TODO
// };
}
}
#endif

22
src/test.cpp Normal file
View File

@ -0,0 +1,22 @@
#include <cstdio>
#include "stadium.hpp"
int main () {
Stadium::Base::KLDRArray<> arr;
char str1[] = "goodbye, var?\n";
char str2[] = "hello, world!\n";
char str3[] = "fisting\n";
char str4[] = "IS 300$!!!!!!!!!!!!!!!!!!\n";
char str5[] = "a)\n";
arr.Add(0x01, sizeof(str1), (void*)&str1);
arr.Add(0x02, sizeof(str2), (void*)&str2);
arr.Add(0xF4, sizeof(str3), (void*)&str3);
arr.Add(0x6a, sizeof(str4), (void*)&str4);
arr.Add(0x6c, sizeof(str5), (void*)&str5);
arr.Print();
arr.Shuffle();
arr.Print();
return 0;
}