diff --git a/.gitignore b/.gitignore index d8a0746..a59d439 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,7 @@ .vs/* + +# Excluding the build and executable folders +breadcrumbs/build/* +!breadcrumbs/build/.blank +breadcrumbs/bin/* +!breadcrumbs/bin/.blank diff --git a/README.md b/README.md index e69de29..20da242 100644 --- a/README.md +++ b/README.md @@ -0,0 +1,5 @@ +# Sensory Biofeedback System +## Nich Chan, Greg Foss, Matt Scalzo & Nate Shaw + + +This is our Senior Design Project. Our goal is to create a system that can interpret 3D data and give meaningful feedback through a belt of tactile motors. \ No newline at end of file diff --git a/breadcrumbs/CMakeConfig.h.in b/breadcrumbs/CMakeConfig.h.in new file mode 100644 index 0000000..be22a44 --- /dev/null +++ b/breadcrumbs/CMakeConfig.h.in @@ -0,0 +1,6 @@ +// the configured options and settings for Tutorial + +#define VERSION_MAJOR @Bfs_VERSION_MAJOR@ +#define VERSION_MINOR @Bfs_VERSION_MINOR@ + +#define ALGORITHM_SERVER_PORT @Bfs_ALGORITHM_SERVER_PORT@ \ No newline at end of file diff --git a/breadcrumbs/CMakeLists.txt b/breadcrumbs/CMakeLists.txt new file mode 100644 index 0000000..94f900a --- /dev/null +++ b/breadcrumbs/CMakeLists.txt @@ -0,0 +1,47 @@ +# This file controls the build process. When you save it, VS figures out what types of executables that it builds. +# Then, you can switch the executable that you want to run at the top from the drop down and hit run to build and +# run it. +# + +cmake_minimum_required (VERSION 2.6) + +message("Starting CMAKE") +project (Breadcrumbs) +# The version number. +set (Bfs_VERSION_MAJOR 1) +set (Bfs_VERSION_MINOR 0) + +# Setting paths +message("Setting paths...") +set(CMAKE_SOURCE_DIR ${PROJECT_SOURCE_DIR}/src) # Code directory +set(CMAKE_BINARY_DIR ${PROJECT_SOURCE_DIR}/build) # Object files and such (.o) +set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${PROJECT_SOURCE_DIR}/bin) # Compiled executables for execution and test (.exe) +set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${PROJECT_SOURCE_DIR}/lib) # Compiled libraries (.lib and .dll) +set(CMAKE_INCLUDE_PATH ${PROJECT_SOURCE_DIR}/include) # Publicly accessible header files +message("Root directory: ${PROJECT_SOURCE_DIR}") +message("Source directory: ${CMAKE_SOURCE_DIR}") +message("Build directory: ${CMAKE_BINARY_DIR}") +message("Executable directory: ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}") +message("Library directory: ${CMAKE_LIBRARY_OUTPUT_DIRECTORY}") +message("Header file directory: ${INCLUDES_DIRECTORY}") + +# Configure a header file to pass some of the CMake settings to the source code +set (Bfs_ALGORITHM_SERVER_PORT \"27634\") + +configure_file ( + "${PROJECT_SOURCE_DIR}/CMakeConfig.h.in" + "${CMAKE_INCLUDE_PATH}/CMakeConfig.h" + ) + +# Adding public includes to include search path +include_directories("${CMAKE_INCLUDE_PATH}") +# Adding private include files from source tree +include_directories("${CMAKE_SOURCE_DIR}") + +# puts all .cpp files inside src to the SOURCES variable +# TODO: replace this with a script for collecting cpp files +file(GLOB_RECURSE SOURCES CONFIGURE_DEPENDS "${CMAKE_SOURCE_DIR}/*.cpp") +message("Source files: ${SOURCES}") + +# Adding executables +add_executable(Breadcrumbs ${SOURCES}) diff --git a/breadcrumbs/CMakeSettings.json b/breadcrumbs/CMakeSettings.json new file mode 100644 index 0000000..ae612b0 --- /dev/null +++ b/breadcrumbs/CMakeSettings.json @@ -0,0 +1,16 @@ +{ + "configurations": [ + { + "name": "basic_build", + "generator": "Ninja", + "configurationType": "Debug", + "inheritEnvironments": [ "msvc_x64_x64" ], + "buildRoot": "${projectDir}\\build\\${name}", + "installRoot": "${projectDir}\\install\\${name}", + "cmakeCommandArgs": "", + "buildCommandArgs": "-v", + "ctestCommandArgs": "", + "variables": [] + } + ] +} diff --git a/breadcrumbs/bfs/out_proc/.blank b/breadcrumbs/bfs/out_proc/.blank deleted file mode 100644 index e69de29..0000000 diff --git a/breadcrumbs/bfs/scripts/.blank b/breadcrumbs/bfs/scripts/.blank deleted file mode 100644 index e69de29..0000000 diff --git a/breadcrumbs/algos/.blank b/breadcrumbs/bin/.blank similarity index 100% rename from breadcrumbs/algos/.blank rename to breadcrumbs/bin/.blank diff --git a/breadcrumbs/doc/style/style.cpp b/breadcrumbs/doc/style/style.cpp new file mode 100644 index 0000000..26df8b9 --- /dev/null +++ b/breadcrumbs/doc/style/style.cpp @@ -0,0 +1,20 @@ +/* + +This file correspondes to style.hpp and is an example of +the .cpp files that would correspond to the .hpp file. + +*/ + + +#include "style.hpp" + + +char TestClass::attrTwoTimesTwo() +{ + return c_attrTwo << 1 +} + +int TestClass::getAttrSum() +{ + return c_attrTwo + i_attrOne +} diff --git a/breadcrumbs/doc/style/style.hpp b/breadcrumbs/doc/style/style.hpp new file mode 100644 index 0000000..dd26d76 --- /dev/null +++ b/breadcrumbs/doc/style/style.hpp @@ -0,0 +1,39 @@ +/* + * + * This file contains the style of each programming construct + * to use in this project. + * + * It should be followed to the letter! All spaces are + * necessary! Make sure to take note of camel case and other + * variable naming schemes! + * + */ + +#ifndef STYLE_HPP +#define STYLE_HPP + +#include + +#include "style.hpp" + +// Header File: +class TestClass +{ +public: + // Constructors + TestClass(int AttrOne, char AttrTwo); + // Mutator methods + int getAttrSum(); + char attrTwoTimesTwo(); + void setAttrOne(int newAttrOne) { i_attrOne = newAttrOne } + void setAttrTwo(char newAttrTwo) { c_attrTwo = newAttrTwo } + // Accessor methods + int getAttrOne() { return i_attrOne } + char getAttrTwo() { return c_attrTwo } +private: + // Private variables + int i_attrOne = 0; + char c_attrTwo; +}; + +#endif diff --git a/breadcrumbs/in_procs/.blank b/breadcrumbs/in_procs/.blank deleted file mode 100644 index e69de29..0000000 diff --git a/breadcrumbs/include/AlgoBreadcrumbs.hpp b/breadcrumbs/include/AlgoBreadcrumbs.hpp new file mode 100644 index 0000000..3502ff5 --- /dev/null +++ b/breadcrumbs/include/AlgoBreadcrumbs.hpp @@ -0,0 +1,18 @@ + +#ifndef ALGO_BREADCRUMBS_HPP +#define ALGO_BREADCRUMBS_HPP + +#include "Algorithm.hpp" + +class AlgoBreadcrumbs : public Algorithm +{ +public: + using Algorithm::Algorithm; + + void loop(); + bool loopCondition(); +private: + INT iterations = 1; +}; + +#endif diff --git a/breadcrumbs/include/Algorithm.hpp b/breadcrumbs/include/Algorithm.hpp new file mode 100644 index 0000000..8edd655 --- /dev/null +++ b/breadcrumbs/include/Algorithm.hpp @@ -0,0 +1,20 @@ + +#ifndef ALGORITHM_HPP +#define ALGORITHM_HPP + +#include "AlgorithmServer.hpp" + +class Algorithm +{ +public: + explicit Algorithm(size_t numProcs); + ~Algorithm(); + + virtual void loop() = 0; + virtual bool loopCondition() { return false; }; +private: + size_t numIoProcs = 0; + AlgorithmServer* server; +}; + +#endif diff --git a/breadcrumbs/include/AlgorithmServer.hpp b/breadcrumbs/include/AlgorithmServer.hpp new file mode 100644 index 0000000..85520d0 --- /dev/null +++ b/breadcrumbs/include/AlgorithmServer.hpp @@ -0,0 +1,53 @@ + +#ifndef ALGORITHM_SERVER_HPP +#define ALGORITHM_SERVER_HPP + + +#undef UNICODE + +#define WIN32_LEAN_AND_MEAN + +#include +#include +#include +#include +#include +#include + +#include "CMakeConfig.h" +#include "DataSyncThread.hpp" + +#define ALGORITHM_PORT "10101" +#define MAX_ACCEPT_FAILURES 5 + +#pragma comment (lib, "Ws2_32.lib") + +class AlgorithmServer +{ +public: + AlgorithmServer(size_t numClients); + ~AlgorithmServer(); + + void serverThreadRuntime(); + static DWORD serverThreadInit(LPVOID pThreadArgs) + { + AlgorithmServer* pAlgorithmServerThread = (AlgorithmServer*)pThreadArgs; + pAlgorithmServerThread->serverThreadRuntime(); + return NULL; + } + + // Updates Algorithm key/value store with IO key/value updates + void pollForUpdates(); + void startServer(); + void stopServer(); + +private: + HANDLE hThread; + DWORD dwThreadId; + bool continueThread = false; + + size_t numClients; + std::vector clientThreads; +}; + +#endif diff --git a/breadcrumbs/include/Attribute.hpp b/breadcrumbs/include/Attribute.hpp new file mode 100644 index 0000000..717ae02 --- /dev/null +++ b/breadcrumbs/include/Attribute.hpp @@ -0,0 +1,10 @@ + +#ifndef ATTRIBUTE_HPP +#define ATTRIBUTE_HPP + +typedef struct BinaryAttributeStructure { + char key[8]; + unsigned char length[2]; +} bAttrib; + +#endif \ No newline at end of file diff --git a/breadcrumbs/include/CMakeConfig.h b/breadcrumbs/include/CMakeConfig.h new file mode 100644 index 0000000..b625ea5 --- /dev/null +++ b/breadcrumbs/include/CMakeConfig.h @@ -0,0 +1,6 @@ +// the configured options and settings for Tutorial + +#define VERSION_MAJOR 1 +#define VERSION_MINOR 0 + +#define ALGORITHM_SERVER_PORT "27634" diff --git a/breadcrumbs/include/DataSyncThread.hpp b/breadcrumbs/include/DataSyncThread.hpp new file mode 100644 index 0000000..ba17598 --- /dev/null +++ b/breadcrumbs/include/DataSyncThread.hpp @@ -0,0 +1,51 @@ + +#ifndef DATA_SYNC_THREAD_HPP +#define DATA_SYNC_THREAD_HPP + +#define WIN32_LEAN_AND_MEAN + +#include +#include +#include +#include +#include + +#include "Attribute.hpp" +#include "CMakeConfig.h" + +// Need to link with Ws2_32.lib, Mswsock.lib, and Advapi32.lib +#pragma comment (lib, "Ws2_32.lib") +#pragma comment (lib, "Mswsock.lib") +#pragma comment (lib, "AdvApi32.lib") + +/* +This class contains the thread for communicating back and forth along a socket to sync attributes + +*/ +class DataSyncThread +{ +private: + SOCKET sock; + HANDLE hThread; + DWORD dwThreadId; + bool continueThread = false; +public: + DataSyncThread(SOCKET s) { sock = s; }; + + // Synchronous functions + void threadRuntime(); + static DWORD threadInit(LPVOID pThreadArgs) + { + DataSyncThread* pDataSyncThread = (DataSyncThread*)pThreadArgs; + pDataSyncThread->threadRuntime(); + return NULL; + } + int recvBytes(void* buffer, size_t numBytes); + + // Async control + void startComms(); + bool stopComms(); + int connectToAlgorithm(char* serverName); +}; + +#endif \ No newline at end of file diff --git a/breadcrumbs/include/IOProcessor.hpp b/breadcrumbs/include/IOProcessor.hpp new file mode 100644 index 0000000..00fead2 --- /dev/null +++ b/breadcrumbs/include/IOProcessor.hpp @@ -0,0 +1,26 @@ + +#ifndef IO_PROCESSOR_HPP +#define IO_PROCESSOR_HPP + + +#include +#include + + +/* +This class is the class that abstracts the io processor side of the data exchange between +IO processors and algorithms + +*/ +class IOProcessor +{ +public: + IOProcessor() {}; + + // Async control + unsigned int startComms(); + bool stopComms(); + +}; + +#endif diff --git a/breadcrumbs/include/VirtualOutputProcessor.hpp b/breadcrumbs/include/VirtualOutputProcessor.hpp new file mode 100644 index 0000000..067fef4 --- /dev/null +++ b/breadcrumbs/include/VirtualOutputProcessor.hpp @@ -0,0 +1,19 @@ + +#ifndef VIRTUAL_OUTPUT_PROCESSOR_HPP +#define VIRTUAL_OUTPUT_PROCESSOR_HPP + + +#include + +#include "IOProcessor.hpp" + + +class VirtualOutputProcessor : public IOProcessor +{ +public: + using IOProcessor::IOProcessor; + + void threadRuntime(IOProcessor* ioProc); +}; + +#endif diff --git a/breadcrumbs/out_procs/.blank b/breadcrumbs/out_procs/.blank deleted file mode 100644 index e69de29..0000000 diff --git a/breadcrumbs/scripts/startbfs.py b/breadcrumbs/scripts/startbfs.py new file mode 100644 index 0000000..618e877 --- /dev/null +++ b/breadcrumbs/scripts/startbfs.py @@ -0,0 +1,24 @@ + +import os +import multiprocessing as mp +import subprocess + + +def start_program(command): + cmd_list = command.split(" ") + return subprocess.call(cmd_list) + + +def start_program_no_hang(command): + print("Running %s from cwd %s" % (command, os.getcwd())) + proc = mp.Process(target=start_program, args=(command,)) + proc.start() + return proc + + +def main(): + start_program_no_hang("start cmd.exe /k \"..\\bin\\Breadcrumbs.exe\"") + + +if __name__ == "__main__": + main() diff --git a/breadcrumbs/src/Breadcrumbs.cpp b/breadcrumbs/src/Breadcrumbs.cpp new file mode 100644 index 0000000..cec95a9 --- /dev/null +++ b/breadcrumbs/src/Breadcrumbs.cpp @@ -0,0 +1,19 @@ + +#include + +#include "AlgoBreadcrumbs.hpp" +#include "VirtualOutputProcessor.hpp" + + +int main() +{ + Algorithm* algorithm = new AlgoBreadcrumbs(1); + + // Loop + while (algorithm->loopCondition()) + { + algorithm->loop(); + } + + return 0; +} diff --git a/breadcrumbs/bfs/.blank b/breadcrumbs/src/algos/.blank similarity index 100% rename from breadcrumbs/bfs/.blank rename to breadcrumbs/src/algos/.blank diff --git a/breadcrumbs/src/algos/AlgoBreadcrumbs.cpp b/breadcrumbs/src/algos/AlgoBreadcrumbs.cpp new file mode 100644 index 0000000..7278eb5 --- /dev/null +++ b/breadcrumbs/src/algos/AlgoBreadcrumbs.cpp @@ -0,0 +1,13 @@ + +#include "AlgoBreadcrumbs.hpp" + + +void AlgoBreadcrumbs::loop() +{ + printf("Breadcrumbs algorithm loop!\n"); +} + +bool AlgoBreadcrumbs::loopCondition() +{ + return --iterations >= 0; +} diff --git a/breadcrumbs/src/algos/Algorithm.cpp b/breadcrumbs/src/algos/Algorithm.cpp new file mode 100644 index 0000000..7ae56b8 --- /dev/null +++ b/breadcrumbs/src/algos/Algorithm.cpp @@ -0,0 +1,15 @@ + +#include "Algorithm.hpp" + +Algorithm::Algorithm(size_t numProcs) +{ + numIoProcs = numProcs; + server = new AlgorithmServer(numProcs); + + server->startServer(); +} + +Algorithm::~Algorithm() +{ + delete server; +} diff --git a/breadcrumbs/src/comms/AlgorithmServer.cpp b/breadcrumbs/src/comms/AlgorithmServer.cpp new file mode 100644 index 0000000..61f43db --- /dev/null +++ b/breadcrumbs/src/comms/AlgorithmServer.cpp @@ -0,0 +1,159 @@ + +#include "AlgorithmServer.hpp" + +AlgorithmServer::AlgorithmServer(size_t numClients) +{ + this->hThread = NULL; + this->dwThreadId = 0; + this->numClients = numClients; + + clientThreads.reserve(numClients); +} + +AlgorithmServer::~AlgorithmServer() +{ + this->stopServer(); +} + +void AlgorithmServer::serverThreadRuntime() +{ + int iResult; + + SOCKET ListenSocket = INVALID_SOCKET; + SOCKET ClientSocket = INVALID_SOCKET; + + struct addrinfo* result = NULL; + struct addrinfo hints; + + int iSendResult; + + ZeroMemory(&hints, sizeof(hints)); + hints.ai_family = AF_INET; + hints.ai_socktype = SOCK_STREAM; + hints.ai_protocol = IPPROTO_TCP; + hints.ai_flags = AI_PASSIVE; + + // Resolve the server address and port + iResult = getaddrinfo(NULL, ALGORITHM_SERVER_PORT, &hints, &result); + if (iResult != 0) { + printf("getaddrinfo failed with error: %d\n", iResult); + WSACleanup(); + return; + } + + // Create a SOCKET for connecting to server + ListenSocket = socket(result->ai_family, result->ai_socktype, result->ai_protocol); + if (ListenSocket == INVALID_SOCKET) { + printf("socket failed with error: %ld\n", WSAGetLastError()); + freeaddrinfo(result); + WSACleanup(); + return; + } + + // Setup the TCP listening socket + iResult = bind(ListenSocket, result->ai_addr, (int)result->ai_addrlen); + if (iResult == SOCKET_ERROR) { + printf("bind failed with error: %d\n", WSAGetLastError()); + freeaddrinfo(result); + closesocket(ListenSocket); + WSACleanup(); + return; + } + freeaddrinfo(result); + + iResult = listen(ListenSocket, SOMAXCONN); + if (iResult == SOCKET_ERROR) { + printf("listen failed with error: %d\n", WSAGetLastError()); + closesocket(ListenSocket); + WSACleanup(); + return; + } + + // Select stuff + FD_SET readSet; + + int AcceptFailures = 0; + // Accept a client socket + while (continueThread) + { + int fds; + + FD_ZERO(&readSet); + FD_SET(ListenSocket, &readSet); + + if ((fds = select(0, &readSet, NULL, NULL, NULL)) == SOCKET_ERROR) + { + printf("select() returned with error %d\n", WSAGetLastError()); + break; + } + + if (fds != 0) + { + ClientSocket = accept(ListenSocket, NULL, NULL); + if (ClientSocket == INVALID_SOCKET) { + printf("accept failed with error: %d\n", WSAGetLastError()); + AcceptFailures++; + if (AcceptFailures >= MAX_ACCEPT_FAILURES) + break; + } + else { + AcceptFailures = 0; + } + + // Creating a new Data sync thread + if (clientThreads.size() < numClients) { + DataSyncThread client = *new DataSyncThread(ClientSocket); + clientThreads.push_back(client); + client.startComms(); + } + else { + printf("Client attempted connection when (%d) clients are already connected", numClients); + } + } + } + + // cleanup + closesocket(ListenSocket); + WSACleanup(); + continueThread = false; + return; +} + +void AlgorithmServer::pollForUpdates() +{ + /* + Polls DataSyncThreads for new updates + Updates master storage accordingly + */ + for (DataSyncThread dst : clientThreads) + { + // TODO: Implement this! + } +} + +void AlgorithmServer::startServer() +{ + + // Initialize Winsock + WSADATA wsaData; + int result; + if (result = WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) { + printf("WSAStartup failed with error: %d\n", result); + return; + } + + // Starts the server thread: + continueThread = true; + hThread = CreateThread( + NULL, // default security attributes + 0, // use default stack size + serverThreadInit, // thread function name + this, // argument to thread function + 0, // use default creation flags + &dwThreadId); // returns the thread identifier +} + +void AlgorithmServer::stopServer() +{ + continueThread = false; +} diff --git a/breadcrumbs/src/comms/DataSyncThread.cpp b/breadcrumbs/src/comms/DataSyncThread.cpp new file mode 100644 index 0000000..a5efa72 --- /dev/null +++ b/breadcrumbs/src/comms/DataSyncThread.cpp @@ -0,0 +1,144 @@ + +#include "DataSyncThread.hpp" + + +void DataSyncThread::threadRuntime() +{ + /* + Handles the data sync between the other end of the socket + */ + int iResult = 1; + + while (continueThread && iResult > 0) + { + // Master while loop that will receive incoming messages + char commandByte; + iResult = recvBytes(&commandByte, 1); + if (iResult <= 0) + break; + + switch (commandByte) + { + case 0: + bAttrib attrib; + iResult = recvBytes(&attrib, sizeof(bAttrib)); + if (iResult <= 0) + break; + printf("Attribute update received, key:%.8s len:%us\n", attrib.key, (unsigned short) attrib.length); + void* value = malloc((unsigned short)attrib.length); + iResult = recvBytes(value, (unsigned short)attrib.length); + if (iResult <= 0) + break; + // TODO: Storing the attrib update + + break; + } + } + + continueThread = false; +} + +int DataSyncThread::recvBytes(void* buffer, size_t numBytes) +{ + size_t bytesRecved = 0; + int iResult; + + while (bytesRecved < numBytes) + { + iResult = recv(sock, ((char*) buffer) + bytesRecved, numBytes - bytesRecved, 0); + if (iResult < 0) + { + printf("recv failed with error: %d\n", WSAGetLastError()); + return iResult; + } + else if (iResult == 0) { + printf("recv returned 0, connection closed.\n"); + return iResult; + } + else + bytesRecved += iResult; + } + return numBytes; +} + +void DataSyncThread::startComms() +{ + /* + Initializes the communication thread + */ + continueThread = true; + hThread = CreateThread( + NULL, // default security attributes + 0, // use default stack size + threadInit, // thread function name + this, // argument to thread function + 0, // use default creation flags + &dwThreadId); // returns the thread identifier +} + +bool DataSyncThread::stopComms() +{ + /* + Stops the communication thread + */ + continueThread = false; + return true; +} + +int DataSyncThread::connectToAlgorithm(char* serverName) +{ + sock = INVALID_SOCKET; + WSADATA wsaData; + struct addrinfo* result = NULL,* ptr = NULL, hints; + int iResult; + + // Initialize Winsock + iResult = WSAStartup(MAKEWORD(2, 2), &wsaData); + if (iResult != 0) { + printf("WSAStartup failed with error: %d\n", iResult); + return 1; + } + + ZeroMemory(&hints, sizeof(hints)); + hints.ai_family = AF_UNSPEC; + hints.ai_socktype = SOCK_STREAM; + hints.ai_protocol = IPPROTO_TCP; + + // Resolve the server address and port + iResult = getaddrinfo(serverName, ALGORITHM_SERVER_PORT, &hints, &result); + if (iResult != 0) { + printf("getaddrinfo failed with error: %d\n", iResult); + WSACleanup(); + return 1; + } + + // Attempt to connect to an address until one succeeds + for (ptr = result; ptr != NULL; ptr = ptr->ai_next) { + + // Create a SOCKET for connecting to server + sock = socket(ptr->ai_family, ptr->ai_socktype, + ptr->ai_protocol); + if (sock == INVALID_SOCKET) { + printf("socket failed with error: %ld\n", WSAGetLastError()); + WSACleanup(); + return 1; + } + + // Connect to server. + iResult = connect(sock, ptr->ai_addr, (int)ptr->ai_addrlen); + if (iResult == SOCKET_ERROR) { + closesocket(sock); + sock = INVALID_SOCKET; + continue; + } + break; + } + + freeaddrinfo(result); + + if (sock == INVALID_SOCKET) { + printf("Unable to connect to server!\n"); + WSACleanup(); + return 1; + } +} diff --git a/breadcrumbs/bfs/algo/.blank b/breadcrumbs/src/config/.blank similarity index 100% rename from breadcrumbs/bfs/algo/.blank rename to breadcrumbs/src/config/.blank diff --git a/breadcrumbs/src/io/IOProcessor.cpp b/breadcrumbs/src/io/IOProcessor.cpp new file mode 100644 index 0000000..437de23 --- /dev/null +++ b/breadcrumbs/src/io/IOProcessor.cpp @@ -0,0 +1,4 @@ + +#include "IOProcessor.hpp" + + diff --git a/breadcrumbs/bfs/in_proc/.blank b/breadcrumbs/src/io/in_procs/.blank similarity index 100% rename from breadcrumbs/bfs/in_proc/.blank rename to breadcrumbs/src/io/in_procs/.blank diff --git a/breadcrumbs/bfs/io_proc/.blank b/breadcrumbs/src/io/out_procs/.blank similarity index 100% rename from breadcrumbs/bfs/io_proc/.blank rename to breadcrumbs/src/io/out_procs/.blank diff --git a/breadcrumbs/src/io/out_procs/VirtualOutputProcessor.cpp b/breadcrumbs/src/io/out_procs/VirtualOutputProcessor.cpp new file mode 100644 index 0000000..01bf3cc --- /dev/null +++ b/breadcrumbs/src/io/out_procs/VirtualOutputProcessor.cpp @@ -0,0 +1,8 @@ + +#include "VirtualOutputProcessor.hpp" + + +void VirtualOutputProcessor::threadRuntime(IOProcessor* ioProc) +{ + printf("VirtualOutputProcessor started.\n"); +} diff --git a/breadcrumbs/bfs/lib/.blank b/breadcrumbs/src/logging/.blank similarity index 100% rename from breadcrumbs/bfs/lib/.blank rename to breadcrumbs/src/logging/.blank