diff --git a/CMakeLists.txt b/CMakeLists.txt index a3507ef..2fc124d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -68,6 +68,7 @@ set(SERVER_SRCS src/server/rccpp.cpp src/impl/fs.cpp src/impl/event.cpp + src/impl/tcpsocket.cpp ) add_executable(${SERVER_EXE_NAME} ${SERVER_SRCS}) TARGET_LINK_LIBRARIES(${SERVER_EXE_NAME} diff --git a/design.txt b/design.txt index 4e8cb37..dec0b16 100644 --- a/design.txt +++ b/design.txt @@ -49,3 +49,6 @@ name->type registry is used for determining numeric packet types. Data is freeform. Types 0...100 are reserved for initialization. +Core uses cereal's portable binary serialization. + + diff --git a/share/builtin/network/server/init.cpp b/share/builtin/network/server/init.cpp new file mode 100644 index 0000000..2369a89 --- /dev/null +++ b/share/builtin/network/server/init.cpp @@ -0,0 +1,48 @@ +#include "interface/module.h" +#include "interface/server.h" +#include "interface/event.h" +#include "interface/tcpsocket.h" +//#include "network/include/api.h" +#include + +using interface::Event; + +namespace network { + +struct Module: public interface::Module +{ + interface::Server *m_server; + sp_ m_socket; + + Module(interface::Server *server): + m_server(server), + m_socket(interface::createTCPSocket()) + { + std::cout<<"network construct"<bind_fd(address, port)){ + std::cerr<<"Failed to bind to "< +#include +#include +#include +#include +#include +#include // strerror() +#include +#include +#include + +namespace interface { + +const unsigned char prefix[] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xFF, 0xFF}; + +bool sockaddr_to_bytes(const sockaddr_storage* ptr, sv_& to) +{ + if(ptr->ss_family == AF_INET) + { + uchar* u = (uchar*)&((struct sockaddr_in*)ptr)->sin_addr.s_addr; + to.assign(u, u + 4); + return true; + } + else if(ptr->ss_family == AF_INET6) + { + uchar* u = (uchar*)&((struct sockaddr_in6*)ptr)->sin6_addr.s6_addr; + if(memcmp(prefix, u, sizeof(prefix)) == 0){ + to.assign(u + 12, u + 16); + return true; + } + to.assign(u, u + 16); + return true; + } + + return false; +}; + +std::string address_bytes_to_string(const sv_ &ip) +{ + std::ostringstream os; + for(size_t i=0; iai_next, i++) + { + std::cerr<<"Trying addrinfo #"<ai_family, res->ai_socktype, res->ai_protocol); + if(try_fd == -1){ + std::cerr<<"socket: "<ai_addr, res->ai_addrlen) == -1){ + std::cerr<<"connect: "<ai_next, i++) + { + //std::cerr<<"Trying addrinfo #"<ai_family, res->ai_socktype, res->ai_protocol); + if(try_fd == -1){ + //std::cerr<<"socket: "<ai_family == AF_INET6){ + int val = 1; + setsockopt(try_fd, IPPROTO_IPV6, IPV6_V6ONLY, &val, sizeof(val)); + } + if(bind(try_fd, res->ai_addr, res->ai_addrlen) == -1){ + //std::cerr<<"bind: "< a; + if(!sockaddr_to_bytes(&sa, a)) + return ""; + return address_bytes_to_string(a); + } + ss_ get_remote_address() const + { + if(m_fd == -1) + return ""; + struct sockaddr_storage sa; + socklen_t sa_len = sizeof(sa); + if(getsockname(m_fd, (sockaddr*)&sa, &sa_len) == -1) + return ""; + sv_ a; + if(!sockaddr_to_bytes(&sa, a)) + return ""; + return address_bytes_to_string(a); + } +}; + +TCPSocket* createTCPSocket() +{ + return new CTCPSocket(); +} + +} diff --git a/src/interface/server.h b/src/interface/server.h index 8b5b5fa..fd26337 100644 --- a/src/interface/server.h +++ b/src/interface/server.h @@ -10,6 +10,7 @@ namespace interface virtual ~Server(){} virtual void load_module(const ss_ &module_name, const ss_ &path) = 0; virtual ss_ get_modules_path() = 0; + virtual ss_ get_builtin_modules_path() = 0; virtual Module* get_module(const ss_ &module_name) = 0; }; } diff --git a/src/interface/tcpsocket.h b/src/interface/tcpsocket.h new file mode 100644 index 0000000..1f81468 --- /dev/null +++ b/src/interface/tcpsocket.h @@ -0,0 +1,24 @@ +#pragma once +#include "core/types.h" + +namespace interface +{ + struct TCPSocket + { + virtual ~TCPSocket(){} + virtual int fd() const = 0; + virtual bool good() const = 0; + virtual void close_fd() = 0; + virtual bool listen_fd() = 0; + virtual bool connect_fd(const ss_ &address, const ss_ &port) = 0; + // Special values "any4", "any6" and "any" + virtual bool bind_fd(const ss_ &address, const ss_ &port) = 0; + virtual bool accept_fd(const TCPSocket &listener) = 0; + virtual bool send_fd(const ss_ &data) = 0; + virtual ss_ get_local_address() const = 0; + virtual ss_ get_remote_address() const = 0; + }; + + TCPSocket* createTCPSocket(); +} + diff --git a/src/server/config.h b/src/server/config.h index e39e62c..8676cd1 100644 --- a/src/server/config.h +++ b/src/server/config.h @@ -7,6 +7,7 @@ namespace server { ss_ rccpp_build_path = "../cache/rccpp_build"; ss_ interface_path = "../src/interface"; + ss_ share_path = "../share"; }; } diff --git a/src/server/main.cpp b/src/server/main.cpp index 044750a..f982449 100644 --- a/src/server/main.cpp +++ b/src/server/main.cpp @@ -12,13 +12,14 @@ int main(int argc, char *argv[]) std::string module_path; - const char opts[100] = "hm:r:i:"; + const char opts[100] = "hm:r:i:S:"; const char usagefmt[1000] = "Usage: %s [OPTION]...\n" " -h Show this help\n" " -m [module_path] Specify module path\n" " -r [rccpp_build_path]Specify runtime compiled C++ build path\n" " -i [interface_path] Specify path to interface headers\n" + " -S [share_path] Specify path to share/\n" ; int c; @@ -41,6 +42,10 @@ int main(int argc, char *argv[]) fprintf(stderr, "INFO: config.interface_path: %s\n", c55_optarg); config.interface_path = c55_optarg; break; + case 'S': + fprintf(stderr, "INFO: config.share_path: %s\n", c55_optarg); + config.share_path = c55_optarg; + break; default: fprintf(stderr, "ERROR: Invalid command-line argument\n"); fprintf(stderr, usagefmt, argv[0]); diff --git a/src/server/state.cpp b/src/server/state.cpp index a64e378..67f92ca 100644 --- a/src/server/state.cpp +++ b/src/server/state.cpp @@ -57,6 +57,11 @@ struct CState: public State, public interface::Server return m_modules_path; } + ss_ get_builtin_modules_path() + { + return g_server_config.share_path+"/builtin"; + } + interface::Module* get_module(const ss_ &module_name) { auto it = m_modules.find(module_name); diff --git a/test/testmodules/__loader/server/init.cpp b/test/testmodules/__loader/server/init.cpp index 19c7315..945a058 100644 --- a/test/testmodules/__loader/server/init.cpp +++ b/test/testmodules/__loader/server/init.cpp @@ -2,7 +2,6 @@ #include "interface/server.h" #include "interface/fs.h" #include "interface/event.h" -//#include #include using interface::Event; @@ -35,10 +34,13 @@ struct Module: public interface::Module void load_modules() { + m_server->load_module("network", m_server->get_builtin_modules_path()+"/network"); + sv_ load_list = {"test1", "test2"}; for(const ss_ &name : load_list){ m_server->load_module(name, m_server->get_modules_path()+"/"+name); } + /*// TODO: Dependencies auto list = interface::getGlobalFilesystem()->list_directory(m_server->get_modules_path()); for(const interface::Filesystem::Node &n : list){