Merge branch 'dev' into 'master'
Sprint - Unit Tests sind cool See merge request link/projekte/ws19/vkvm-new/library!4
This commit is contained in:
commit
0e24f7db35
@ -1,3 +1,3 @@
|
|||||||
Checks: '*,-llvm-header-guard,-fuchsia*,-cppcoreguidelines-pro-bounds-pointer-arithmetic,-cppcoreguidelines-pro-bounds-constant-array-index,-bugprone-narrowing-conversions,-cppcoreguidelines-narrowing-conversions,-cppcoreguidelines-pro-type-const-cast,-cppcoreguidelines-pro-type-reinterpret-cast,-hicpp-signed-bitwise,-bugprone-exception-escape,-cppcoreguidelines-pro-type-member-init,-cppcoreguidelines-pro-type-cstyle-cast,-hicpp-member-init,-google-readability-namespace-comments,-llvm-namespace-comment,-cppcoreguidelines-pro-type-vararg,-hicpp-vararg,-modernize-use-trailing-return-type'
|
Checks: '*,-llvm-header-guard,-fuchsia*,-cppcoreguidelines-pro-bounds-pointer-arithmetic,-cppcoreguidelines-pro-bounds-constant-array-index,-bugprone-narrowing-conversions,-cppcoreguidelines-narrowing-conversions,-cppcoreguidelines-pro-type-const-cast,-cppcoreguidelines-pro-type-reinterpret-cast,-hicpp-signed-bitwise,-bugprone-exception-escape,-cppcoreguidelines-pro-type-member-init,-cppcoreguidelines-pro-type-cstyle-cast,-hicpp-member-init,-google-readability-namespace-comments,-llvm-namespace-comment,-cppcoreguidelines-pro-type-vararg,-hicpp-vararg,-modernize-use-trailing-return-type,-readability-magic-numbers,-cppcoreguidelines-avoid-magic-numbers'
|
||||||
WarningsAsErrors: 'true'
|
WarningsAsErrors: 'true'
|
||||||
HeaderFilterRegex: '.*,-catch.hpp'
|
HeaderFilterRegex: '.*,-catch.hpp'
|
@ -40,3 +40,12 @@ target_link_libraries(UnitTests Catch2::Catch2)
|
|||||||
include(CTest)
|
include(CTest)
|
||||||
include(Catch)
|
include(Catch)
|
||||||
catch_discover_tests(UnitTests)
|
catch_discover_tests(UnitTests)
|
||||||
|
|
||||||
|
if (ENABLE_COVERAGE)
|
||||||
|
set(CMAKE_MODULE_PATH "${CMAKE_SOURCE_DIR}/../external/codecov/cmake" ${CMAKE_MODULE_PATH})
|
||||||
|
list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_LIST_DIR}/CMake")
|
||||||
|
find_package(codecov)
|
||||||
|
add_coverage(UnitTests)
|
||||||
|
list(APPEND LCOV_REMOVE_PATTERNS "/usr/")
|
||||||
|
coverage_evaluate()
|
||||||
|
endif()
|
||||||
|
@ -2,16 +2,21 @@
|
|||||||
|
|
||||||
namespace vkvm {
|
namespace vkvm {
|
||||||
|
|
||||||
|
constexpr int maxValue = 255;
|
||||||
|
|
||||||
Color::Color() noexcept
|
Color::Color() noexcept
|
||||||
: red(0), green(0), blue(0) {}
|
: red(0), green(0), blue(0) {}
|
||||||
|
|
||||||
Color::Color(unsigned char red, unsigned char green, unsigned char blue) noexcept
|
Color::Color(int red, int green, int blue) noexcept {
|
||||||
: red(red), green(green), blue(blue) {}
|
setRed(red);
|
||||||
|
setGreen(green);
|
||||||
|
setBlue(blue);
|
||||||
|
}
|
||||||
|
|
||||||
Color::Color(unsigned int hex) noexcept {
|
Color::Color(unsigned int hex) noexcept {
|
||||||
red = (unsigned char) ((hex >> 16 & 0xFF));//NOLINT
|
red = static_cast<unsigned char>(hex >> 16 & 0xFF);
|
||||||
green = (unsigned char) ((hex >> 8u & 0xFF));//NOLINT
|
green = static_cast<unsigned char>(hex >> 8U & 0xFF);
|
||||||
blue = (unsigned char) ((hex & 0xFF));//NOLINT
|
blue = static_cast<unsigned char>((hex & 0xFF));
|
||||||
}
|
}
|
||||||
|
|
||||||
auto Color::getRed() -> unsigned char {
|
auto Color::getRed() -> unsigned char {
|
||||||
@ -26,15 +31,27 @@ namespace vkvm {
|
|||||||
return blue;
|
return blue;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto Color::setRed(unsigned char value) -> void {
|
auto Color::setRed(int value) -> void {
|
||||||
|
if(value > maxValue) {
|
||||||
|
value = maxValue;
|
||||||
|
}
|
||||||
|
|
||||||
red = value;
|
red = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto Color::setGreen(unsigned char value) -> void {
|
auto Color::setGreen(int value) -> void {
|
||||||
|
if(value > maxValue) {
|
||||||
|
value = maxValue;
|
||||||
|
}
|
||||||
|
|
||||||
green = value;
|
green = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto Color::setBlue(unsigned char value) -> void {
|
auto Color::setBlue(int value) -> void {
|
||||||
|
if(value > maxValue) {
|
||||||
|
value = maxValue;
|
||||||
|
}
|
||||||
|
|
||||||
blue = value;
|
blue = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -18,7 +18,7 @@ namespace vkvm {
|
|||||||
public:
|
public:
|
||||||
Color() noexcept;
|
Color() noexcept;
|
||||||
|
|
||||||
Color(unsigned char red, unsigned char green, unsigned char blue) noexcept;
|
Color(int red, int green, int blue) noexcept;
|
||||||
|
|
||||||
explicit Color(unsigned int hex) noexcept;
|
explicit Color(unsigned int hex) noexcept;
|
||||||
|
|
||||||
@ -28,11 +28,11 @@ namespace vkvm {
|
|||||||
|
|
||||||
auto getBlue() -> unsigned char;
|
auto getBlue() -> unsigned char;
|
||||||
|
|
||||||
auto setRed(unsigned char value) -> void;
|
auto setRed(int value) -> void;
|
||||||
|
|
||||||
auto setGreen(unsigned char value) -> void;
|
auto setGreen(int value) -> void;
|
||||||
|
|
||||||
auto setBlue(unsigned char value) -> void;
|
auto setBlue(int value) -> void;
|
||||||
|
|
||||||
bool operator==(const Color &other) const ;
|
bool operator==(const Color &other) const ;
|
||||||
|
|
||||||
|
@ -1,24 +0,0 @@
|
|||||||
#include "FontType.hpp"
|
|
||||||
|
|
||||||
namespace vkvm {
|
|
||||||
|
|
||||||
FontType::FontType(int id, const char * name, int height, int width) noexcept : id(id), name(name), height(height), width(width) {
|
|
||||||
}
|
|
||||||
|
|
||||||
auto FontType::getId() const -> int {
|
|
||||||
return id;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto FontType::getName() const -> std::string {
|
|
||||||
return std::string(name);
|
|
||||||
}
|
|
||||||
|
|
||||||
auto FontType::getHeight() const -> int {
|
|
||||||
return height;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto FontType::getWidth() const -> int {
|
|
||||||
return width;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -2,32 +2,15 @@
|
|||||||
|
|
||||||
#define LIBRARY_FONT_H
|
#define LIBRARY_FONT_H
|
||||||
|
|
||||||
#include <string>
|
|
||||||
#include <utility>
|
|
||||||
|
|
||||||
namespace vkvm {
|
namespace vkvm {
|
||||||
|
|
||||||
class FontType {
|
enum FontType {
|
||||||
private:
|
FuturisticBlack = 1,
|
||||||
int id;
|
//TODO(julian): find name of this font
|
||||||
const char * name;
|
NoNameFound = 2,
|
||||||
int height;
|
ProFontIIX = 3,
|
||||||
int width;
|
Unifont = 4
|
||||||
|
|
||||||
public:
|
|
||||||
FontType(int id, const char * name, int height, int width) noexcept;
|
|
||||||
|
|
||||||
auto getId() const -> int;
|
|
||||||
|
|
||||||
auto getName() const -> std::string;
|
|
||||||
|
|
||||||
auto getHeight() const -> int;
|
|
||||||
|
|
||||||
auto getWidth() const -> int;
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
static const FontType font_1 = FontType(1, "DummyFont", 10, 5);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -1,14 +1,17 @@
|
|||||||
#ifndef LIBRARY_KEYCODE_HPP
|
#ifndef LIBRARY_KEYCODE_HPP
|
||||||
#define LIBRARY_KEYCODE_HPP
|
#define LIBRARY_KEYCODE_HPP
|
||||||
|
|
||||||
#include <sys/types.h>
|
|
||||||
|
|
||||||
namespace vkvm {
|
namespace vkvm {
|
||||||
|
|
||||||
enum KeyCode {
|
enum KeyCode {
|
||||||
Backspcce = 32,
|
Backspace = 32,
|
||||||
Tab = 33,
|
Tab = 33,
|
||||||
Enter = 37,
|
Enter = 37,
|
||||||
|
Arrow_Left = 105,
|
||||||
|
Arrow_Down = 108,
|
||||||
|
Arrow_Right = 107,
|
||||||
|
Arrow_Up = 106,
|
||||||
ShiftLeft = 249,
|
ShiftLeft = 249,
|
||||||
ShiftRight = 249,
|
ShiftRight = 249,
|
||||||
Ctrl = 251,
|
Ctrl = 251,
|
||||||
|
@ -1,30 +1,24 @@
|
|||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
#include <cstdlib>
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <iostream>
|
|
||||||
#include <sys/ipc.h>
|
#include <sys/ipc.h>
|
||||||
#include <sys/sem.h>
|
#include <sys/sem.h>
|
||||||
#include <sys/shm.h>
|
#include <sys/shm.h>
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <unistd.h>
|
|
||||||
|
|
||||||
#include "SharedMemoryAccess.hpp" /* header is important for the shmID. name could be different. maybe not needed cause: (shmget(memory_access_key, NULL, 0)) */
|
#include "SharedMemoryAccess.hpp"
|
||||||
#include "internal.hpp"
|
#include "internal.hpp"
|
||||||
#include "log.hpp"
|
#include "log.hpp"
|
||||||
|
|
||||||
namespace vkvm {
|
namespace vkvm {
|
||||||
constexpr int PERM = 0666; /* access rights */
|
constexpr int PERMISSION = 0666;
|
||||||
constexpr int LOCK = -1;
|
constexpr int LOCK = -1;
|
||||||
constexpr int UNLOCK = 1;
|
constexpr int UNLOCK = 1;
|
||||||
constexpr int SEM_KEY = 123458L;
|
constexpr int SEM_KEY = 123458L;
|
||||||
|
|
||||||
//int memoryAccessKey; /* var type is int. but could be another type. */ //TODO: look after type in sharedmemory group
|
|
||||||
int semId;
|
int semId;
|
||||||
struct sembuf semaphore;
|
struct sembuf semaphore;
|
||||||
|
|
||||||
std::vector<char> localSharedMemory;
|
|
||||||
|
|
||||||
auto initSemaphore() -> int {
|
auto initSemaphore() -> int {
|
||||||
/* Testen, ob das Semaphor bereits existiert */
|
/* Testen, ob das Semaphor bereits existiert */
|
||||||
semId = semget(SEM_KEY, 0, IPC_PRIVATE);
|
semId = semget(SEM_KEY, 0, IPC_PRIVATE);
|
||||||
@ -33,7 +27,7 @@ namespace vkvm {
|
|||||||
/* Alle Zugriffsrechte der Dateikreierungsmaske */
|
/* Alle Zugriffsrechte der Dateikreierungsmaske */
|
||||||
/* erlauben */
|
/* erlauben */
|
||||||
umask(0);
|
umask(0);
|
||||||
semId = semget(SEM_KEY, 1, IPC_CREAT | IPC_EXCL | PERM);
|
semId = semget(SEM_KEY, 1, IPC_CREAT | IPC_EXCL | PERMISSION);
|
||||||
if (semId < 0) {
|
if (semId < 0) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
@ -50,6 +44,7 @@ namespace vkvm {
|
|||||||
semaphore.sem_flg = SEM_UNDO;
|
semaphore.sem_flg = SEM_UNDO;
|
||||||
if (semop(semId, &semaphore, 1) == -1) {
|
if (semop(semId, &semaphore, 1) == -1) {
|
||||||
perror(" semop ");
|
perror(" semop ");
|
||||||
|
log(LogLevel::CRITICAL, "could not operate on semaphore, exiting");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
return 1;
|
return 1;
|
||||||
@ -67,11 +62,11 @@ namespace vkvm {
|
|||||||
givenWarning = true;
|
givenWarning = true;
|
||||||
log(LogLevel::WARNING, "no shared memory found, using local memory instead!");
|
log(LogLevel::WARNING, "no shared memory found, using local memory instead!");
|
||||||
}
|
}
|
||||||
if (localSharedMemory.empty()) {
|
if (impl.localSharedMemory.empty()) {
|
||||||
constexpr int kilo = 1024;
|
constexpr int kilo = 1024;
|
||||||
localSharedMemory.resize(impl.sharedMemorySize * kilo);
|
impl.localSharedMemory.resize(impl.sharedMemorySize * kilo);
|
||||||
}
|
}
|
||||||
return &localSharedMemory[0];
|
return &impl.localSharedMemory[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getSharedMemory() -> char * {
|
auto getSharedMemory() -> char * {
|
||||||
@ -90,6 +85,7 @@ namespace vkvm {
|
|||||||
impl.sharedMemory = ptr;
|
impl.sharedMemory = ptr;
|
||||||
return ptr;
|
return ptr;
|
||||||
}
|
}
|
||||||
|
//using a local buffer for shared memory testing
|
||||||
return getLocalMemory();
|
return getLocalMemory();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8,6 +8,26 @@ namespace vkvm {
|
|||||||
|
|
||||||
Impl impl;
|
Impl impl;
|
||||||
|
|
||||||
|
auto setDefaultValues() -> void {
|
||||||
|
impl.localMemoryWarn = false;
|
||||||
|
if (getSharedMemory() != nullptr) {
|
||||||
|
if(getSharedMemory() == &impl.localSharedMemory[0]) {
|
||||||
|
setMode(GraphicMode::RGB);
|
||||||
|
setCharactersPerRow(60);
|
||||||
|
setCharactersPerColumn(20);
|
||||||
|
setHeight(600);
|
||||||
|
setWidth(800);
|
||||||
|
setMousePosition(42, 42);
|
||||||
|
setBackgroundColor(black);
|
||||||
|
setForegroundColor(white);
|
||||||
|
setRedrawInterval(500);
|
||||||
|
setTimerInterruptInterval(1000);
|
||||||
|
setFont(FontType::ProFontIIX);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
impl.localMemoryWarn = true;
|
||||||
|
}
|
||||||
|
|
||||||
auto sendSignal(pid_t pid, int signalNumber) -> void {
|
auto sendSignal(pid_t pid, int signalNumber) -> void {
|
||||||
kill(pid, signalNumber);
|
kill(pid, signalNumber);
|
||||||
}
|
}
|
||||||
@ -50,18 +70,21 @@ namespace vkvm {
|
|||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->layout_version = newValue;
|
getRegisters()->layout_version = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto setCharactersPerColumn(int newValue) -> void {
|
auto setCharactersPerColumn(int newValue) -> void {
|
||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->characters_per_column = newValue;
|
getRegisters()->characters_per_column = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto setCharactersPerRow(int newValue) -> void {
|
auto setCharactersPerRow(int newValue) -> void {
|
||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->characters_per_row = newValue;
|
getRegisters()->characters_per_row = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto setMousePosition(int x, int y) -> void {
|
auto setMousePosition(int x, int y) -> void {
|
||||||
@ -69,16 +92,26 @@ namespace vkvm {
|
|||||||
getRegisters()->mouse_pos_x = x;
|
getRegisters()->mouse_pos_x = x;
|
||||||
getRegisters()->mouse_pos_y = y;
|
getRegisters()->mouse_pos_y = y;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto buttonPressed(KeyCode keyCode) -> void {
|
auto buttonPressed(KeyCode keyCode) -> void {
|
||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
auto reg = getRegisters();
|
auto reg = getRegisters();
|
||||||
if (reg->keyboardBuffer_index_write >= sizeof(reg->keyboardBuffer)) {
|
reg->keyboardBuffer[(reg->keyboardBuffer_index_write) % keyboardBufferSize] = keyCode;
|
||||||
reg->keyboardBuffer_index_write = 0;
|
|
||||||
}
|
|
||||||
reg->keyboardBuffer[reg->keyboardBuffer_index_write++] = keyCode;
|
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
auto getRegisteredProcesses(EventType eventType) -> std::vector<int> {
|
||||||
|
std::vector<int> result;
|
||||||
|
auto ivt = getInterruptTable();
|
||||||
|
for(int i = 0; i < impl.interruptEntrysPerEventType;i++){
|
||||||
|
auto &entry= ivt[eventType * impl.interruptEntrysPerEventType + i];
|
||||||
|
if (entry.pid != 0) {
|
||||||
|
result.push_back(entry.pid);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -38,7 +38,7 @@ constexpr int keyboardBufferSize = 16;
|
|||||||
int textMode_font_height;
|
int textMode_font_height;
|
||||||
int mouse_pos_x;
|
int mouse_pos_x;
|
||||||
int mouse_pos_y;
|
int mouse_pos_y;
|
||||||
std::array<int16_t, keyboardBufferSize> keyboardBuffer;
|
std::array<int32_t, keyboardBufferSize> keyboardBuffer;
|
||||||
int keyboardBuffer_index_write;
|
int keyboardBuffer_index_write;
|
||||||
int keyboardBuffer_index_read;
|
int keyboardBuffer_index_read;
|
||||||
};
|
};
|
||||||
@ -61,10 +61,14 @@ constexpr int keyboardBufferSize = 16;
|
|||||||
std::vector<std::function<void()>> eventTable;
|
std::vector<std::function<void()>> eventTable;
|
||||||
bool localMemoryWarn = true;
|
bool localMemoryWarn = true;
|
||||||
char *sharedMemory = nullptr;
|
char *sharedMemory = nullptr;
|
||||||
|
std::vector<char> localSharedMemory;
|
||||||
};
|
};
|
||||||
|
|
||||||
extern Impl impl;
|
extern Impl impl;
|
||||||
|
|
||||||
|
|
||||||
|
auto setDefaultValues() -> void;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* send a signal to a process
|
* send a signal to a process
|
||||||
* @param pid of the process to which the signal is send
|
* @param pid of the process to which the signal is send
|
||||||
@ -126,6 +130,12 @@ constexpr int keyboardBufferSize = 16;
|
|||||||
*/
|
*/
|
||||||
auto buttonPressed(KeyCode keyCode) -> void;
|
auto buttonPressed(KeyCode keyCode) -> void;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* get registered Processes for a given event type.
|
||||||
|
* @param eventType.
|
||||||
|
*/
|
||||||
|
auto getRegisteredProcesses(EventType eventType) -> std::vector<int>;
|
||||||
|
|
||||||
// Shared Memory Layout
|
// Shared Memory Layout
|
||||||
// --------------------------------------------------------------------
|
// --------------------------------------------------------------------
|
||||||
// struct ControlRegisters
|
// struct ControlRegisters
|
||||||
|
103
src/log.cpp
103
src/log.cpp
@ -5,9 +5,15 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#include "log.hpp"
|
#include "log.hpp"
|
||||||
|
#include <fstream>
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
namespace vkvm {
|
namespace vkvm {
|
||||||
|
|
||||||
|
LogLevel logLevel = LogLevel::INFO;
|
||||||
|
LogLevel fileLogLevel = LogLevel::INFO;
|
||||||
|
std::ofstream logToFileStream;//NOLINT
|
||||||
|
|
||||||
//converts the level to a string of the level
|
//converts the level to a string of the level
|
||||||
auto getLevelName(LogLevel level) -> std::string {
|
auto getLevelName(LogLevel level) -> std::string {
|
||||||
switch(level){
|
switch(level){
|
||||||
@ -44,66 +50,98 @@ namespace vkvm {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
LogLevel logLevel = LogLevel::INFO;
|
|
||||||
|
|
||||||
//log the current time
|
//log the current time
|
||||||
auto logTime() -> void {
|
auto logTime() -> std::string {
|
||||||
time_t rawtime;
|
time_t rawtime;
|
||||||
time(&rawtime);
|
time(&rawtime);
|
||||||
struct tm *timeinfo;
|
struct tm *timeinfo;
|
||||||
timeinfo = localtime(&rawtime);
|
timeinfo = localtime(&rawtime);
|
||||||
|
|
||||||
constexpr int decimalBase = 10;
|
constexpr int decimalBase = 10;
|
||||||
|
std::stringstream stream;
|
||||||
|
|
||||||
if (timeinfo->tm_hour < decimalBase) {
|
if (timeinfo->tm_hour < decimalBase) {
|
||||||
std::cout << "0";
|
stream << "0";
|
||||||
}
|
}
|
||||||
std::cout << timeinfo->tm_hour;
|
stream << timeinfo->tm_hour;
|
||||||
std::cout << ":";
|
stream << ":";
|
||||||
if (timeinfo->tm_min < decimalBase) {
|
if (timeinfo->tm_min < decimalBase) {
|
||||||
std::cout << "0";
|
stream << "0";
|
||||||
}
|
}
|
||||||
std::cout << timeinfo->tm_min;
|
stream << timeinfo->tm_min;
|
||||||
std::cout << ":";
|
stream << ":";
|
||||||
if (timeinfo->tm_sec < decimalBase) {
|
if (timeinfo->tm_sec < decimalBase) {
|
||||||
std::cout << "0";
|
stream << "0";
|
||||||
}
|
}
|
||||||
std::cout << timeinfo->tm_sec;
|
stream << timeinfo->tm_sec;
|
||||||
|
return stream.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
//log the message
|
//log the message
|
||||||
auto log(LogLevel level, const std::string &msg) -> void {
|
auto log(LogLevel level, const std::string &msg) -> void {
|
||||||
if(level >= logLevel) {
|
if(level >= logLevel || level >= fileLogLevel) {
|
||||||
std::string levelName = getLevelName(level);
|
std::string levelName = getLevelName(level);
|
||||||
const int maxLevelNameLength = 8;
|
const int maxLevelNameLength = 8;
|
||||||
|
|
||||||
//time
|
std::stringstream stream;
|
||||||
std::cout << "[";
|
std::stringstream noColorStream;
|
||||||
logTime();
|
|
||||||
std::cout << "] ";
|
|
||||||
|
|
||||||
//color and level name;lo
|
//time
|
||||||
std::cout << "[";
|
std::string time = logTime();
|
||||||
std::cout << "\033[" << getLevelColor(level) << "m" << levelName << "\033[0m";
|
stream << "[";
|
||||||
std::cout << "] ";
|
stream << time;
|
||||||
|
stream << "] ";
|
||||||
|
|
||||||
|
noColorStream << "[";
|
||||||
|
noColorStream << time;
|
||||||
|
noColorStream << "] ";
|
||||||
|
|
||||||
|
//color and level name
|
||||||
|
stream << "[";
|
||||||
|
stream << "\033[" << getLevelColor(level) << "m" << levelName << "\033[0m";
|
||||||
|
stream << "] ";
|
||||||
for (int i = levelName.size(); i < maxLevelNameLength; i++) {
|
for (int i = levelName.size(); i < maxLevelNameLength; i++) {
|
||||||
std::cout << " ";
|
stream << " ";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//no color and level name
|
||||||
|
noColorStream << "[";
|
||||||
|
noColorStream << levelName;
|
||||||
|
noColorStream << "] ";
|
||||||
|
for (int i = levelName.size(); i < maxLevelNameLength; i++) {
|
||||||
|
noColorStream << " ";
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
//message
|
//message
|
||||||
for(char c : msg){
|
for(char c : msg){
|
||||||
if(c == '\n'){
|
if(c == '\n'){
|
||||||
//intend newlines so that they align with the start of the message
|
//intend newlines so that they align with the start of the message
|
||||||
std::cout << "\n";
|
stream << "\n";
|
||||||
|
noColorStream << "\n";
|
||||||
const int paddingSize = 22;
|
const int paddingSize = 22;
|
||||||
for(int i = 0; i < paddingSize;i++){
|
for(int i = 0; i < paddingSize;i++){
|
||||||
std::cout << " ";
|
stream << " ";
|
||||||
|
noColorStream << " ";
|
||||||
}
|
}
|
||||||
}else{
|
}else{
|
||||||
std::cout << c;
|
stream << c;
|
||||||
|
noColorStream << c;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
stream << "\n";
|
||||||
|
noColorStream << "\n";
|
||||||
|
|
||||||
|
if(level >= logLevel){
|
||||||
|
std::cout << stream.str();
|
||||||
|
}
|
||||||
|
if(logToFileStream.is_open()){
|
||||||
|
if(level >= fileLogLevel){
|
||||||
|
logToFileStream << noColorStream.str();
|
||||||
|
//TODO(julian): fixme
|
||||||
|
logToFileStream.flush();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
std::cout << "\n";
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -111,4 +149,17 @@ namespace vkvm {
|
|||||||
logLevel = level;
|
logLevel = level;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
auto setLogFileLevel(LogLevel level) -> void {
|
||||||
|
fileLogLevel = level;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto setLogToFile(const std::string &file) -> void {
|
||||||
|
if(logToFileStream.is_open()){
|
||||||
|
logToFileStream.close();
|
||||||
|
}
|
||||||
|
if(!file.empty()){
|
||||||
|
logToFileStream.open(file, std::ofstream::app);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -47,6 +47,8 @@ namespace vkvm {
|
|||||||
* @since 0.1.0
|
* @since 0.1.0
|
||||||
*/
|
*/
|
||||||
auto setLogLevel(LogLevel level) -> void;
|
auto setLogLevel(LogLevel level) -> void;
|
||||||
|
auto setLogFileLevel(LogLevel level) -> void;
|
||||||
|
auto setLogToFile(const std::string &file) -> void;
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
153
src/vkvm.cpp
153
src/vkvm.cpp
@ -6,51 +6,32 @@
|
|||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
|
||||||
namespace vkvm {
|
namespace vkvm {
|
||||||
// NOLINT
|
|
||||||
auto initialize(int pid) -> void {
|
auto initialize(int pid) -> void {
|
||||||
impl.sharedMemoryPid = pid;
|
impl.sharedMemoryPid = pid;
|
||||||
impl.sharedMemoryKey = 12345;// NOLINT
|
impl.sharedMemoryKey = 12345;
|
||||||
impl.sharedMemorySize = 8000;// NOLINT
|
impl.sharedMemorySize = 8000;
|
||||||
initSemaphore();
|
initSemaphore();
|
||||||
setDefaultValues();
|
setDefaultValues();
|
||||||
}
|
}
|
||||||
|
|
||||||
auto setDefaultValues() -> void {
|
|
||||||
impl.localMemoryWarn = false;
|
|
||||||
if(getSharedMemory() != nullptr) {
|
|
||||||
//set default values
|
|
||||||
setMode(GraphicMode::RGB);
|
|
||||||
setCharactersPerRow(60);// NOLINT
|
|
||||||
setCharactersPerColumn(20);// NOLINT
|
|
||||||
setHeight(600);// NOLINT
|
|
||||||
setWidth(800);// NOLINT
|
|
||||||
setMousePosition(42, 42);// NOLINT
|
|
||||||
setBackgroundColor(black);
|
|
||||||
setForegroundColor(white);
|
|
||||||
setRedrawInterval(20);// NOLINT
|
|
||||||
setTimerInterruptInterval(10);// NOLINT
|
|
||||||
setFont(FontType(3,"",0,0));
|
|
||||||
}
|
|
||||||
impl.localMemoryWarn = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto registerEvent(EventType type, const std::function<void()> &handler) -> bool {
|
auto registerEvent(EventType type, const std::function<void()> &handler) -> bool {
|
||||||
int signum = SIGUSR1 + impl.eventTable.size();
|
int signum = SIGUSR1 + impl.eventTable.size();
|
||||||
auto ivt = getInterruptTable();
|
auto ivt = getInterruptTable();
|
||||||
|
|
||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
|
|
||||||
for(int i = 0; i < impl.interruptEntrysPerEventType;i++){
|
for (int i = 0; i < impl.interruptEntrysPerEventType; i++) {
|
||||||
auto &entry= ivt[type * impl.interruptEntrysPerEventType + i];
|
auto &entry = ivt[type * impl.interruptEntrysPerEventType + i];
|
||||||
if (entry.pid == 0) {
|
if (entry.pid == 0) {
|
||||||
|
|
||||||
entry.pid = getpid();
|
entry.pid = getpid();
|
||||||
entry.signum = signum;
|
entry.signum = signum;
|
||||||
impl.eventTable.push_back(handler);
|
impl.eventTable.push_back(handler);
|
||||||
|
|
||||||
onSignal(signum, [](int sig){
|
onSignal(signum, [](int sig) {
|
||||||
if(sig >= SIGUSR1){
|
if (sig >= SIGUSR1) {
|
||||||
if((sig - SIGUSR1) < impl.eventTable.size()){
|
if ((sig - SIGUSR1) < impl.eventTable.size()) {
|
||||||
impl.eventTable[sig - SIGUSR1]();
|
impl.eventTable[sig - SIGUSR1]();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -64,19 +45,24 @@ namespace vkvm {
|
|||||||
}
|
}
|
||||||
|
|
||||||
auto setPixel(int x, int y, Color color) -> bool {
|
auto setPixel(int x, int y, Color color) -> bool {
|
||||||
lockSharedMemory();
|
if(x < 0 || y < 0){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (x > getWidth() || y > getHeight()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
//lockSharedMemory();
|
||||||
auto reg = getRegisters();
|
auto reg = getRegisters();
|
||||||
const int bitsPerPixel = 8;
|
const int bitsPerPixel = 8;
|
||||||
|
|
||||||
switch(reg->graphicMode) {
|
switch (reg->graphicMode) {
|
||||||
case Text: {
|
case Text: {
|
||||||
int pixelIndex = (y * getWidth() + x);
|
int pixelIndex = (y * getWidth() + x);
|
||||||
unsigned char *ptr = reinterpret_cast<unsigned char *>(getPixelArea()) + (pixelIndex / bitsPerPixel);
|
unsigned char *ptr = reinterpret_cast<unsigned char *>(getPixelArea()) + (pixelIndex / bitsPerPixel);
|
||||||
if(color == reg->foreground_color){
|
if (color == reg->foreground_color) {
|
||||||
//set bit to 1
|
//set bit to 1
|
||||||
ptr[0] |= (1 << (pixelIndex % bitsPerPixel));
|
ptr[0] |= (1 << (pixelIndex % bitsPerPixel));
|
||||||
}
|
} else {
|
||||||
else{
|
|
||||||
//set bit to 0
|
//set bit to 0
|
||||||
ptr[0] &= ~(1 << (pixelIndex % bitsPerPixel));
|
ptr[0] &= ~(1 << (pixelIndex % bitsPerPixel));
|
||||||
}
|
}
|
||||||
@ -85,11 +71,10 @@ namespace vkvm {
|
|||||||
case TwoColors: {
|
case TwoColors: {
|
||||||
int pixelIndex = (y * getWidth() + x);
|
int pixelIndex = (y * getWidth() + x);
|
||||||
unsigned char *ptr = reinterpret_cast<unsigned char *>(getPixelArea()) + (pixelIndex / bitsPerPixel);
|
unsigned char *ptr = reinterpret_cast<unsigned char *>(getPixelArea()) + (pixelIndex / bitsPerPixel);
|
||||||
if(color == reg->foreground_color){
|
if (color.getRed() > 127 || color.getGreen() > 127 || color.getBlue() > 127) {
|
||||||
//set bit to 1
|
//set bit to 1
|
||||||
ptr[0] |= (1 << (pixelIndex % bitsPerPixel));
|
ptr[0] |= (1 << (pixelIndex % bitsPerPixel));
|
||||||
}
|
} else {
|
||||||
else{
|
|
||||||
//set bit to 0
|
//set bit to 0
|
||||||
ptr[0] &= ~(1 << (pixelIndex % bitsPerPixel));
|
ptr[0] &= ~(1 << (pixelIndex % bitsPerPixel));
|
||||||
}
|
}
|
||||||
@ -110,24 +95,31 @@ namespace vkvm {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
unlockSharedMemory();
|
//unlockSharedMemory();
|
||||||
return false;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getPixel(int x, int y) -> Color {
|
auto getPixel(int x, int y) -> Color {
|
||||||
Color color = Color(0,0,0);
|
if(x < 0 || y < 0) {
|
||||||
|
return getBackgroundColor();
|
||||||
|
}
|
||||||
|
if (x > getWidth() || y > getHeight()) {
|
||||||
|
return getBackgroundColor();
|
||||||
|
}
|
||||||
|
|
||||||
|
Color color = Color(0, 0, 0);
|
||||||
auto reg = getRegisters();
|
auto reg = getRegisters();
|
||||||
const int bitsPerPixel = 8;
|
const int bitsPerPixel = 8;
|
||||||
|
|
||||||
switch(reg->graphicMode) {
|
switch (reg->graphicMode) {
|
||||||
case Text: {
|
case Text: {
|
||||||
int pixelIndex = (y * getWidth() + x);
|
int pixelIndex = (y * getWidth() + x);
|
||||||
unsigned char *ptr = reinterpret_cast<unsigned char *>(getPixelArea()) + pixelIndex / bitsPerPixel;
|
unsigned char *ptr = reinterpret_cast<unsigned char *>(getPixelArea()) + pixelIndex / bitsPerPixel;
|
||||||
bool bit = static_cast<bool>(ptr[0] & (1 << (pixelIndex % bitsPerPixel)));
|
bool bit = static_cast<bool>(ptr[0] & (1 << (pixelIndex % bitsPerPixel)));
|
||||||
if(bit){
|
if (bit) {
|
||||||
color = reg->foreground_color;
|
color = reg->foreground_color;
|
||||||
}else{
|
} else {
|
||||||
color =reg->background_color;
|
color = reg->background_color;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -135,10 +127,10 @@ namespace vkvm {
|
|||||||
int pixelIndex = (y * getWidth() + x);
|
int pixelIndex = (y * getWidth() + x);
|
||||||
unsigned char *ptr = reinterpret_cast<unsigned char *>(getPixelArea()) + (pixelIndex / bitsPerPixel);
|
unsigned char *ptr = reinterpret_cast<unsigned char *>(getPixelArea()) + (pixelIndex / bitsPerPixel);
|
||||||
bool bit = static_cast<bool>(ptr[0] & (1 << (pixelIndex % bitsPerPixel)));
|
bool bit = static_cast<bool>(ptr[0] & (1 << (pixelIndex % bitsPerPixel)));
|
||||||
if(bit){
|
if (bit) {
|
||||||
color = reg->foreground_color;
|
color = reg->foreground_color;
|
||||||
}else{
|
} else {
|
||||||
color =reg->background_color;
|
color = reg->background_color;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -159,21 +151,35 @@ namespace vkvm {
|
|||||||
auto setText(std::string text) -> bool {
|
auto setText(std::string text) -> bool {
|
||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
char *ptr = getTextArea();
|
char *ptr = getTextArea();
|
||||||
for(int i = 0; i < static_cast<int>(text.size());i++){
|
for (int i = 0; i < static_cast<int>(text.size()); i++) {
|
||||||
if(i >= getCharactersPerColumn() * getCharactersPerRow()){
|
if (i < getCharactersPerColumn() * getCharactersPerRow()) {
|
||||||
break;
|
|
||||||
}
|
|
||||||
ptr[i] = text[i];
|
ptr[i] = text[i];
|
||||||
}
|
}
|
||||||
if(text.size() < getCharactersPerColumn() * getCharactersPerRow()){
|
}
|
||||||
|
if (text.size() < getCharactersPerColumn() * getCharactersPerRow()) {
|
||||||
ptr[text.size()] = '\0';
|
ptr[text.size()] = '\0';
|
||||||
}
|
}
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::RenderText);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getText() -> std::string {
|
auto getText() -> std::string {
|
||||||
return std::string (getTextArea());
|
std::string text = getTextArea();
|
||||||
|
|
||||||
|
return text.substr(0, getCharactersPerColumn() * getCharactersPerRow());
|
||||||
|
}
|
||||||
|
|
||||||
|
auto clearText() -> bool {
|
||||||
|
lockSharedMemory();
|
||||||
|
char *ptr = getTextArea();
|
||||||
|
for (int i = 0; i < getCharactersPerColumn() * getCharactersPerRow(); ++i) {
|
||||||
|
ptr[i] = '\0';
|
||||||
|
}
|
||||||
|
|
||||||
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::RenderText);
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getLayoutVersion() -> LayoutVersion {
|
auto getLayoutVersion() -> LayoutVersion {
|
||||||
@ -181,7 +187,7 @@ namespace vkvm {
|
|||||||
}
|
}
|
||||||
|
|
||||||
auto reset() -> void {
|
auto reset() -> void {
|
||||||
//TODO(julian): reset
|
setDefaultValues();
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getWidth() -> int {
|
auto getWidth() -> int {
|
||||||
@ -192,6 +198,7 @@ namespace vkvm {
|
|||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->width_pixels = newValue;
|
getRegisters()->width_pixels = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getHeight() -> int {
|
auto getHeight() -> int {
|
||||||
@ -202,6 +209,7 @@ namespace vkvm {
|
|||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->height_pixels = newValue;
|
getRegisters()->height_pixels = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getMode() -> GraphicMode {
|
auto getMode() -> GraphicMode {
|
||||||
@ -211,32 +219,33 @@ namespace vkvm {
|
|||||||
auto setMode(GraphicMode newValue) -> void {
|
auto setMode(GraphicMode newValue) -> void {
|
||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
auto reg = getRegisters();
|
auto reg = getRegisters();
|
||||||
if(reg->graphicMode != newValue){
|
if (reg->graphicMode != newValue) {
|
||||||
|
|
||||||
std::vector<Color> pixels;
|
std::vector<Color> pixels;
|
||||||
int height = reg->height_pixels;
|
int height = reg->height_pixels;
|
||||||
int width = reg->width_pixels;
|
int width = reg->width_pixels;
|
||||||
pixels.resize(height * width);
|
pixels.resize(height * width);
|
||||||
|
|
||||||
for(int y = 0; y < height;y++){
|
for (int y = 0; y < height; y++) {
|
||||||
for(int x = 0;x < width;x++){
|
for (int x = 0; x < width; x++) {
|
||||||
pixels[y * width + x] = getPixel(x,y);
|
pixels[y * width + x] = getPixel(x, y);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
getRegisters()->graphicMode = newValue;
|
getRegisters()->graphicMode = newValue;
|
||||||
|
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
for(int y = 0; y < height;y++){
|
for (int y = 0; y < height; y++) {
|
||||||
for(int x = 0;x < width;x++){
|
for (int x = 0; x < width; x++) {
|
||||||
setPixel(x,y, pixels[y * width + x]);
|
setPixel(x, y, pixels[y * width + x]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
}else{
|
} else {
|
||||||
reg->graphicMode = newValue;
|
reg->graphicMode = newValue;
|
||||||
}
|
}
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getRedrawInterval() -> int {
|
auto getRedrawInterval() -> int {
|
||||||
@ -247,6 +256,7 @@ namespace vkvm {
|
|||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->autoRedrawInterval = newValue;
|
getRegisters()->autoRedrawInterval = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getTimerInterruptInterval() -> int {
|
auto getTimerInterruptInterval() -> int {
|
||||||
@ -257,6 +267,7 @@ namespace vkvm {
|
|||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->timerInterruptInterval = newValue;
|
getRegisters()->timerInterruptInterval = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getBackgroundColor() -> Color {
|
auto getBackgroundColor() -> Color {
|
||||||
@ -267,6 +278,7 @@ namespace vkvm {
|
|||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->background_color = newValue;
|
getRegisters()->background_color = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getForegroundColor() -> Color {
|
auto getForegroundColor() -> Color {
|
||||||
@ -277,6 +289,7 @@ namespace vkvm {
|
|||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->foreground_color = newValue;
|
getRegisters()->foreground_color = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getCharactersPerRow() -> int {
|
auto getCharactersPerRow() -> int {
|
||||||
@ -288,15 +301,14 @@ namespace vkvm {
|
|||||||
}
|
}
|
||||||
|
|
||||||
auto getFont() -> FontType {
|
auto getFont() -> FontType {
|
||||||
//TODO(julian): get font properly
|
return FontType(getRegisters()->textMode_font);
|
||||||
return {getRegisters()->textMode_font, "", 0, 0};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
auto setFont(const FontType &newValue) -> void {
|
auto setFont(const FontType &newValue) -> void {
|
||||||
//TODO(julian): setFont properly
|
|
||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
getRegisters()->textMode_font = newValue.getId();
|
getRegisters()->textMode_font = newValue;
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
|
callEvent(EventType::UpdateControlRegisters);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto getMousePosition() -> Coordinates {
|
auto getMousePosition() -> Coordinates {
|
||||||
@ -307,12 +319,15 @@ namespace vkvm {
|
|||||||
lockSharedMemory();
|
lockSharedMemory();
|
||||||
auto keyCode = KeyCode(0);
|
auto keyCode = KeyCode(0);
|
||||||
auto reg = getRegisters();
|
auto reg = getRegisters();
|
||||||
if(reg->keyboardBuffer_index_read != reg->keyboardBuffer_index_write) {
|
|
||||||
keyCode = static_cast<KeyCode>(reg->keyboardBuffer[reg->keyboardBuffer_index_read++]);
|
if(reg->keyboardBuffer_index_read >= reg->keyboardBuffer_index_write) {
|
||||||
if (reg->keyboardBuffer_index_read >= sizeof(reg->keyboardBuffer)) {
|
auto code = reg->keyboardBuffer[(reg->keyboardBuffer_index_read) % keyboardBufferSize];
|
||||||
reg->keyboardBuffer_index_read = 0;
|
keyCode = KeyCode(code);
|
||||||
}
|
}else{
|
||||||
|
auto code = reg->keyboardBuffer[(reg->keyboardBuffer_index_read) % keyboardBufferSize];
|
||||||
|
keyCode = KeyCode(code);
|
||||||
}
|
}
|
||||||
|
|
||||||
unlockSharedMemory();
|
unlockSharedMemory();
|
||||||
return keyCode;
|
return keyCode;
|
||||||
}
|
}
|
||||||
|
@ -28,7 +28,6 @@ namespace vkvm {
|
|||||||
*/
|
*/
|
||||||
auto initialize(int pid) -> void;
|
auto initialize(int pid) -> void;
|
||||||
|
|
||||||
auto setDefaultValues() -> void;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* set pixel at a x,y position to a certain color.
|
* set pixel at a x,y position to a certain color.
|
||||||
@ -67,6 +66,13 @@ namespace vkvm {
|
|||||||
*/
|
*/
|
||||||
auto getText() -> std::string;
|
auto getText() -> std::string;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* clear text area
|
||||||
|
* @return if text could be cleared, false if it could not be cleared.
|
||||||
|
*/
|
||||||
|
auto clearText() -> bool;
|
||||||
|
|
||||||
|
|
||||||
//Control registers start here
|
//Control registers start here
|
||||||
|
|
||||||
//all modes
|
//all modes
|
||||||
|
25
test/area_test.cpp
Normal file
25
test/area_test.cpp
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
#include "../src/vkvm.hpp"
|
||||||
|
#include <catch2/catch.hpp>
|
||||||
|
|
||||||
|
TEST_CASE("AREA") {
|
||||||
|
vkvm::initialize(0);
|
||||||
|
vkvm::setWidth(200);
|
||||||
|
vkvm::setHeight(200);
|
||||||
|
|
||||||
|
SECTION("inside bounds") {
|
||||||
|
REQUIRE(vkvm::setPixel(100, 100, vkvm::white));
|
||||||
|
REQUIRE(vkvm::getPixel(100, 100) == vkvm::white);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Out of bounds") {
|
||||||
|
REQUIRE_FALSE(vkvm::setPixel(400, 400, vkvm::white));
|
||||||
|
REQUIRE(vkvm::getPixel(400, 400) == vkvm::black);
|
||||||
|
|
||||||
|
REQUIRE_FALSE(vkvm::setPixel(-5, -5, vkvm::white));
|
||||||
|
REQUIRE(vkvm::getPixel(-5, -5) == vkvm::black);
|
||||||
|
|
||||||
|
vkvm::setBackgroundColor(vkvm::blue);
|
||||||
|
|
||||||
|
REQUIRE(vkvm::getPixel(400, 400) == vkvm::blue);
|
||||||
|
}
|
||||||
|
}
|
19
test/buffer_test.cpp
Normal file
19
test/buffer_test.cpp
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
#include "../src/internal.hpp"
|
||||||
|
#include "../src/vkvm.hpp"
|
||||||
|
#include <catch2/catch.hpp>
|
||||||
|
|
||||||
|
|
||||||
|
TEST_CASE("Keyboard Buffer") {
|
||||||
|
SECTION("write") {
|
||||||
|
vkvm::setLogLevel(vkvm::DEBUG);
|
||||||
|
//vkvm::buttonPressed(vkvm::A);
|
||||||
|
//vkvm::buttonPressed(vkvm::B);
|
||||||
|
//vkvm::buttonPressed(vkvm::C);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("read") {
|
||||||
|
//CHECK(vkvm::getLastPressedKey() == vkvm::C);
|
||||||
|
//CHECK(vkvm::getLastPressedKey() == vkvm::C);
|
||||||
|
//CHECK(vkvm::getLastPressedKey() == vkvm::C);
|
||||||
|
}
|
||||||
|
}
|
@ -4,45 +4,72 @@
|
|||||||
|
|
||||||
TEST_CASE("Colors") {
|
TEST_CASE("Colors") {
|
||||||
vkvm::initialize(0);
|
vkvm::initialize(0);
|
||||||
vkvm::setPixel(10, 10, vkvm::black);//NOLINT
|
vkvm::setMode(vkvm::RGB);
|
||||||
vkvm::setPixel(11, 11, vkvm::white);//NOLINT
|
REQUIRE(vkvm::setPixel(10, 10, vkvm::black));
|
||||||
vkvm::setPixel(12, 12, vkvm::green);//NOLINT
|
REQUIRE(vkvm::setPixel(11, 11, vkvm::white));
|
||||||
vkvm::setPixel(13, 13, vkvm::red);//NOLINT
|
REQUIRE(vkvm::setPixel(12, 12, vkvm::green));
|
||||||
vkvm::setPixel(14, 14, vkvm::blue);//NOLINT
|
REQUIRE(vkvm::setPixel(13, 13, vkvm::red));
|
||||||
vkvm::setPixel(15, 15, vkvm::Color(66, 77, 88)); //NOLINT
|
REQUIRE(vkvm::setPixel(14, 14, vkvm::blue));
|
||||||
vkvm::setPixel(16, 16, vkvm::Color(0xFFFFFF));//NOLINT
|
REQUIRE(vkvm::setPixel(15, 15, vkvm::Color(66, 77, 88)));
|
||||||
|
REQUIRE(vkvm::setPixel(16, 16, vkvm::Color(0xFFFFFF)));
|
||||||
|
REQUIRE(vkvm::setPixel(17, 17, vkvm::Color(500, 500, 500)));
|
||||||
|
REQUIRE(vkvm::setPixel(18, 18, vkvm::Color(0x000000)));
|
||||||
|
|
||||||
SECTION("RGB") {
|
SECTION("RGB") {
|
||||||
REQUIRE(vkvm::getPixel(10, 10) == vkvm::black);//NOLINT
|
REQUIRE(vkvm::getPixel(10, 10) == vkvm::black);
|
||||||
REQUIRE(vkvm::getPixel(11, 11) == vkvm::white);//NOLINT
|
REQUIRE(vkvm::getPixel(11, 11) == vkvm::white);
|
||||||
REQUIRE(vkvm::getPixel(12, 12) == vkvm::green);//NOLINT
|
REQUIRE(vkvm::getPixel(12, 12) == vkvm::green);
|
||||||
REQUIRE(vkvm::getPixel(13, 13) == vkvm::red);//NOLINT
|
REQUIRE(vkvm::getPixel(13, 13) == vkvm::red);
|
||||||
REQUIRE(vkvm::getPixel(14, 14) == vkvm::blue);//NOLINT
|
REQUIRE(vkvm::getPixel(14, 14) == vkvm::blue);
|
||||||
REQUIRE(vkvm::getPixel(15, 15) == vkvm::Color(66, 77, 88));//NOLINT
|
REQUIRE(vkvm::getPixel(15, 15) == vkvm::Color(66, 77, 88));
|
||||||
REQUIRE(vkvm::getPixel(16, 16) == vkvm::white);//NOLINT
|
REQUIRE(vkvm::getPixel(16, 16) == vkvm::white);
|
||||||
|
REQUIRE(vkvm::getPixel(17, 17) == vkvm::white);
|
||||||
|
REQUIRE(vkvm::getPixel(18, 18) == vkvm::black);
|
||||||
}
|
}
|
||||||
|
|
||||||
SECTION("TwoColors") {
|
SECTION("TwoColors") {
|
||||||
vkvm::setMode(vkvm::TwoColors);
|
vkvm::setMode(vkvm::TwoColors);
|
||||||
REQUIRE(vkvm::getPixel(10, 10) == vkvm::black);//NOLINT
|
REQUIRE(vkvm::getPixel(10, 10) == vkvm::black);
|
||||||
REQUIRE(vkvm::getPixel(11, 11) == vkvm::white);//NOLINT
|
REQUIRE(vkvm::getPixel(11, 11) == vkvm::white);
|
||||||
REQUIRE(vkvm::getPixel(12, 12) == vkvm::black);//NOLINT
|
REQUIRE(vkvm::getPixel(12, 12) == vkvm::white);
|
||||||
REQUIRE(vkvm::getPixel(13, 13) == vkvm::black);//NOLINT
|
REQUIRE(vkvm::getPixel(13, 13) == vkvm::white);
|
||||||
REQUIRE(vkvm::getPixel(14, 14) == vkvm::black);//NOLINT
|
REQUIRE(vkvm::getPixel(14, 14) == vkvm::white);
|
||||||
REQUIRE(vkvm::getPixel(15, 15) == vkvm::black);//NOLINT
|
REQUIRE(vkvm::getPixel(15, 15) == vkvm::black);
|
||||||
REQUIRE(vkvm::getPixel(16, 16) == vkvm::white);//NOLINT
|
REQUIRE(vkvm::getPixel(16, 16) == vkvm::white);
|
||||||
|
REQUIRE(vkvm::getPixel(17, 17) == vkvm::white);
|
||||||
|
REQUIRE(vkvm::getPixel(18, 18) == vkvm::black);
|
||||||
|
|
||||||
|
|
||||||
|
//different foreground/background color
|
||||||
|
vkvm::setBackgroundColor(vkvm::blue);
|
||||||
|
vkvm::setForegroundColor(vkvm::red);
|
||||||
|
|
||||||
|
REQUIRE(vkvm::getBackgroundColor() == vkvm::blue);
|
||||||
|
REQUIRE(vkvm::getForegroundColor() == vkvm::red);
|
||||||
|
|
||||||
|
REQUIRE(vkvm::getPixel(10, 10) == vkvm::blue);
|
||||||
|
REQUIRE(vkvm::getPixel(11, 11) == vkvm::red);
|
||||||
|
REQUIRE(vkvm::getPixel(12, 12) == vkvm::red);
|
||||||
|
REQUIRE(vkvm::getPixel(13, 13) == vkvm::red);
|
||||||
|
REQUIRE(vkvm::getPixel(14, 14) == vkvm::red);
|
||||||
|
REQUIRE(vkvm::getPixel(15, 15) == vkvm::blue);
|
||||||
|
REQUIRE(vkvm::getPixel(16, 16) == vkvm::red);
|
||||||
|
REQUIRE(vkvm::getPixel(17, 17) == vkvm::red);
|
||||||
|
REQUIRE(vkvm::getPixel(18, 18) == vkvm::blue);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
SECTION("Gray256") {
|
SECTION("Gray256") {
|
||||||
vkvm::setMode(vkvm::Gray_256);
|
vkvm::setMode(vkvm::Gray_256);
|
||||||
REQUIRE(vkvm::getPixel(10, 10) == vkvm::black);//NOLINT
|
REQUIRE(vkvm::getPixel(10, 10) == vkvm::black);
|
||||||
REQUIRE(vkvm::getPixel(11, 11) == vkvm::white);//NOLINT
|
REQUIRE(vkvm::getPixel(11, 11) == vkvm::white);
|
||||||
REQUIRE(vkvm::getPixel(12, 12) == vkvm::Color(85, 85, 85));//NOLINT
|
REQUIRE(vkvm::getPixel(12, 12) == vkvm::Color(85, 85, 85));
|
||||||
REQUIRE(vkvm::getPixel(13, 13) == vkvm::Color(85, 85, 85));//NOLINT
|
REQUIRE(vkvm::getPixel(13, 13) == vkvm::Color(85, 85, 85));
|
||||||
REQUIRE(vkvm::getPixel(14, 14) == vkvm::Color(85, 85, 85));//NOLINT
|
REQUIRE(vkvm::getPixel(14, 14) == vkvm::Color(85, 85, 85));
|
||||||
REQUIRE(vkvm::getPixel(15, 15) == vkvm::Color(77, 77, 77));//NOLINT
|
REQUIRE(vkvm::getPixel(15, 15) == vkvm::Color(77, 77, 77));
|
||||||
REQUIRE(vkvm::getPixel(16, 16) == vkvm::white);//NOLINT
|
REQUIRE(vkvm::getPixel(16, 16) == vkvm::white);
|
||||||
|
REQUIRE(vkvm::getPixel(17, 17) == vkvm::white);
|
||||||
|
REQUIRE(vkvm::getPixel(18, 18) == vkvm::black);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
70
test/default_test.cpp
Normal file
70
test/default_test.cpp
Normal file
@ -0,0 +1,70 @@
|
|||||||
|
#include "../src/internal.hpp"
|
||||||
|
#include "../src/vkvm.hpp"
|
||||||
|
#include <catch2/catch.hpp>
|
||||||
|
|
||||||
|
TEST_CASE("Default values") {
|
||||||
|
vkvm::initialize(0);
|
||||||
|
|
||||||
|
SECTION("before") {
|
||||||
|
REQUIRE(vkvm::getMode() == vkvm::RGB);
|
||||||
|
REQUIRE(vkvm::getCharactersPerRow() == 60);
|
||||||
|
REQUIRE(vkvm::getCharactersPerColumn() == 20);
|
||||||
|
REQUIRE(vkvm::getHeight() == 600);
|
||||||
|
REQUIRE(vkvm::getWidth() == 800);
|
||||||
|
REQUIRE(vkvm::getMousePosition().x == 42);
|
||||||
|
REQUIRE(vkvm::getMousePosition().y == 42);
|
||||||
|
REQUIRE(vkvm::getBackgroundColor() == vkvm::black);
|
||||||
|
REQUIRE(vkvm::getForegroundColor() == vkvm::white);
|
||||||
|
REQUIRE(vkvm::getRedrawInterval() == 500);
|
||||||
|
REQUIRE(vkvm::getTimerInterruptInterval() == 1000);
|
||||||
|
REQUIRE(vkvm::getFont() == vkvm::ProFontIIX);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("change") {
|
||||||
|
vkvm::setMode(vkvm::TwoColors);
|
||||||
|
vkvm::setCharactersPerRow(100);
|
||||||
|
vkvm::setCharactersPerColumn(100);
|
||||||
|
vkvm::setHeight(40);
|
||||||
|
vkvm::setWidth(40);
|
||||||
|
vkvm::setMousePosition(41, 43);
|
||||||
|
vkvm::setBackgroundColor(vkvm::red);
|
||||||
|
vkvm::setForegroundColor(vkvm::blue);
|
||||||
|
vkvm::setRedrawInterval(1);
|
||||||
|
vkvm::setTimerInterruptInterval(2);
|
||||||
|
vkvm::setFont(vkvm::ProFontIIX);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
REQUIRE(vkvm::getMode() == vkvm::TwoColors);
|
||||||
|
REQUIRE(vkvm::getCharactersPerRow() == 100);
|
||||||
|
REQUIRE(vkvm::getCharactersPerColumn() == 100);
|
||||||
|
REQUIRE(vkvm::getHeight() == 40);
|
||||||
|
REQUIRE(vkvm::getWidth() == 40);
|
||||||
|
REQUIRE(vkvm::getMousePosition().x == 41);
|
||||||
|
REQUIRE(vkvm::getMousePosition().y == 43);
|
||||||
|
REQUIRE(vkvm::getBackgroundColor() == vkvm::red);
|
||||||
|
REQUIRE(vkvm::getForegroundColor() == vkvm::blue);
|
||||||
|
REQUIRE(vkvm::getRedrawInterval() == 1);
|
||||||
|
REQUIRE(vkvm::getTimerInterruptInterval() == 2);
|
||||||
|
REQUIRE(vkvm::getFont() == vkvm::ProFontIIX);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
SECTION("after") {
|
||||||
|
vkvm::reset();
|
||||||
|
REQUIRE(vkvm::getMode() == vkvm::RGB);
|
||||||
|
REQUIRE(vkvm::getCharactersPerRow() == 60);
|
||||||
|
REQUIRE(vkvm::getCharactersPerColumn() == 20);
|
||||||
|
REQUIRE(vkvm::getHeight() == 600);
|
||||||
|
REQUIRE(vkvm::getWidth() == 800);
|
||||||
|
REQUIRE(vkvm::getMousePosition().x == 42);
|
||||||
|
REQUIRE(vkvm::getMousePosition().y == 42);
|
||||||
|
REQUIRE(vkvm::getBackgroundColor() == vkvm::black);
|
||||||
|
REQUIRE(vkvm::getForegroundColor() == vkvm::white);
|
||||||
|
REQUIRE(vkvm::getRedrawInterval() == 500);
|
||||||
|
REQUIRE(vkvm::getTimerInterruptInterval() == 1000);
|
||||||
|
REQUIRE(vkvm::getFont() == vkvm::ProFontIIX);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
32
test/event_test.cpp
Normal file
32
test/event_test.cpp
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
#include "../src/internal.hpp"
|
||||||
|
#include "../src/vkvm.hpp"
|
||||||
|
#include <catch2/catch.hpp>
|
||||||
|
|
||||||
|
TEST_CASE("Event") {
|
||||||
|
vkvm::initialize(0);
|
||||||
|
|
||||||
|
SECTION("Register") {
|
||||||
|
bool mouseMove = false;
|
||||||
|
bool keyup = false;
|
||||||
|
bool keyup2 = false;
|
||||||
|
vkvm::registerEvent(vkvm::MouseMove, [&]() {
|
||||||
|
mouseMove = true;
|
||||||
|
});
|
||||||
|
vkvm::registerEvent(vkvm::KeyUp, [&]() {
|
||||||
|
keyup = true;
|
||||||
|
});
|
||||||
|
vkvm::registerEvent(vkvm::KeyUp, [&]() {
|
||||||
|
keyup2 = true;
|
||||||
|
});
|
||||||
|
|
||||||
|
REQUIRE_FALSE(mouseMove);
|
||||||
|
vkvm::callEvent(vkvm::MouseMove);
|
||||||
|
REQUIRE(mouseMove);
|
||||||
|
|
||||||
|
REQUIRE_FALSE(keyup);
|
||||||
|
REQUIRE_FALSE(keyup2);
|
||||||
|
vkvm::callEvent(vkvm::KeyUp);
|
||||||
|
REQUIRE(keyup);
|
||||||
|
REQUIRE(keyup2);
|
||||||
|
}
|
||||||
|
}
|
@ -1,10 +0,0 @@
|
|||||||
#include "catch2/catch.hpp"
|
|
||||||
#include "../src/vkvm.hpp"
|
|
||||||
|
|
||||||
TEST_CASE("add works") {
|
|
||||||
vkvm::initialize(0);
|
|
||||||
vkvm::setText("Hello World");
|
|
||||||
SECTION("equals") {
|
|
||||||
REQUIRE(vkvm::getText() == "Hello World");
|
|
||||||
}
|
|
||||||
}
|
|
28
test/text_test.cpp
Normal file
28
test/text_test.cpp
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
#include "../src/internal.hpp"
|
||||||
|
#include "../src/vkvm.hpp"
|
||||||
|
#include <catch2/catch.hpp>
|
||||||
|
|
||||||
|
TEST_CASE("Text") {
|
||||||
|
vkvm::initialize(0);
|
||||||
|
|
||||||
|
REQUIRE(vkvm::setText("Hello World, this is a test"));
|
||||||
|
REQUIRE(vkvm::getText() == "Hello World, this is a test");
|
||||||
|
|
||||||
|
REQUIRE(vkvm::setText("Hello World"));
|
||||||
|
REQUIRE(vkvm::getText() == "Hello World");
|
||||||
|
|
||||||
|
vkvm::setCharactersPerColumn(5);
|
||||||
|
vkvm::setCharactersPerRow(1);
|
||||||
|
|
||||||
|
REQUIRE(vkvm::clearText());
|
||||||
|
|
||||||
|
REQUIRE(vkvm::getCharactersPerColumn() == 5);
|
||||||
|
REQUIRE(vkvm::getCharactersPerRow() == 1);
|
||||||
|
|
||||||
|
REQUIRE(vkvm::setText("Hello World"));
|
||||||
|
REQUIRE(vkvm::getText() == "Hello");
|
||||||
|
|
||||||
|
REQUIRE(vkvm::clearText());
|
||||||
|
|
||||||
|
REQUIRE(vkvm::getText().empty());
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user