Wayland example window

This commit is contained in:
jmsgrogan 2022-05-18 08:42:44 +01:00
parent 160b746182
commit 26f54c4581
30 changed files with 825 additions and 22 deletions

View file

@ -20,8 +20,12 @@ list(APPEND core_LIB_INCLUDES
file_utilities/BinaryFile.cpp
file_utilities/File.cpp
file_utilities/FileFormats.cpp
memory/SharedMemory.cpp
RandomUtils.cpp
StringUtils.cpp
http/HttpResponse.cpp)
http/HttpResponse.cpp
http/HttpHeader.cpp
http/HttpRequest.cpp)
# add the executable
add_library(core SHARED ${core_LIB_INCLUDES} ${core_HEADERS})
@ -30,6 +34,7 @@ target_include_directories(core PUBLIC
"${CMAKE_CURRENT_SOURCE_DIR}"
"${CMAKE_CURRENT_SOURCE_DIR}/file_utilities"
"${CMAKE_CURRENT_SOURCE_DIR}/loggers"
"${CMAKE_CURRENT_SOURCE_DIR}/memory"
)
set_target_properties( core PROPERTIES WINDOWS_EXPORT_ALL_SYMBOLS ON )
set_property(TARGET core PROPERTY FOLDER src)

22
src/core/RandomUtils.cpp Normal file
View file

@ -0,0 +1,22 @@
#include "RandomUtils.h"
#include <random>
#include <algorithm>
#include <iterator>
std::vector<unsigned> RandomUtils::getRandomVecUnsigned(std::size_t size)
{
std::random_device rnd_device;
std::mt19937 mersenne_engine {rnd_device()};
std::uniform_int_distribution<unsigned> dist {0, 9};
auto generator = [&dist, &mersenne_engine]()
{
return dist(mersenne_engine);
};
std::vector<unsigned> vec(size);
std::generate(std::begin(vec), std::end(vec), generator);
return vec;
}

10
src/core/RandomUtils.h Normal file
View file

@ -0,0 +1,10 @@
#pragma once
#include <vector>
class RandomUtils
{
public:
static std::vector<unsigned> getRandomVecUnsigned(std::size_t size);
};

View file

@ -13,6 +13,7 @@ public:
static constexpr char EQUALS = '=';
static constexpr char DOUBLE_QUOTE = '"';
static constexpr char SINGLE_QUOTE = '\'';
static constexpr char COLON = ':';
static bool IsAlphaNumeric(char c);
static bool IsSpace(char c);

View file

@ -0,0 +1,80 @@
#include "HttpHeader.h"
#include "StringUtils.h"
void HttpHeader::parse(const std::vector<std::string >& message)
{
std::string tag;
std::string value;
bool foundDelimiter{false};
for (const auto& line : message)
{
for(std::size_t idx = 0; idx< line.size(); idx++)
{
const auto c = line[idx];
if (c == StringUtils::COLON)
{
foundDelimiter = true;
}
else if(foundDelimiter)
{
value.push_back(c);
}
else
{
tag.push_back(c);
}
}
}
if (tag.empty() || value.empty())
{
return;
}
if (tag == "Host")
{
mHost = value;
}
else if (tag == "User-Agent")
{
mUserAgent = value;
}
else if (tag == "Accept")
{
mAccept = value;
}
else if (tag == "Accept-Language")
{
mAcceptLanguage = value;
}
else if (tag == "Accept-Encoding")
{
mAcceptEncoding = value;
}
else if (tag == "Connection")
{
mConnection = value;
}
else if (tag == "Referer")
{
mReferer = value;
}
else if (tag == "Sec-Fetch-Dest")
{
mSecFetchDest = value;
}
else if (tag == "Sec-Fetch-Mode")
{
mSecFetchMode = value;
}
else if (tag == "Sec-Fetch-Site")
{
mSecFetchSite = value;
}
else
{
mOtherFields[tag] = value;
}
}

View file

@ -0,0 +1,26 @@
#pragma once
#include <string>
#include <vector>
#include <map>
class HttpHeader
{
public:
void parse(const std::vector<std::string >& message);
private:
std::string mHost;
std::string mUserAgent;
std::string mAccept;
std::string mAcceptLanguage;
std::string mAcceptEncoding;
std::string mConnection;
std::string mReferer;
std::string mSecFetchDest;
std::string mSecFetchMode;
std::string mSecFetchSite;
std::map<std::string, std::string> mOtherFields;
};

View file

@ -0,0 +1,68 @@
#include "HttpRequest.h"
#include "StringUtils.h"
#include <sstream>
void HttpRequest::parseMessage(const std::string& message)
{
std::stringstream ss(message);
std::string buffer;
bool firstLine {true};
std::vector<std::string> headers;
while(std::getline(ss, buffer, '\n'))
{
if (firstLine)
{
parseFirstLine(buffer);
firstLine = false;
}
else
{
headers.push_back(buffer);
}
}
mHeader.parse(headers);
}
void HttpRequest::parseFirstLine(const std::string& line)
{
bool inPath{false};
bool inMethod{true};
bool inProtocol{false};
for (std::size_t idx=0; idx<line.size();idx++)
{
const auto c = line[idx];
if (inPath)
{
if (StringUtils::IsSpace(c))
{
inPath = false;
inMethod = true;
}
else
{
mMethod.push_back(c);
}
}
else if (inMethod)
{
if (StringUtils::IsSpace(c))
{
inMethod = false;
inProtocol = true;
}
else
{
mPath.push_back(c);
}
}
else if (inProtocol)
{
mProtocolVersion.push_back(c);
}
}
}

View file

@ -0,0 +1,22 @@
#pragma once
#include "HttpHeader.h"
#include <string>
class HttpRequest
{
public:
HttpRequest() = default;
void parseMessage(const std::string& message);
private:
void parseFirstLine(const std::string& line);
HttpHeader mHeader;
std::string mMethod;
std::string mPath;
std::string mProtocolVersion;
};

View file

@ -5,11 +5,6 @@
class HttpResponse
{
std::string mHttpVersion;
std::string mResponseCode;
std::string mContentType;
std::string mBody;
public:
HttpResponse();
@ -23,4 +18,10 @@ public:
std::string GetHeaderString() const;
std::string ToString() const;
private:
std::string mHttpVersion;
std::string mResponseCode;
std::string mContentType;
std::string mBody;
};

View file

@ -0,0 +1,68 @@
#include "SharedMemory.h"
#include "RandomUtils.h"
#include <unistd.h>
#include <sys/types.h>
#include <sys/mman.h>
#include <sys/stat.h>
#include <fcntl.h>
void SharedMemory::allocate(const std::string& namePrefix, std::size_t size)
{
createFile(namePrefix);
if (!mIsValid)
{
return;
}
int ret{-1};
do {
ret = ftruncate(mFileDescriptor, size);
} while (ret < 0 && errno == EINTR);
if (ret < 0)
{
close(mFileDescriptor);
mIsValid = false;
}
}
int SharedMemory::getFileDescriptor() const
{
return mFileDescriptor;
}
bool SharedMemory::isValid() const
{
return mIsValid;
}
void SharedMemory::createFile(const std::string& namePrefix)
{
unsigned retries = 100;
do {
const auto name = getRandomName(namePrefix);
--retries;
const int fd = shm_open(name.c_str(), O_RDWR | O_CREAT | O_EXCL, 0600);
if (fd >= 0)
{
shm_unlink(name.c_str());
mFileDescriptor = fd;
mIsValid = true;
break;
}
} while (retries > 0 && errno == EEXIST);
}
std::string SharedMemory::getRandomName(const std::string& namePrefix) const
{
std::string randomSuffix;
for (const auto entry : RandomUtils::getRandomVecUnsigned(6))
{
randomSuffix += std::to_string(entry);
}
return namePrefix + randomSuffix;
}

View file

@ -0,0 +1,22 @@
#pragma once
#include <string>
class SharedMemory
{
public:
void allocate(const std::string& namePrefix, std::size_t size);
int getFileDescriptor() const;
bool isValid() const;
private:
void createFile(const std::string& namePrefix);
std::string getRandomName(const std::string& namePrefix) const;
int mFileDescriptor{0};
bool mIsValid{false};
};