added a clang-format file, updated the whole codebase

This commit is contained in:
Michele Caini 2022-03-08 12:59:19 +01:00
parent 25b8fad800
commit 5664b04075
82 changed files with 850 additions and 1599 deletions

41
.clang-format Normal file
View File

@ -0,0 +1,41 @@
BasedOnStyle: llvm
---
AccessModifierOffset: -4
AlignEscapedNewlines: DontAlign
AllowShortBlocksOnASingleLine: Empty
AllowShortEnumsOnASingleLine: true
AllowShortFunctionsOnASingleLine: Empty
AllowShortIfStatementsOnASingleLine: WithoutElse
AllowShortLoopsOnASingleLine: true
AlwaysBreakTemplateDeclarations: Yes
BreakBeforeBinaryOperators: NonAssignment
BreakBeforeTernaryOperators: true
ColumnLimit: 0
DerivePointerAlignment: false
IncludeCategories:
- Regex: '<[[:alnum:]_]+>'
Priority: 1
- Regex: '<(gtest|gmock)/'
Priority: 2
- Regex: '<[[:alnum:]_./]+>'
Priority: 3
- Regex: '<entt/'
Priority: 4
- Regex: '.*'
Priority: 5
IndentPPDirectives: AfterHash
IndentWidth: 4
KeepEmptyLinesAtTheStartOfBlocks: false
Language: Cpp
PointerAlignment: Right
SpaceAfterCStyleCast: false
SpaceAfterTemplateKeyword: false
SpaceAroundPointerQualifiers: After
SpaceBeforeCaseColon: false
SpaceBeforeCtorInitializerColon: false
SpaceBeforeInheritanceColon: false
SpaceBeforeParens: Never
SpaceBeforeRangeBasedForLoopColon: false
Standard: Latest
TabWidth: 4
UseTab: Never

View File

@ -1,27 +1,22 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "async.h" # include "async.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE void AsyncHandle::sendCallback(uv_async_t *handle) { UVW_INLINE void AsyncHandle::sendCallback(uv_async_t *handle) {
AsyncHandle &async = *(static_cast<AsyncHandle *>(handle->data)); AsyncHandle &async = *(static_cast<AsyncHandle *>(handle->data));
async.publish(AsyncEvent{}); async.publish(AsyncEvent{});
} }
UVW_INLINE bool AsyncHandle::init() { UVW_INLINE bool AsyncHandle::init() {
return initialize(&uv_async_init, &sendCallback); return initialize(&uv_async_init, &sendCallback);
} }
UVW_INLINE void AsyncHandle::send() { UVW_INLINE void AsyncHandle::send() {
invoke(&uv_async_send, get()); invoke(&uv_async_send, get());
} }
} // namespace uvw
}

View File

@ -1,15 +1,12 @@
#ifndef UVW_ASYNC_INCLUDE_H #ifndef UVW_ASYNC_INCLUDE_H
#define UVW_ASYNC_INCLUDE_H #define UVW_ASYNC_INCLUDE_H
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "loop.h" #include "loop.h"
namespace uvw { namespace uvw {
/** /**
* @brief AsyncEvent event. * @brief AsyncEvent event.
* *
@ -17,7 +14,6 @@ namespace uvw {
*/ */
struct AsyncEvent {}; struct AsyncEvent {};
/** /**
* @brief The AsyncHandle handle. * @brief The AsyncHandle handle.
* *
@ -55,12 +51,10 @@ public:
void send(); void send();
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "async.cpp" # include "async.cpp"
#endif #endif
#endif // UVW_ASYNC_INCLUDE_H #endif // UVW_ASYNC_INCLUDE_H

View File

@ -1,32 +1,26 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "check.h" # include "check.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE void CheckHandle::startCallback(uv_check_t *handle) { UVW_INLINE void CheckHandle::startCallback(uv_check_t *handle) {
CheckHandle &check = *(static_cast<CheckHandle *>(handle->data)); CheckHandle &check = *(static_cast<CheckHandle *>(handle->data));
check.publish(CheckEvent{}); check.publish(CheckEvent{});
} }
UVW_INLINE bool CheckHandle::init() { UVW_INLINE bool CheckHandle::init() {
return initialize(&uv_check_init); return initialize(&uv_check_init);
} }
UVW_INLINE void CheckHandle::start() { UVW_INLINE void CheckHandle::start() {
invoke(&uv_check_start, get(), &startCallback); invoke(&uv_check_start, get(), &startCallback);
} }
UVW_INLINE void CheckHandle::stop() { UVW_INLINE void CheckHandle::stop() {
invoke(&uv_check_stop, get()); invoke(&uv_check_stop, get());
} }
} // namespace uvw
}

View File

@ -1,15 +1,12 @@
#ifndef UVW_CHECK_INCLUDE_H #ifndef UVW_CHECK_INCLUDE_H
#define UVW_CHECK_INCLUDE_H #define UVW_CHECK_INCLUDE_H
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "loop.h" #include "loop.h"
namespace uvw { namespace uvw {
/** /**
* @brief CheckEvent event. * @brief CheckEvent event.
* *
@ -17,7 +14,6 @@ namespace uvw {
*/ */
struct CheckEvent {}; struct CheckEvent {};
/** /**
* @brief The CheckHandle handle. * @brief The CheckHandle handle.
* *
@ -52,12 +48,10 @@ public:
void stop(); void stop();
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "check.cpp" # include "check.cpp"
#endif #endif
#endif // UVW_CHECK_INCLUDE_H #endif // UVW_CHECK_INCLUDE_H

View File

@ -1,12 +1,10 @@
#ifndef UVW_CONFIG_H #ifndef UVW_CONFIG_H
#define UVW_CONFIG_H #define UVW_CONFIG_H
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#define UVW_INLINE inline # define UVW_INLINE inline
#else #else
#define UVW_INLINE # define UVW_INLINE
#endif #endif
#endif #endif

View File

@ -1,100 +1,73 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "dns.h" # include "dns.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE AddrInfoEvent::AddrInfoEvent(std::unique_ptr<addrinfo, Deleter> addr) UVW_INLINE AddrInfoEvent::AddrInfoEvent(std::unique_ptr<addrinfo, Deleter> addr)
: data{std::move(addr)} : data{std::move(addr)} {}
{}
UVW_INLINE NameInfoEvent::NameInfoEvent(const char *host, const char *serv) UVW_INLINE NameInfoEvent::NameInfoEvent(const char *host, const char *serv)
: hostname{host}, service{serv} : hostname{host}, service{serv} {}
{}
UVW_INLINE void GetAddrInfoReq::addrInfoCallback(uv_getaddrinfo_t *req, int status, addrinfo *res) { UVW_INLINE void GetAddrInfoReq::addrInfoCallback(uv_getaddrinfo_t *req, int status, addrinfo *res) {
auto ptr = reserve(req); if(auto ptr = reserve(req); status) {
if(status) {
ptr->publish(ErrorEvent{status}); ptr->publish(ErrorEvent{status});
} else { } else {
auto data = std::unique_ptr<addrinfo, void (*)(addrinfo *)>{res, [](addrinfo *addr) { auto data = std::unique_ptr<addrinfo, void (*)(addrinfo *)>{res, [](addrinfo *addr) { uv_freeaddrinfo(addr); }};
uv_freeaddrinfo(addr);
}};
ptr->publish(AddrInfoEvent{std::move(data)}); ptr->publish(AddrInfoEvent{std::move(data)});
} }
} }
UVW_INLINE void GetAddrInfoReq::nodeAddrInfo(const char *node, const char *service, addrinfo *hints) { UVW_INLINE void GetAddrInfoReq::nodeAddrInfo(const char *node, const char *service, addrinfo *hints) {
invoke(&uv_getaddrinfo, parent(), get(), &addrInfoCallback, node, service, hints); invoke(&uv_getaddrinfo, parent(), get(), &addrInfoCallback, node, service, hints);
} }
UVW_INLINE auto GetAddrInfoReq::nodeAddrInfoSync(const char *node, const char *service, addrinfo *hints) { UVW_INLINE auto GetAddrInfoReq::nodeAddrInfoSync(const char *node, const char *service, addrinfo *hints) {
auto req = get(); auto req = get();
auto err = uv_getaddrinfo(parent(), req, nullptr, node, service, hints); auto err = uv_getaddrinfo(parent(), req, nullptr, node, service, hints);
auto data = std::unique_ptr<addrinfo, void (*)(addrinfo *)>{req->addrinfo, [](addrinfo *addr) { auto data = std::unique_ptr<addrinfo, void (*)(addrinfo *)>{req->addrinfo, [](addrinfo *addr) { uv_freeaddrinfo(addr); }};
uv_freeaddrinfo(addr);
}};
return std::make_pair(!err, std::move(data)); return std::make_pair(!err, std::move(data));
} }
UVW_INLINE void GetAddrInfoReq::nodeAddrInfo(const std::string &node, addrinfo *hints) { UVW_INLINE void GetAddrInfoReq::nodeAddrInfo(const std::string &node, addrinfo *hints) {
nodeAddrInfo(node.data(), nullptr, hints); nodeAddrInfo(node.data(), nullptr, hints);
} }
UVW_INLINE std::pair<bool, std::unique_ptr<addrinfo, GetAddrInfoReq::Deleter>> GetAddrInfoReq::nodeAddrInfoSync(const std::string &node, addrinfo *hints) { UVW_INLINE std::pair<bool, std::unique_ptr<addrinfo, GetAddrInfoReq::Deleter>> GetAddrInfoReq::nodeAddrInfoSync(const std::string &node, addrinfo *hints) {
return nodeAddrInfoSync(node.data(), nullptr, hints); return nodeAddrInfoSync(node.data(), nullptr, hints);
} }
UVW_INLINE void GetAddrInfoReq::serviceAddrInfo(const std::string &service, addrinfo *hints) { UVW_INLINE void GetAddrInfoReq::serviceAddrInfo(const std::string &service, addrinfo *hints) {
nodeAddrInfo(nullptr, service.data(), hints); nodeAddrInfo(nullptr, service.data(), hints);
} }
UVW_INLINE std::pair<bool, std::unique_ptr<addrinfo, GetAddrInfoReq::Deleter>> GetAddrInfoReq::serviceAddrInfoSync(const std::string &service, addrinfo *hints) { UVW_INLINE std::pair<bool, std::unique_ptr<addrinfo, GetAddrInfoReq::Deleter>> GetAddrInfoReq::serviceAddrInfoSync(const std::string &service, addrinfo *hints) {
return nodeAddrInfoSync(nullptr, service.data(), hints); return nodeAddrInfoSync(nullptr, service.data(), hints);
} }
UVW_INLINE void GetAddrInfoReq::addrInfo(const std::string &node, const std::string &service, addrinfo *hints) { UVW_INLINE void GetAddrInfoReq::addrInfo(const std::string &node, const std::string &service, addrinfo *hints) {
nodeAddrInfo(node.data(), service.data(), hints); nodeAddrInfo(node.data(), service.data(), hints);
} }
UVW_INLINE std::pair<bool, std::unique_ptr<addrinfo, GetAddrInfoReq::Deleter>> GetAddrInfoReq::addrInfoSync(const std::string &node, const std::string &service, addrinfo *hints) { UVW_INLINE std::pair<bool, std::unique_ptr<addrinfo, GetAddrInfoReq::Deleter>> GetAddrInfoReq::addrInfoSync(const std::string &node, const std::string &service, addrinfo *hints) {
return nodeAddrInfoSync(node.data(), service.data(), hints); return nodeAddrInfoSync(node.data(), service.data(), hints);
} }
UVW_INLINE void GetNameInfoReq::nameInfoCallback(uv_getnameinfo_t *req, int status, const char *hostname, const char *service) { UVW_INLINE void GetNameInfoReq::nameInfoCallback(uv_getnameinfo_t *req, int status, const char *hostname, const char *service) {
auto ptr = reserve(req); if(auto ptr = reserve(req); status) {
if(status) {
ptr->publish(ErrorEvent{status}); ptr->publish(ErrorEvent{status});
} else { } else {
ptr->publish(NameInfoEvent{hostname, service}); ptr->publish(NameInfoEvent{hostname, service});
} }
} }
UVW_INLINE void GetNameInfoReq::nameInfo(const sockaddr &addr, int flags) { UVW_INLINE void GetNameInfoReq::nameInfo(const sockaddr &addr, int flags) {
invoke(&uv_getnameinfo, parent(), get(), &nameInfoCallback, &addr, flags); invoke(&uv_getnameinfo, parent(), get(), &nameInfoCallback, &addr, flags);
} }
template<typename I> template<typename I>
UVW_INLINE void GetNameInfoReq::nameInfo(const std::string &ip, unsigned int port, int flags) { UVW_INLINE void GetNameInfoReq::nameInfo(const std::string &ip, unsigned int port, int flags) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -113,7 +86,6 @@ UVW_INLINE std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq
return std::make_pair(!err, std::make_pair(req->host, req->service)); return std::make_pair(!err, std::make_pair(req->host, req->service));
} }
template<typename I> template<typename I>
UVW_INLINE std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::nameInfoSync(const std::string &ip, unsigned int port, int flags) { UVW_INLINE std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::nameInfoSync(const std::string &ip, unsigned int port, int flags) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -121,13 +93,11 @@ UVW_INLINE std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq
return nameInfoSync(reinterpret_cast<const sockaddr &>(addr), flags); return nameInfoSync(reinterpret_cast<const sockaddr &>(addr), flags);
} }
template<typename I> template<typename I>
UVW_INLINE std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::nameInfoSync(Addr addr, int flags) { UVW_INLINE std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::nameInfoSync(Addr addr, int flags) {
return nameInfoSync<I>(std::move(addr.ip), addr.port, flags); return nameInfoSync<I>(std::move(addr.ip), addr.port, flags);
} }
// explicit instantiations // explicit instantiations
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
template void GetNameInfoReq::nameInfo<IPv4>(const std::string &, unsigned int, int); template void GetNameInfoReq::nameInfo<IPv4>(const std::string &, unsigned int, int);
@ -143,5 +113,4 @@ template std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::
template std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::nameInfoSync<IPv6>(Addr, int); template std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::nameInfoSync<IPv6>(Addr, int);
#endif // UVW_AS_LIB #endif // UVW_AS_LIB
} // namespace uvw
}

View File

@ -1,26 +1,23 @@
#ifndef UVW_DNS_INCLUDE_H #ifndef UVW_DNS_INCLUDE_H
#define UVW_DNS_INCLUDE_H #define UVW_DNS_INCLUDE_H
#include <utility>
#include <memory> #include <memory>
#include <string> #include <string>
#include <utility>
#include <uv.h> #include <uv.h>
#include "loop.h"
#include "request.hpp" #include "request.hpp"
#include "util.h" #include "util.h"
#include "loop.h"
namespace uvw { namespace uvw {
/** /**
* @brief AddrInfoEvent event. * @brief AddrInfoEvent event.
* *
* It will be emitted by GetAddrInfoReq according with its functionalities. * It will be emitted by GetAddrInfoReq according with its functionalities.
*/ */
struct AddrInfoEvent { struct AddrInfoEvent {
using Deleter = void(*)(addrinfo *); using Deleter = void (*)(addrinfo *);
AddrInfoEvent(std::unique_ptr<addrinfo, Deleter> addr); AddrInfoEvent(std::unique_ptr<addrinfo, Deleter> addr);
@ -33,7 +30,6 @@ struct AddrInfoEvent {
std::unique_ptr<addrinfo, Deleter> data; std::unique_ptr<addrinfo, Deleter> data;
}; };
/** /**
* @brief NameInfoEvent event. * @brief NameInfoEvent event.
* *
@ -48,7 +44,7 @@ struct NameInfoEvent {
* See [getnameinfo](http://linux.die.net/man/3/getnameinfo) for further * See [getnameinfo](http://linux.die.net/man/3/getnameinfo) for further
* details. * details.
*/ */
const char * hostname; const char *hostname;
/** /**
* @brief A valid service name. * @brief A valid service name.
@ -56,10 +52,9 @@ struct NameInfoEvent {
* See [getnameinfo](http://linux.die.net/man/3/getnameinfo) for further * See [getnameinfo](http://linux.die.net/man/3/getnameinfo) for further
* details. * details.
*/ */
const char * service; const char *service;
}; };
/** /**
* @brief The GetAddrInfoReq request. * @brief The GetAddrInfoReq request.
* *
@ -74,7 +69,7 @@ class GetAddrInfoReq final: public Request<GetAddrInfoReq, uv_getaddrinfo_t> {
auto nodeAddrInfoSync(const char *node, const char *service, addrinfo *hints = nullptr); auto nodeAddrInfoSync(const char *node, const char *service, addrinfo *hints = nullptr);
public: public:
using Deleter = void(*)(addrinfo *); using Deleter = void (*)(addrinfo *);
using Request::Request; using Request::Request;
@ -144,7 +139,6 @@ public:
std::pair<bool, std::unique_ptr<addrinfo, Deleter>> addrInfoSync(const std::string &node, const std::string &service, addrinfo *hints = nullptr); std::pair<bool, std::unique_ptr<addrinfo, Deleter>> addrInfoSync(const std::string &node, const std::string &service, addrinfo *hints = nullptr);
}; };
/** /**
* @brief The GetNameInfoReq request. * @brief The GetNameInfoReq request.
* *
@ -229,13 +223,11 @@ public:
std::pair<bool, std::pair<const char *, const char *>> nameInfoSync(Addr addr, int flags = 0); std::pair<bool, std::pair<const char *, const char *>> nameInfoSync(Addr addr, int flags = 0);
}; };
/** /**
* @cond TURN_OFF_DOXYGEN * @cond TURN_OFF_DOXYGEN
* Internal details not to be documented. * Internal details not to be documented.
*/ */
// (extern) explicit instantiations // (extern) explicit instantiations
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
extern template void GetNameInfoReq::nameInfo<IPv4>(const std::string &, unsigned int, int); extern template void GetNameInfoReq::nameInfo<IPv4>(const std::string &, unsigned int, int);
@ -251,19 +243,15 @@ extern template std::pair<bool, std::pair<const char *, const char *>> GetNameIn
extern template std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::nameInfoSync<IPv6>(Addr, int); extern template std::pair<bool, std::pair<const char *, const char *>> GetNameInfoReq::nameInfoSync<IPv6>(Addr, int);
#endif // UVW_AS_LIB #endif // UVW_AS_LIB
/** /**
* Internal details not to be documented. * Internal details not to be documented.
* @endcond * @endcond
*/ */
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "dns.cpp" # include "dns.cpp"
#endif #endif
#endif // UVW_DNS_INCLUDE_H #endif // UVW_DNS_INCLUDE_H

View File

@ -1,37 +1,29 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "emitter.h" # include "emitter.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE int ErrorEvent::translate(int sys) noexcept { UVW_INLINE int ErrorEvent::translate(int sys) noexcept {
return uv_translate_sys_error(sys); return uv_translate_sys_error(sys);
} }
UVW_INLINE const char *ErrorEvent::what() const noexcept {
UVW_INLINE const char * ErrorEvent::what() const noexcept {
return uv_strerror(ec); return uv_strerror(ec);
} }
UVW_INLINE const char *ErrorEvent::name() const noexcept {
UVW_INLINE const char * ErrorEvent::name() const noexcept {
return uv_err_name(ec); return uv_err_name(ec);
} }
UVW_INLINE int ErrorEvent::code() const noexcept { UVW_INLINE int ErrorEvent::code() const noexcept {
return ec; return ec;
} }
UVW_INLINE ErrorEvent::operator bool() const noexcept { UVW_INLINE ErrorEvent::operator bool() const noexcept {
return ec < 0; return ec < 0;
} }
} // namespace uvw
}

View File

@ -1,22 +1,19 @@
#ifndef UVW_EMITTER_INCLUDE_H #ifndef UVW_EMITTER_INCLUDE_H
#define UVW_EMITTER_INCLUDE_H #define UVW_EMITTER_INCLUDE_H
#include <type_traits>
#include <functional>
#include <algorithm> #include <algorithm>
#include <utility>
#include <cstddef> #include <cstddef>
#include <unordered_map> #include <functional>
#include <memory>
#include <list> #include <list>
#include <memory>
#include <type_traits>
#include <unordered_map>
#include <utility>
#include <uv.h> #include <uv.h>
#include "type_info.hpp" #include "type_info.hpp"
namespace uvw { namespace uvw {
/** /**
* @brief The ErrorEvent event. * @brief The ErrorEvent event.
* *
@ -25,8 +22,7 @@ namespace uvw {
struct ErrorEvent { struct ErrorEvent {
template<typename U, typename = std::enable_if_t<std::is_integral_v<U>>> template<typename U, typename = std::enable_if_t<std::is_integral_v<U>>>
explicit ErrorEvent(U val) noexcept explicit ErrorEvent(U val) noexcept
: ec{static_cast<int>(val)} : ec{static_cast<int>(val)} {}
{}
/** /**
* @brief Returns the `libuv` error code equivalent to the given platform dependent error code. * @brief Returns the `libuv` error code equivalent to the given platform dependent error code.
@ -49,7 +45,7 @@ struct ErrorEvent {
* *
* @return The error message for the given error code. * @return The error message for the given error code.
*/ */
const char * what() const noexcept; const char *what() const noexcept;
/** /**
* @brief Returns the error name for the given error code. * @brief Returns the error name for the given error code.
@ -58,7 +54,7 @@ struct ErrorEvent {
* *
* @return The error name for the given error code. * @return The error name for the given error code.
*/ */
const char * name() const noexcept; const char *name() const noexcept;
/** /**
* @brief Gets the underlying error code, that is an error constant of `libuv`. * @brief Gets the underlying error code, that is an error constant of `libuv`.
@ -76,7 +72,6 @@ private:
const int ec; const int ec;
}; };
/** /**
* @brief Event emitter base class. * @brief Event emitter base class.
* *
@ -99,15 +94,14 @@ class Emitter {
using Connection = typename ListenerList::iterator; using Connection = typename ListenerList::iterator;
bool empty() const noexcept override { bool empty() const noexcept override {
auto pred = [](auto &&element){ return element.first; }; auto pred = [](auto &&element) { return element.first; };
return std::all_of(onceL.cbegin(), onceL.cend(), pred) && return std::all_of(onceL.cbegin(), onceL.cend(), pred) && std::all_of(onL.cbegin(), onL.cend(), pred);
std::all_of(onL.cbegin(), onL.cend(), pred);
} }
void clear() noexcept override { void clear() noexcept override {
if(publishing) { if(publishing) {
auto func = [](auto &&element){ element.first = true; }; auto func = [](auto &&element) { element.first = true; };
std::for_each(onceL.begin(), onceL.end(), func); std::for_each(onceL.begin(), onceL.end(), func);
std::for_each(onL.begin(), onL.end(), func); std::for_each(onL.begin(), onL.end(), func);
} else { } else {
@ -128,7 +122,7 @@ class Emitter {
conn->first = true; conn->first = true;
if(!publishing) { if(!publishing) {
auto pred = [](auto &&element){ return element.first; }; auto pred = [](auto &&element) { return element.first; };
onceL.remove_if(pred); onceL.remove_if(pred);
onL.remove_if(pred); onL.remove_if(pred);
} }
@ -149,7 +143,7 @@ class Emitter {
publishing = false; publishing = false;
onL.remove_if([](auto &&element){ return element.first; }); onL.remove_if([](auto &&element) { return element.first; });
} }
private: private:
@ -159,20 +153,20 @@ class Emitter {
}; };
template<typename E> template<typename E>
Handler<E> & handler() noexcept { Handler<E> &handler() noexcept {
auto id = type<E>(); auto id = type<E>();
if(!handlers.count(id)) { if(!handlers.count(id)) {
handlers[id] = std::make_unique<Handler<E>>(); handlers[id] = std::make_unique<Handler<E>>();
} }
return static_cast<Handler<E>&>(*handlers.at(id)); return static_cast<Handler<E> &>(*handlers.at(id));
} }
protected: protected:
template<typename E> template<typename E>
void publish(E event) { void publish(E event) {
handler<E>().publish(std::move(event), *static_cast<T*>(this)); handler<E>().publish(std::move(event), *static_cast<T *>(this));
} }
public: public:
@ -188,18 +182,18 @@ public:
*/ */
template<typename E> template<typename E>
struct Connection: private Handler<E>::Connection { struct Connection: private Handler<E>::Connection {
template<typename> friend class Emitter; template<typename>
friend class Emitter;
Connection() = default; Connection() = default;
Connection(const Connection &) = default; Connection(const Connection &) = default;
Connection(Connection &&) = default; Connection(Connection &&) = default;
Connection(typename Handler<E>::Connection conn) Connection(typename Handler<E>::Connection conn)
: Handler<E>::Connection{std::move(conn)} : Handler<E>::Connection{std::move(conn)} {}
{}
Connection & operator=(const Connection &) = default; Connection &operator=(const Connection &) = default;
Connection & operator=(Connection &&) = default; Connection &operator=(Connection &&) = default;
}; };
virtual ~Emitter() noexcept { virtual ~Emitter() noexcept {
@ -267,8 +261,7 @@ public:
* @brief Disconnects all the listeners. * @brief Disconnects all the listeners.
*/ */
void clear() noexcept { void clear() noexcept {
std::for_each(handlers.begin(), handlers.end(), std::for_each(handlers.begin(), handlers.end(), [](auto &&hdlr) { if(hdlr.second) { hdlr.second->clear(); } });
[](auto &&hdlr){ if(hdlr.second) { hdlr.second->clear(); } });
} }
/** /**
@ -280,8 +273,7 @@ public:
bool empty() const noexcept { bool empty() const noexcept {
auto id = type<E>(); auto id = type<E>();
return (!handlers.count(id) || return (!handlers.count(id) || static_cast<Handler<E> &>(*handlers.at(id)).empty());
static_cast<Handler<E>&>(*handlers.at(id)).empty());
} }
/** /**
@ -290,20 +282,17 @@ public:
* false otherwise. * false otherwise.
*/ */
bool empty() const noexcept { bool empty() const noexcept {
return std::all_of(handlers.cbegin(), handlers.cend(), return std::all_of(handlers.cbegin(), handlers.cend(), [](auto &&hdlr) { return !hdlr.second || hdlr.second->empty(); });
[](auto &&hdlr){ return !hdlr.second || hdlr.second->empty(); });
} }
private: private:
std::unordered_map<std::uint32_t, std::unique_ptr<BaseHandler>> handlers{}; std::unordered_map<std::uint32_t, std::unique_ptr<BaseHandler>> handlers{};
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "emitter.cpp" # include "emitter.cpp"
#endif #endif
#endif // UVW_EMITTER_INCLUDE_H #endif // UVW_EMITTER_INCLUDE_H

View File

@ -1,13 +1,11 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "fs.h" # include "fs.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE void FileReq::fsOpenCallback(uv_fs_t *req) { UVW_INLINE void FileReq::fsOpenCallback(uv_fs_t *req) {
auto ptr = reserve(req); auto ptr = reserve(req);
@ -19,7 +17,6 @@ UVW_INLINE void FileReq::fsOpenCallback(uv_fs_t *req) {
} }
} }
UVW_INLINE void FileReq::fsCloseCallback(uv_fs_t *req) { UVW_INLINE void FileReq::fsCloseCallback(uv_fs_t *req) {
auto ptr = reserve(req); auto ptr = reserve(req);
@ -31,7 +28,6 @@ UVW_INLINE void FileReq::fsCloseCallback(uv_fs_t *req) {
} }
} }
UVW_INLINE void FileReq::fsReadCallback(uv_fs_t *req) { UVW_INLINE void FileReq::fsReadCallback(uv_fs_t *req) {
auto ptr = reserve(req); auto ptr = reserve(req);
@ -42,17 +38,14 @@ UVW_INLINE void FileReq::fsReadCallback(uv_fs_t *req) {
} }
} }
UVW_INLINE FileReq::~FileReq() noexcept { UVW_INLINE FileReq::~FileReq() noexcept {
uv_fs_req_cleanup(get()); uv_fs_req_cleanup(get());
} }
UVW_INLINE void FileReq::close() { UVW_INLINE void FileReq::close() {
cleanupAndInvoke(&uv_fs_close, parent(), get(), file, &fsCloseCallback); cleanupAndInvoke(&uv_fs_close, parent(), get(), file, &fsCloseCallback);
} }
UVW_INLINE bool FileReq::closeSync() { UVW_INLINE bool FileReq::closeSync() {
auto req = get(); auto req = get();
@ -65,12 +58,10 @@ UVW_INLINE bool FileReq::closeSync() {
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FileReq::open(const std::string &path, Flags<FileOpen> flags, int mode) { UVW_INLINE void FileReq::open(const std::string &path, Flags<FileOpen> flags, int mode) {
cleanupAndInvoke(&uv_fs_open, parent(), get(), path.data(), flags, mode, &fsOpenCallback); cleanupAndInvoke(&uv_fs_open, parent(), get(), path.data(), flags, mode, &fsOpenCallback);
} }
UVW_INLINE bool FileReq::openSync(const std::string &path, Flags<FileOpen> flags, int mode) { UVW_INLINE bool FileReq::openSync(const std::string &path, Flags<FileOpen> flags, int mode) {
auto req = get(); auto req = get();
@ -83,7 +74,6 @@ UVW_INLINE bool FileReq::openSync(const std::string &path, Flags<FileOpen> flags
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FileReq::read(int64_t offset, unsigned int len) { UVW_INLINE void FileReq::read(int64_t offset, unsigned int len) {
current = std::unique_ptr<char[]>{new char[len]}; current = std::unique_ptr<char[]>{new char[len]};
buffer = uv_buf_init(current.get(), len); buffer = uv_buf_init(current.get(), len);
@ -91,7 +81,6 @@ UVW_INLINE void FileReq::read(int64_t offset, unsigned int len) {
cleanupAndInvoke(&uv_fs_read, parent(), get(), file, bufs, 1, offset, &fsReadCallback); cleanupAndInvoke(&uv_fs_read, parent(), get(), file, bufs, 1, offset, &fsReadCallback);
} }
UVW_INLINE std::pair<bool, std::pair<std::unique_ptr<const char[]>, std::size_t>> FileReq::readSync(int64_t offset, unsigned int len) { UVW_INLINE std::pair<bool, std::pair<std::unique_ptr<const char[]>, std::size_t>> FileReq::readSync(int64_t offset, unsigned int len) {
current = std::unique_ptr<char[]>{new char[len]}; current = std::unique_ptr<char[]>{new char[len]};
buffer = uv_buf_init(current.get(), len); buffer = uv_buf_init(current.get(), len);
@ -102,20 +91,17 @@ UVW_INLINE std::pair<bool, std::pair<std::unique_ptr<const char[]>, std::size_t>
return std::make_pair(!err, std::make_pair(std::move(current), err ? 0 : std::size_t(req->result))); return std::make_pair(!err, std::make_pair(std::move(current), err ? 0 : std::size_t(req->result)));
} }
UVW_INLINE void FileReq::write(std::unique_ptr<char[]> buf, unsigned int len, int64_t offset) { UVW_INLINE void FileReq::write(std::unique_ptr<char[]> buf, unsigned int len, int64_t offset) {
current = std::move(buf); current = std::move(buf);
uv_buf_t bufs[] = {uv_buf_init(current.get(), len)}; uv_buf_t bufs[] = {uv_buf_init(current.get(), len)};
cleanupAndInvoke(&uv_fs_write, parent(), get(), file, bufs, 1, offset, &fsResultCallback<Type::WRITE>); cleanupAndInvoke(&uv_fs_write, parent(), get(), file, bufs, 1, offset, &fsResultCallback<Type::WRITE>);
} }
UVW_INLINE void FileReq::write(char *buf, unsigned int len, int64_t offset) { UVW_INLINE void FileReq::write(char *buf, unsigned int len, int64_t offset) {
uv_buf_t bufs[] = {uv_buf_init(buf, len)}; uv_buf_t bufs[] = {uv_buf_init(buf, len)};
cleanupAndInvoke(&uv_fs_write, parent(), get(), file, bufs, 1, offset, &fsResultCallback<Type::WRITE>); cleanupAndInvoke(&uv_fs_write, parent(), get(), file, bufs, 1, offset, &fsResultCallback<Type::WRITE>);
} }
UVW_INLINE std::pair<bool, std::size_t> FileReq::writeSync(std::unique_ptr<char[]> buf, unsigned int len, int64_t offset) { UVW_INLINE std::pair<bool, std::size_t> FileReq::writeSync(std::unique_ptr<char[]> buf, unsigned int len, int64_t offset) {
current = std::move(buf); current = std::move(buf);
uv_buf_t bufs[] = {uv_buf_init(current.get(), len)}; uv_buf_t bufs[] = {uv_buf_init(current.get(), len)};
@ -125,60 +111,50 @@ UVW_INLINE std::pair<bool, std::size_t> FileReq::writeSync(std::unique_ptr<char[
return std::make_pair(!err, err ? 0 : std::size_t(req->result)); return std::make_pair(!err, err ? 0 : std::size_t(req->result));
} }
UVW_INLINE void FileReq::stat() { UVW_INLINE void FileReq::stat() {
cleanupAndInvoke(&uv_fs_fstat, parent(), get(), file, &fsStatCallback<Type::FSTAT>); cleanupAndInvoke(&uv_fs_fstat, parent(), get(), file, &fsStatCallback<Type::FSTAT>);
} }
UVW_INLINE std::pair<bool, Stat> FileReq::statSync() { UVW_INLINE std::pair<bool, Stat> FileReq::statSync() {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_fstat, parent(), req, file); cleanupAndInvokeSync(&uv_fs_fstat, parent(), req, file);
return std::make_pair(!(req->result < 0), req->statbuf); return std::make_pair(!(req->result < 0), req->statbuf);
} }
UVW_INLINE void FileReq::sync() { UVW_INLINE void FileReq::sync() {
cleanupAndInvoke(&uv_fs_fsync, parent(), get(), file, &fsGenericCallback<Type::FSYNC>); cleanupAndInvoke(&uv_fs_fsync, parent(), get(), file, &fsGenericCallback<Type::FSYNC>);
} }
UVW_INLINE bool FileReq::syncSync() { UVW_INLINE bool FileReq::syncSync() {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_fsync, parent(), req, file); cleanupAndInvokeSync(&uv_fs_fsync, parent(), req, file);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FileReq::datasync() { UVW_INLINE void FileReq::datasync() {
cleanupAndInvoke(&uv_fs_fdatasync, parent(), get(), file, &fsGenericCallback<Type::FDATASYNC>); cleanupAndInvoke(&uv_fs_fdatasync, parent(), get(), file, &fsGenericCallback<Type::FDATASYNC>);
} }
UVW_INLINE bool FileReq::datasyncSync() { UVW_INLINE bool FileReq::datasyncSync() {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_fdatasync, parent(), req, file); cleanupAndInvokeSync(&uv_fs_fdatasync, parent(), req, file);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FileReq::truncate(int64_t offset) { UVW_INLINE void FileReq::truncate(int64_t offset) {
cleanupAndInvoke(&uv_fs_ftruncate, parent(), get(), file, offset, &fsGenericCallback<Type::FTRUNCATE>); cleanupAndInvoke(&uv_fs_ftruncate, parent(), get(), file, offset, &fsGenericCallback<Type::FTRUNCATE>);
} }
UVW_INLINE bool FileReq::truncateSync(int64_t offset) { UVW_INLINE bool FileReq::truncateSync(int64_t offset) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_ftruncate, parent(), req, file, offset); cleanupAndInvokeSync(&uv_fs_ftruncate, parent(), req, file, offset);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FileReq::sendfile(FileHandle out, int64_t offset, std::size_t length) { UVW_INLINE void FileReq::sendfile(FileHandle out, int64_t offset, std::size_t length) {
cleanupAndInvoke(&uv_fs_sendfile, parent(), get(), out, file, offset, length, &fsResultCallback<Type::SENDFILE>); cleanupAndInvoke(&uv_fs_sendfile, parent(), get(), out, file, offset, length, &fsResultCallback<Type::SENDFILE>);
} }
UVW_INLINE std::pair<bool, std::size_t> FileReq::sendfileSync(FileHandle out, int64_t offset, std::size_t length) { UVW_INLINE std::pair<bool, std::size_t> FileReq::sendfileSync(FileHandle out, int64_t offset, std::size_t length) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_sendfile, parent(), req, out, file, offset, length); cleanupAndInvokeSync(&uv_fs_sendfile, parent(), req, out, file, offset, length);
@ -186,48 +162,40 @@ UVW_INLINE std::pair<bool, std::size_t> FileReq::sendfileSync(FileHandle out, in
return std::make_pair(!err, err ? 0 : std::size_t(req->result)); return std::make_pair(!err, err ? 0 : std::size_t(req->result));
} }
UVW_INLINE void FileReq::chmod(int mode) { UVW_INLINE void FileReq::chmod(int mode) {
cleanupAndInvoke(&uv_fs_fchmod, parent(), get(), file, mode, &fsGenericCallback<Type::FCHMOD>); cleanupAndInvoke(&uv_fs_fchmod, parent(), get(), file, mode, &fsGenericCallback<Type::FCHMOD>);
} }
UVW_INLINE bool FileReq::chmodSync(int mode) { UVW_INLINE bool FileReq::chmodSync(int mode) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_fchmod, parent(), req, file, mode); cleanupAndInvokeSync(&uv_fs_fchmod, parent(), req, file, mode);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FileReq::futime(FsRequest::Time atime, FsRequest::Time mtime) { UVW_INLINE void FileReq::futime(FsRequest::Time atime, FsRequest::Time mtime) {
cleanupAndInvoke(&uv_fs_futime, parent(), get(), file, atime.count(), mtime.count(), &fsGenericCallback<Type::FUTIME>); cleanupAndInvoke(&uv_fs_futime, parent(), get(), file, atime.count(), mtime.count(), &fsGenericCallback<Type::FUTIME>);
} }
UVW_INLINE bool FileReq::futimeSync(FsRequest::Time atime, FsRequest::Time mtime) { UVW_INLINE bool FileReq::futimeSync(FsRequest::Time atime, FsRequest::Time mtime) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_futime, parent(), req, file, atime.count(), mtime.count()); cleanupAndInvokeSync(&uv_fs_futime, parent(), req, file, atime.count(), mtime.count());
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FileReq::chown(Uid uid, Gid gid) { UVW_INLINE void FileReq::chown(Uid uid, Gid gid) {
cleanupAndInvoke(&uv_fs_fchown, parent(), get(), file, uid, gid, &fsGenericCallback<Type::FCHOWN>); cleanupAndInvoke(&uv_fs_fchown, parent(), get(), file, uid, gid, &fsGenericCallback<Type::FCHOWN>);
} }
UVW_INLINE bool FileReq::chownSync(Uid uid, Gid gid) { UVW_INLINE bool FileReq::chownSync(Uid uid, Gid gid) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_fchown, parent(), req, file, uid, gid); cleanupAndInvokeSync(&uv_fs_fchown, parent(), req, file, uid, gid);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE FileReq::operator FileHandle() const noexcept { UVW_INLINE FileReq::operator FileHandle() const noexcept {
return file; return file;
} }
UVW_INLINE void FsReq::fsReadlinkCallback(uv_fs_t *req) { UVW_INLINE void FsReq::fsReadlinkCallback(uv_fs_t *req) {
auto ptr = reserve(req); auto ptr = reserve(req);
@ -238,7 +206,6 @@ UVW_INLINE void FsReq::fsReadlinkCallback(uv_fs_t *req) {
} }
} }
UVW_INLINE void FsReq::fsReaddirCallback(uv_fs_t *req) { UVW_INLINE void FsReq::fsReaddirCallback(uv_fs_t *req) {
auto ptr = reserve(req); auto ptr = reserve(req);
@ -250,53 +217,44 @@ UVW_INLINE void FsReq::fsReaddirCallback(uv_fs_t *req) {
} }
} }
UVW_INLINE FsReq::~FsReq() noexcept { UVW_INLINE FsReq::~FsReq() noexcept {
uv_fs_req_cleanup(get()); uv_fs_req_cleanup(get());
} }
UVW_INLINE void FsReq::unlink(const std::string &path) { UVW_INLINE void FsReq::unlink(const std::string &path) {
cleanupAndInvoke(&uv_fs_unlink, parent(), get(), path.data(), &fsGenericCallback<Type::UNLINK>); cleanupAndInvoke(&uv_fs_unlink, parent(), get(), path.data(), &fsGenericCallback<Type::UNLINK>);
} }
UVW_INLINE bool FsReq::unlinkSync(const std::string &path) { UVW_INLINE bool FsReq::unlinkSync(const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_unlink, parent(), req, path.data()); cleanupAndInvokeSync(&uv_fs_unlink, parent(), req, path.data());
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::mkdir(const std::string &path, int mode) { UVW_INLINE void FsReq::mkdir(const std::string &path, int mode) {
cleanupAndInvoke(&uv_fs_mkdir, parent(), get(), path.data(), mode, &fsGenericCallback<Type::MKDIR>); cleanupAndInvoke(&uv_fs_mkdir, parent(), get(), path.data(), mode, &fsGenericCallback<Type::MKDIR>);
} }
UVW_INLINE bool FsReq::mkdirSync(const std::string &path, int mode) { UVW_INLINE bool FsReq::mkdirSync(const std::string &path, int mode) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_mkdir, parent(), req, path.data(), mode); cleanupAndInvokeSync(&uv_fs_mkdir, parent(), req, path.data(), mode);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::mkdtemp(const std::string &tpl) { UVW_INLINE void FsReq::mkdtemp(const std::string &tpl) {
cleanupAndInvoke(&uv_fs_mkdtemp, parent(), get(), tpl.data(), &fsGenericCallback<Type::MKDTEMP>); cleanupAndInvoke(&uv_fs_mkdtemp, parent(), get(), tpl.data(), &fsGenericCallback<Type::MKDTEMP>);
} }
UVW_INLINE std::pair<bool, const char *> FsReq::mkdtempSync(const std::string &tpl) { UVW_INLINE std::pair<bool, const char *> FsReq::mkdtempSync(const std::string &tpl) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_mkdtemp, parent(), req, tpl.data()); cleanupAndInvokeSync(&uv_fs_mkdtemp, parent(), req, tpl.data());
return std::make_pair(!(req->result < 0), req->path); return std::make_pair(!(req->result < 0), req->path);
} }
UVW_INLINE void FsReq::mkstemp(const std::string &tpl) { UVW_INLINE void FsReq::mkstemp(const std::string &tpl) {
cleanupAndInvoke(&uv_fs_mkstemp, parent(), get(), tpl.data(), &fsResultCallback<Type::MKSTEMP>); cleanupAndInvoke(&uv_fs_mkstemp, parent(), get(), tpl.data(), &fsResultCallback<Type::MKSTEMP>);
} }
UVW_INLINE std::pair<bool, std::pair<std::string, std::size_t>> FsReq::mkstempSync(const std::string &tpl) { UVW_INLINE std::pair<bool, std::pair<std::string, std::size_t>> FsReq::mkstempSync(const std::string &tpl) {
std::pair<bool, std::pair<std::string, std::size_t>> ret{false, {}}; std::pair<bool, std::pair<std::string, std::size_t>> ret{false, {}};
auto req = get(); auto req = get();
@ -311,36 +269,30 @@ UVW_INLINE std::pair<bool, std::pair<std::string, std::size_t>> FsReq::mkstempSy
return ret; return ret;
} }
UVW_INLINE void FsReq::lutime(const std::string &path, Time atime, Time mtime) { UVW_INLINE void FsReq::lutime(const std::string &path, Time atime, Time mtime) {
cleanupAndInvoke(&uv_fs_lutime, parent(), get(), path.data(), atime.count(), mtime.count(), &fsGenericCallback<Type::LUTIME>); cleanupAndInvoke(&uv_fs_lutime, parent(), get(), path.data(), atime.count(), mtime.count(), &fsGenericCallback<Type::LUTIME>);
} }
UVW_INLINE bool FsReq::lutimeSync(const std::string &path, Time atime, Time mtime) { UVW_INLINE bool FsReq::lutimeSync(const std::string &path, Time atime, Time mtime) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_lutime, parent(), req, path.data(), atime.count(), mtime.count()); cleanupAndInvokeSync(&uv_fs_lutime, parent(), req, path.data(), atime.count(), mtime.count());
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::rmdir(const std::string &path) { UVW_INLINE void FsReq::rmdir(const std::string &path) {
cleanupAndInvoke(&uv_fs_rmdir, parent(), get(), path.data(), &fsGenericCallback<Type::RMDIR>); cleanupAndInvoke(&uv_fs_rmdir, parent(), get(), path.data(), &fsGenericCallback<Type::RMDIR>);
} }
UVW_INLINE bool FsReq::rmdirSync(const std::string &path) { UVW_INLINE bool FsReq::rmdirSync(const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_rmdir, parent(), req, path.data()); cleanupAndInvokeSync(&uv_fs_rmdir, parent(), req, path.data());
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::scandir(const std::string &path, int flags) { UVW_INLINE void FsReq::scandir(const std::string &path, int flags) {
cleanupAndInvoke(&uv_fs_scandir, parent(), get(), path.data(), flags, &fsResultCallback<Type::SCANDIR>); cleanupAndInvoke(&uv_fs_scandir, parent(), get(), path.data(), flags, &fsResultCallback<Type::SCANDIR>);
} }
UVW_INLINE std::pair<bool, std::size_t> FsReq::scandirSync(const std::string &path, int flags) { UVW_INLINE std::pair<bool, std::size_t> FsReq::scandirSync(const std::string &path, int flags) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_scandir, parent(), req, path.data(), flags); cleanupAndInvokeSync(&uv_fs_scandir, parent(), req, path.data(), flags);
@ -348,9 +300,8 @@ UVW_INLINE std::pair<bool, std::size_t> FsReq::scandirSync(const std::string &pa
return std::make_pair(!err, err ? 0 : std::size_t(req->result)); return std::make_pair(!err, err ? 0 : std::size_t(req->result));
} }
UVW_INLINE std::pair<bool, std::pair<FsReq::EntryType, const char *>> FsReq::scandirNext() { UVW_INLINE std::pair<bool, std::pair<FsReq::EntryType, const char *>> FsReq::scandirNext() {
std::pair<bool, std::pair<EntryType, const char *>> ret{false, { EntryType::UNKNOWN, nullptr }}; std::pair<bool, std::pair<EntryType, const char *>> ret{false, {EntryType::UNKNOWN, nullptr}};
// we cannot use cleanupAndInvokeSync because of the return value of uv_fs_scandir_next // we cannot use cleanupAndInvokeSync because of the return value of uv_fs_scandir_next
uv_fs_req_cleanup(get()); uv_fs_req_cleanup(get());
@ -365,132 +316,110 @@ UVW_INLINE std::pair<bool, std::pair<FsReq::EntryType, const char *>> FsReq::sca
return ret; return ret;
} }
UVW_INLINE void FsReq::stat(const std::string &path) { UVW_INLINE void FsReq::stat(const std::string &path) {
cleanupAndInvoke(&uv_fs_stat, parent(), get(), path.data(), &fsStatCallback<Type::STAT>); cleanupAndInvoke(&uv_fs_stat, parent(), get(), path.data(), &fsStatCallback<Type::STAT>);
} }
UVW_INLINE std::pair<bool, Stat> FsReq::statSync(const std::string &path) { UVW_INLINE std::pair<bool, Stat> FsReq::statSync(const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_stat, parent(), req, path.data()); cleanupAndInvokeSync(&uv_fs_stat, parent(), req, path.data());
return std::make_pair(!(req->result < 0), req->statbuf); return std::make_pair(!(req->result < 0), req->statbuf);
} }
UVW_INLINE void FsReq::lstat(const std::string &path) { UVW_INLINE void FsReq::lstat(const std::string &path) {
cleanupAndInvoke(&uv_fs_lstat, parent(), get(), path.data(), &fsStatCallback<Type::LSTAT>); cleanupAndInvoke(&uv_fs_lstat, parent(), get(), path.data(), &fsStatCallback<Type::LSTAT>);
} }
UVW_INLINE std::pair<bool, Stat> FsReq::lstatSync(const std::string &path) { UVW_INLINE std::pair<bool, Stat> FsReq::lstatSync(const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_lstat, parent(), req, path.data()); cleanupAndInvokeSync(&uv_fs_lstat, parent(), req, path.data());
return std::make_pair(!(req->result < 0), req->statbuf); return std::make_pair(!(req->result < 0), req->statbuf);
} }
UVW_INLINE void FsReq::statfs(const std::string &path) { UVW_INLINE void FsReq::statfs(const std::string &path) {
cleanupAndInvoke(&uv_fs_statfs, parent(), get(), path.data(), &fsStatfsCallback); cleanupAndInvoke(&uv_fs_statfs, parent(), get(), path.data(), &fsStatfsCallback);
} }
UVW_INLINE std::pair<bool, Statfs> FsReq::statfsSync(const std::string &path) { UVW_INLINE std::pair<bool, Statfs> FsReq::statfsSync(const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_statfs, parent(), req, path.data()); cleanupAndInvokeSync(&uv_fs_statfs, parent(), req, path.data());
return std::make_pair(!(req->result < 0), *static_cast<uv_statfs_t *>(req->ptr)); return std::make_pair(!(req->result < 0), *static_cast<uv_statfs_t *>(req->ptr));
} }
UVW_INLINE void FsReq::rename(const std::string &old, const std::string &path) { UVW_INLINE void FsReq::rename(const std::string &old, const std::string &path) {
cleanupAndInvoke(&uv_fs_rename, parent(), get(), old.data(), path.data(), &fsGenericCallback<Type::RENAME>); cleanupAndInvoke(&uv_fs_rename, parent(), get(), old.data(), path.data(), &fsGenericCallback<Type::RENAME>);
} }
UVW_INLINE bool FsReq::renameSync(const std::string &old, const std::string &path) { UVW_INLINE bool FsReq::renameSync(const std::string &old, const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_rename, parent(), req, old.data(), path.data()); cleanupAndInvokeSync(&uv_fs_rename, parent(), req, old.data(), path.data());
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::copyfile(const std::string &old, const std::string &path, Flags<CopyFile> flags) { UVW_INLINE void FsReq::copyfile(const std::string &old, const std::string &path, Flags<CopyFile> flags) {
cleanupAndInvoke(&uv_fs_copyfile, parent(), get(), old.data(), path.data(), flags, &fsGenericCallback<Type::COPYFILE>); cleanupAndInvoke(&uv_fs_copyfile, parent(), get(), old.data(), path.data(), flags, &fsGenericCallback<Type::COPYFILE>);
} }
UVW_INLINE bool FsReq::copyfileSync(const std::string &old, const std::string &path, Flags<CopyFile> flags) { UVW_INLINE bool FsReq::copyfileSync(const std::string &old, const std::string &path, Flags<CopyFile> flags) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_copyfile, parent(), get(), old.data(), path.data(), flags); cleanupAndInvokeSync(&uv_fs_copyfile, parent(), get(), old.data(), path.data(), flags);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::access(const std::string &path, int mode) { UVW_INLINE void FsReq::access(const std::string &path, int mode) {
cleanupAndInvoke(&uv_fs_access, parent(), get(), path.data(), mode, &fsGenericCallback<Type::ACCESS>); cleanupAndInvoke(&uv_fs_access, parent(), get(), path.data(), mode, &fsGenericCallback<Type::ACCESS>);
} }
UVW_INLINE bool FsReq::accessSync(const std::string &path, int mode) { UVW_INLINE bool FsReq::accessSync(const std::string &path, int mode) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_access, parent(), req, path.data(), mode); cleanupAndInvokeSync(&uv_fs_access, parent(), req, path.data(), mode);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::chmod(const std::string &path, int mode) { UVW_INLINE void FsReq::chmod(const std::string &path, int mode) {
cleanupAndInvoke(&uv_fs_chmod, parent(), get(), path.data(), mode, &fsGenericCallback<Type::CHMOD>); cleanupAndInvoke(&uv_fs_chmod, parent(), get(), path.data(), mode, &fsGenericCallback<Type::CHMOD>);
} }
UVW_INLINE bool FsReq::chmodSync(const std::string &path, int mode) { UVW_INLINE bool FsReq::chmodSync(const std::string &path, int mode) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_chmod, parent(), req, path.data(), mode); cleanupAndInvokeSync(&uv_fs_chmod, parent(), req, path.data(), mode);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::utime(const std::string &path, FsRequest::Time atime, FsRequest::Time mtime) { UVW_INLINE void FsReq::utime(const std::string &path, FsRequest::Time atime, FsRequest::Time mtime) {
cleanupAndInvoke(&uv_fs_utime, parent(), get(), path.data(), atime.count(), mtime.count(), &fsGenericCallback<Type::UTIME>); cleanupAndInvoke(&uv_fs_utime, parent(), get(), path.data(), atime.count(), mtime.count(), &fsGenericCallback<Type::UTIME>);
} }
UVW_INLINE bool FsReq::utimeSync(const std::string &path, FsRequest::Time atime, FsRequest::Time mtime) { UVW_INLINE bool FsReq::utimeSync(const std::string &path, FsRequest::Time atime, FsRequest::Time mtime) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_utime, parent(), req, path.data(), atime.count(), mtime.count()); cleanupAndInvokeSync(&uv_fs_utime, parent(), req, path.data(), atime.count(), mtime.count());
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::link(const std::string &old, const std::string &path) { UVW_INLINE void FsReq::link(const std::string &old, const std::string &path) {
cleanupAndInvoke(&uv_fs_link, parent(), get(), old.data(), path.data(), &fsGenericCallback<Type::LINK>); cleanupAndInvoke(&uv_fs_link, parent(), get(), old.data(), path.data(), &fsGenericCallback<Type::LINK>);
} }
UVW_INLINE bool FsReq::linkSync(const std::string &old, const std::string &path) { UVW_INLINE bool FsReq::linkSync(const std::string &old, const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_link, parent(), req, old.data(), path.data()); cleanupAndInvokeSync(&uv_fs_link, parent(), req, old.data(), path.data());
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::symlink(const std::string &old, const std::string &path, Flags<SymLink> flags) { UVW_INLINE void FsReq::symlink(const std::string &old, const std::string &path, Flags<SymLink> flags) {
cleanupAndInvoke(&uv_fs_symlink, parent(), get(), old.data(), path.data(), flags, &fsGenericCallback<Type::SYMLINK>); cleanupAndInvoke(&uv_fs_symlink, parent(), get(), old.data(), path.data(), flags, &fsGenericCallback<Type::SYMLINK>);
} }
UVW_INLINE bool FsReq::symlinkSync(const std::string &old, const std::string &path, Flags<SymLink> flags) { UVW_INLINE bool FsReq::symlinkSync(const std::string &old, const std::string &path, Flags<SymLink> flags) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_symlink, parent(), req, old.data(), path.data(), flags); cleanupAndInvokeSync(&uv_fs_symlink, parent(), req, old.data(), path.data(), flags);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::readlink(const std::string &path) { UVW_INLINE void FsReq::readlink(const std::string &path) {
cleanupAndInvoke(&uv_fs_readlink, parent(), get(), path.data(), &fsReadlinkCallback); cleanupAndInvoke(&uv_fs_readlink, parent(), get(), path.data(), &fsReadlinkCallback);
} }
UVW_INLINE std::pair<bool, std::pair<const char *, std::size_t>> FsReq::readlinkSync(const std::string &path) { UVW_INLINE std::pair<bool, std::pair<const char *, std::size_t>> FsReq::readlinkSync(const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_readlink, parent(), req, path.data()); cleanupAndInvokeSync(&uv_fs_readlink, parent(), req, path.data());
@ -498,62 +427,52 @@ UVW_INLINE std::pair<bool, std::pair<const char *, std::size_t>> FsReq::readlink
return std::make_pair(!err, std::make_pair(static_cast<char *>(req->ptr), err ? 0 : std::size_t(req->result))); return std::make_pair(!err, std::make_pair(static_cast<char *>(req->ptr), err ? 0 : std::size_t(req->result)));
} }
UVW_INLINE void FsReq::realpath(const std::string &path) { UVW_INLINE void FsReq::realpath(const std::string &path) {
cleanupAndInvoke(&uv_fs_realpath, parent(), get(), path.data(), &fsGenericCallback<Type::REALPATH>); cleanupAndInvoke(&uv_fs_realpath, parent(), get(), path.data(), &fsGenericCallback<Type::REALPATH>);
} }
UVW_INLINE std::pair<bool, const char *> FsReq::realpathSync(const std::string &path) { UVW_INLINE std::pair<bool, const char *> FsReq::realpathSync(const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_realpath, parent(), req, path.data()); cleanupAndInvokeSync(&uv_fs_realpath, parent(), req, path.data());
return std::make_pair(!(req->result < 0), req->path); return std::make_pair(!(req->result < 0), req->path);
} }
UVW_INLINE void FsReq::chown(const std::string &path, Uid uid, Gid gid) { UVW_INLINE void FsReq::chown(const std::string &path, Uid uid, Gid gid) {
cleanupAndInvoke(&uv_fs_chown, parent(), get(), path.data(), uid, gid, &fsGenericCallback<Type::CHOWN>); cleanupAndInvoke(&uv_fs_chown, parent(), get(), path.data(), uid, gid, &fsGenericCallback<Type::CHOWN>);
} }
UVW_INLINE bool FsReq::chownSync(const std::string &path, Uid uid, Gid gid) { UVW_INLINE bool FsReq::chownSync(const std::string &path, Uid uid, Gid gid) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_chown, parent(), req, path.data(), uid, gid); cleanupAndInvokeSync(&uv_fs_chown, parent(), req, path.data(), uid, gid);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::lchown(const std::string &path, Uid uid, Gid gid) { UVW_INLINE void FsReq::lchown(const std::string &path, Uid uid, Gid gid) {
cleanupAndInvoke(&uv_fs_lchown, parent(), get(), path.data(), uid, gid, &fsGenericCallback<Type::LCHOWN>); cleanupAndInvoke(&uv_fs_lchown, parent(), get(), path.data(), uid, gid, &fsGenericCallback<Type::LCHOWN>);
} }
UVW_INLINE bool FsReq::lchownSync(const std::string &path, Uid uid, Gid gid) { UVW_INLINE bool FsReq::lchownSync(const std::string &path, Uid uid, Gid gid) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_lchown, parent(), req, path.data(), uid, gid); cleanupAndInvokeSync(&uv_fs_lchown, parent(), req, path.data(), uid, gid);
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::opendir(const std::string &path) { UVW_INLINE void FsReq::opendir(const std::string &path) {
cleanupAndInvoke(&uv_fs_opendir, parent(), get(), path.data(), &fsGenericCallback<Type::OPENDIR>); cleanupAndInvoke(&uv_fs_opendir, parent(), get(), path.data(), &fsGenericCallback<Type::OPENDIR>);
} }
UVW_INLINE bool FsReq::opendirSync(const std::string &path) { UVW_INLINE bool FsReq::opendirSync(const std::string &path) {
auto req = get(); auto req = get();
cleanupAndInvokeSync(&uv_fs_opendir, parent(), req, path.data()); cleanupAndInvokeSync(&uv_fs_opendir, parent(), req, path.data());
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::closedir() { UVW_INLINE void FsReq::closedir() {
auto req = get(); auto req = get();
auto *dir = static_cast<uv_dir_t *>(req->ptr); auto *dir = static_cast<uv_dir_t *>(req->ptr);
cleanupAndInvoke(&uv_fs_closedir, parent(), req, dir, &fsGenericCallback<Type::CLOSEDIR>); cleanupAndInvoke(&uv_fs_closedir, parent(), req, dir, &fsGenericCallback<Type::CLOSEDIR>);
} }
UVW_INLINE bool FsReq::closedirSync() { UVW_INLINE bool FsReq::closedirSync() {
auto req = get(); auto req = get();
auto *dir = static_cast<uv_dir_t *>(req->ptr); auto *dir = static_cast<uv_dir_t *>(req->ptr);
@ -561,7 +480,6 @@ UVW_INLINE bool FsReq::closedirSync() {
return !(req->result < 0); return !(req->result < 0);
} }
UVW_INLINE void FsReq::readdir() { UVW_INLINE void FsReq::readdir() {
auto req = get(); auto req = get();
auto *dir = static_cast<uv_dir_t *>(req->ptr); auto *dir = static_cast<uv_dir_t *>(req->ptr);
@ -570,25 +488,21 @@ UVW_INLINE void FsReq::readdir() {
cleanupAndInvoke(&uv_fs_readdir, parent(), req, dir, &fsReaddirCallback); cleanupAndInvoke(&uv_fs_readdir, parent(), req, dir, &fsReaddirCallback);
} }
UVW_INLINE std::pair<bool, std::pair<FsReq::EntryType, const char *>> FsReq::readdirSync() { UVW_INLINE std::pair<bool, std::pair<FsReq::EntryType, const char *>> FsReq::readdirSync() {
auto req = get(); auto req = get();
auto *dir = static_cast<uv_dir_t *>(req->ptr); auto *dir = static_cast<uv_dir_t *>(req->ptr);
dir->dirents = dirents; dir->dirents = dirents;
dir->nentries = 1; dir->nentries = 1;
cleanupAndInvokeSync(&uv_fs_readdir, parent(), req, dir); cleanupAndInvokeSync(&uv_fs_readdir, parent(), req, dir);
return {req->result != 0, { static_cast<EntryType>(dirents[0].type), dirents[0].name }}; return {req->result != 0, {static_cast<EntryType>(dirents[0].type), dirents[0].name}};
} }
UVW_INLINE OSFileDescriptor FsHelper::handle(FileHandle file) noexcept { UVW_INLINE OSFileDescriptor FsHelper::handle(FileHandle file) noexcept {
return uv_get_osfhandle(file); return uv_get_osfhandle(file);
} }
UVW_INLINE FileHandle FsHelper::open(OSFileDescriptor descriptor) noexcept { UVW_INLINE FileHandle FsHelper::open(OSFileDescriptor descriptor) noexcept {
return uv_open_osfhandle(descriptor); return uv_open_osfhandle(descriptor);
} }
} // namespace uvw
}

View File

@ -1,24 +1,20 @@
#ifndef UVW_FS_INCLUDE_H #ifndef UVW_FS_INCLUDE_H
#define UVW_FS_INCLUDE_H #define UVW_FS_INCLUDE_H
#include <chrono>
#include <utility>
#include <memory> #include <memory>
#include <string> #include <string>
#include <chrono> #include <utility>
#include <uv.h> #include <uv.h>
#include "loop.h"
#include "request.hpp" #include "request.hpp"
#include "util.h" #include "util.h"
#include "loop.h"
namespace uvw { namespace uvw {
namespace details { namespace details {
enum class UVFsType : std::underlying_type_t<uv_fs_type> {
enum class UVFsType: std::underlying_type_t<uv_fs_type> {
UNKNOWN = UV_FS_UNKNOWN, UNKNOWN = UV_FS_UNKNOWN,
CUSTOM = UV_FS_CUSTOM, CUSTOM = UV_FS_CUSTOM,
OPEN = UV_FS_OPEN, OPEN = UV_FS_OPEN,
@ -59,8 +55,7 @@ enum class UVFsType: std::underlying_type_t<uv_fs_type> {
LUTIME = UV_FS_LUTIME LUTIME = UV_FS_LUTIME
}; };
enum class UVDirentTypeT : std::underlying_type_t<uv_dirent_type_t> {
enum class UVDirentTypeT: std::underlying_type_t<uv_dirent_type_t> {
UNKNOWN = UV_DIRENT_UNKNOWN, UNKNOWN = UV_DIRENT_UNKNOWN,
FILE = UV_DIRENT_FILE, FILE = UV_DIRENT_FILE,
DIR = UV_DIRENT_DIR, DIR = UV_DIRENT_DIR,
@ -71,8 +66,7 @@ enum class UVDirentTypeT: std::underlying_type_t<uv_dirent_type_t> {
BLOCK = UV_DIRENT_BLOCK BLOCK = UV_DIRENT_BLOCK
}; };
enum class UVFileOpenFlags : int {
enum class UVFileOpenFlags: int {
APPEND = UV_FS_O_APPEND, APPEND = UV_FS_O_APPEND,
CREAT = UV_FS_O_CREAT, CREAT = UV_FS_O_CREAT,
DIRECT = UV_FS_O_DIRECT, DIRECT = UV_FS_O_DIRECT,
@ -97,22 +91,18 @@ enum class UVFileOpenFlags: int {
WRONLY = UV_FS_O_WRONLY WRONLY = UV_FS_O_WRONLY
}; };
enum class UVCopyFileFlags : int {
enum class UVCopyFileFlags: int {
EXCL = UV_FS_COPYFILE_EXCL, EXCL = UV_FS_COPYFILE_EXCL,
FICLONE = UV_FS_COPYFILE_FICLONE, FICLONE = UV_FS_COPYFILE_FICLONE,
FICLONE_FORCE = UV_FS_COPYFILE_FICLONE_FORCE FICLONE_FORCE = UV_FS_COPYFILE_FICLONE_FORCE
}; };
enum class UVSymLinkFlags : int {
enum class UVSymLinkFlags: int {
DIR = UV_FS_SYMLINK_DIR, DIR = UV_FS_SYMLINK_DIR,
JUNCTION = UV_FS_SYMLINK_JUNCTION JUNCTION = UV_FS_SYMLINK_JUNCTION
}; };
} // namespace details
}
/** /**
* @brief Default FsEvent event. * @brief Default FsEvent event.
@ -167,12 +157,12 @@ enum class UVSymLinkFlags: int {
*/ */
template<details::UVFsType e> template<details::UVFsType e>
struct FsEvent { struct FsEvent {
FsEvent(const char *pathname) noexcept: path{pathname} {} FsEvent(const char *pathname) noexcept
: path{pathname} {}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::READ`. * @brief FsEvent event specialization for `FsRequest::Type::READ`.
* *
@ -182,15 +172,13 @@ struct FsEvent {
template<> template<>
struct FsEvent<details::UVFsType::READ> { struct FsEvent<details::UVFsType::READ> {
FsEvent(const char *pathname, std::unique_ptr<const char[]> buf, std::size_t sz) noexcept FsEvent(const char *pathname, std::unique_ptr<const char[]> buf, std::size_t sz) noexcept
: path{pathname}, data{std::move(buf)}, size{sz} : path{pathname}, data{std::move(buf)}, size{sz} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
std::unique_ptr<const char[]> data; /*!< A bunch of data read from the given path. */ std::unique_ptr<const char[]> data; /*!< A bunch of data read from the given path. */
std::size_t size; /*!< The amount of data read from the given path. */ std::size_t size; /*!< The amount of data read from the given path. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::WRITE`. * @brief FsEvent event specialization for `FsRequest::Type::WRITE`.
* *
@ -200,14 +188,12 @@ struct FsEvent<details::UVFsType::READ> {
template<> template<>
struct FsEvent<details::UVFsType::WRITE> { struct FsEvent<details::UVFsType::WRITE> {
FsEvent(const char *pathname, std::size_t sz) noexcept FsEvent(const char *pathname, std::size_t sz) noexcept
: path{pathname}, size{sz} : path{pathname}, size{sz} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
std::size_t size; /*!< The amount of data written to the given path. */ std::size_t size; /*!< The amount of data written to the given path. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::SENDFILE`. * @brief FsEvent event specialization for `FsRequest::Type::SENDFILE`.
* *
@ -217,14 +203,12 @@ struct FsEvent<details::UVFsType::WRITE> {
template<> template<>
struct FsEvent<details::UVFsType::SENDFILE> { struct FsEvent<details::UVFsType::SENDFILE> {
FsEvent(const char *pathname, std::size_t sz) noexcept FsEvent(const char *pathname, std::size_t sz) noexcept
: path{pathname}, size{sz} : path{pathname}, size{sz} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
std::size_t size; /*!< The amount of data transferred. */ std::size_t size; /*!< The amount of data transferred. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::STAT`. * @brief FsEvent event specialization for `FsRequest::Type::STAT`.
* *
@ -234,14 +218,12 @@ struct FsEvent<details::UVFsType::SENDFILE> {
template<> template<>
struct FsEvent<details::UVFsType::STAT> { struct FsEvent<details::UVFsType::STAT> {
FsEvent(const char *pathname, Stat curr) noexcept FsEvent(const char *pathname, Stat curr) noexcept
: path{pathname}, stat{std::move(curr)} : path{pathname}, stat{std::move(curr)} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
Stat stat; /*!< An initialized instance of Stat. */ Stat stat; /*!< An initialized instance of Stat. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::FSTAT`. * @brief FsEvent event specialization for `FsRequest::Type::FSTAT`.
* *
@ -251,14 +233,12 @@ struct FsEvent<details::UVFsType::STAT> {
template<> template<>
struct FsEvent<details::UVFsType::FSTAT> { struct FsEvent<details::UVFsType::FSTAT> {
FsEvent(const char *pathname, Stat curr) noexcept FsEvent(const char *pathname, Stat curr) noexcept
: path{pathname}, stat{std::move(curr)} : path{pathname}, stat{std::move(curr)} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
Stat stat; /*!< An initialized instance of Stat. */ Stat stat; /*!< An initialized instance of Stat. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::LSTAT`. * @brief FsEvent event specialization for `FsRequest::Type::LSTAT`.
* *
@ -268,14 +248,12 @@ struct FsEvent<details::UVFsType::FSTAT> {
template<> template<>
struct FsEvent<details::UVFsType::LSTAT> { struct FsEvent<details::UVFsType::LSTAT> {
FsEvent(const char *pathname, Stat curr) noexcept FsEvent(const char *pathname, Stat curr) noexcept
: path{pathname}, stat{std::move(curr)} : path{pathname}, stat{std::move(curr)} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
Stat stat; /*!< An initialized instance of Stat. */ Stat stat; /*!< An initialized instance of Stat. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::STATFS`. * @brief FsEvent event specialization for `FsRequest::Type::STATFS`.
* *
@ -285,14 +263,12 @@ struct FsEvent<details::UVFsType::LSTAT> {
template<> template<>
struct FsEvent<details::UVFsType::STATFS> { struct FsEvent<details::UVFsType::STATFS> {
FsEvent(const char *pathname, Statfs curr) noexcept FsEvent(const char *pathname, Statfs curr) noexcept
: path{pathname}, statfs{std::move(curr)} : path{pathname}, statfs{std::move(curr)} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
Statfs statfs; /*!< An initialized instance of Statfs. */ Statfs statfs; /*!< An initialized instance of Statfs. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::MKSTEMP`. * @brief FsEvent event specialization for `FsRequest::Type::MKSTEMP`.
* *
@ -302,14 +278,12 @@ struct FsEvent<details::UVFsType::STATFS> {
template<> template<>
struct FsEvent<details::UVFsType::MKSTEMP> { struct FsEvent<details::UVFsType::MKSTEMP> {
FsEvent(const char *pathname, std::size_t desc) noexcept FsEvent(const char *pathname, std::size_t desc) noexcept
: path{pathname}, descriptor{desc} : path{pathname}, descriptor{desc} {}
{}
const char * path; /*!< The created file path. */ const char *path; /*!< The created file path. */
std::size_t descriptor; /*!< The file descriptor as an integer. */ std::size_t descriptor; /*!< The file descriptor as an integer. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::SCANDIR`. * @brief FsEvent event specialization for `FsRequest::Type::SCANDIR`.
* *
@ -319,14 +293,12 @@ struct FsEvent<details::UVFsType::MKSTEMP> {
template<> template<>
struct FsEvent<details::UVFsType::SCANDIR> { struct FsEvent<details::UVFsType::SCANDIR> {
FsEvent(const char *pathname, std::size_t sz) noexcept FsEvent(const char *pathname, std::size_t sz) noexcept
: path{pathname}, size{sz} : path{pathname}, size{sz} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
std::size_t size; /*!< The number of directory entries selected. */ std::size_t size; /*!< The number of directory entries selected. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::READLINK`. * @brief FsEvent event specialization for `FsRequest::Type::READLINK`.
* *
@ -336,15 +308,13 @@ struct FsEvent<details::UVFsType::SCANDIR> {
template<> template<>
struct FsEvent<details::UVFsType::READLINK> { struct FsEvent<details::UVFsType::READLINK> {
explicit FsEvent(const char *pathname, const char *buf, std::size_t sz) noexcept explicit FsEvent(const char *pathname, const char *buf, std::size_t sz) noexcept
: path{pathname}, data{buf}, size{sz} : path{pathname}, data{buf}, size{sz} {}
{}
const char * path; /*!< The path affecting the request. */ const char *path; /*!< The path affecting the request. */
const char * data; /*!< A bunch of data read from the given path. */ const char *data; /*!< A bunch of data read from the given path. */
std::size_t size; /*!< The amount of data read from the given path. */ std::size_t size; /*!< The amount of data read from the given path. */
}; };
/** /**
* @brief FsEvent event specialization for `FsRequest::Type::READDIR`. * @brief FsEvent event specialization for `FsRequest::Type::READDIR`.
* *
@ -356,15 +326,13 @@ struct FsEvent<details::UVFsType::READDIR> {
using EntryType = details::UVDirentTypeT; using EntryType = details::UVDirentTypeT;
FsEvent(const char *name, EntryType type, bool eos) noexcept FsEvent(const char *name, EntryType type, bool eos) noexcept
: name{name}, type{type}, eos{eos} : name{name}, type{type}, eos{eos} {}
{}
const char * name; /*!< The name of the last entry. */ const char *name; /*!< The name of the last entry. */
EntryType type; /*!< The entry type. */ EntryType type; /*!< The entry type. */
bool eos; /*!< True if there a no more entries to read. */ bool eos; /*!< True if there a no more entries to read. */
}; };
/** /**
* @brief Base class for FsReq and/or FileReq. * @brief Base class for FsReq and/or FileReq.
* *
@ -375,39 +343,47 @@ class FsRequest: public Request<T, uv_fs_t> {
protected: protected:
template<details::UVFsType e> template<details::UVFsType e>
static void fsGenericCallback(uv_fs_t *req) { static void fsGenericCallback(uv_fs_t *req) {
auto ptr = Request<T, uv_fs_t>::reserve(req); if(auto ptr = Request<T, uv_fs_t>::reserve(req); req->result < 0) {
if(req->result < 0) { ptr->publish(ErrorEvent{req->result}); } ptr->publish(ErrorEvent{req->result});
else { ptr->publish(FsEvent<e>{req->path}); } } else {
ptr->publish(FsEvent<e>{req->path});
}
} }
template<details::UVFsType e> template<details::UVFsType e>
static void fsResultCallback(uv_fs_t *req) { static void fsResultCallback(uv_fs_t *req) {
auto ptr = Request<T, uv_fs_t>::reserve(req); if(auto ptr = Request<T, uv_fs_t>::reserve(req); req->result < 0) {
if(req->result < 0) { ptr->publish(ErrorEvent{req->result}); } ptr->publish(ErrorEvent{req->result});
else { ptr->publish(FsEvent<e>{req->path, static_cast<std::size_t>(req->result)}); } } else {
ptr->publish(FsEvent<e>{req->path, static_cast<std::size_t>(req->result)});
}
} }
template<details::UVFsType e> template<details::UVFsType e>
static void fsStatCallback(uv_fs_t *req) { static void fsStatCallback(uv_fs_t *req) {
auto ptr = Request<T, uv_fs_t>::reserve(req); if(auto ptr = Request<T, uv_fs_t>::reserve(req); req->result < 0) {
if(req->result < 0) { ptr->publish(ErrorEvent{req->result}); } ptr->publish(ErrorEvent{req->result});
else { ptr->publish(FsEvent<e>{req->path, req->statbuf}); } } else {
ptr->publish(FsEvent<e>{req->path, req->statbuf});
}
} }
static void fsStatfsCallback(uv_fs_t *req) { static void fsStatfsCallback(uv_fs_t *req) {
auto ptr = Request<T, uv_fs_t>::reserve(req); if(auto ptr = Request<T, uv_fs_t>::reserve(req); req->result < 0) {
if(req->result < 0) { ptr->publish(ErrorEvent{req->result}); } ptr->publish(ErrorEvent{req->result});
else { ptr->publish(FsEvent<Type::STATFS>{req->path, *static_cast<Statfs *>(req->ptr)}); } } else {
ptr->publish(FsEvent<Type::STATFS>{req->path, *static_cast<Statfs *>(req->ptr)});
}
} }
template<typename... Args> template<typename... Args>
void cleanupAndInvoke(Args&&... args) { void cleanupAndInvoke(Args &&...args) {
uv_fs_req_cleanup(this->get()); uv_fs_req_cleanup(this->get());
this->invoke(std::forward<Args>(args)...); this->invoke(std::forward<Args>(args)...);
} }
template<typename F, typename... Args> template<typename F, typename... Args>
void cleanupAndInvokeSync(F &&f, Args&&... args) { void cleanupAndInvokeSync(F &&f, Args &&...args) {
uv_fs_req_cleanup(this->get()); uv_fs_req_cleanup(this->get());
std::forward<F>(f)(std::forward<Args>(args)..., nullptr); std::forward<F>(f)(std::forward<Args>(args)..., nullptr);
} }
@ -420,7 +396,6 @@ public:
using Request<T, uv_fs_t>::Request; using Request<T, uv_fs_t>::Request;
}; };
/** /**
* @brief The FileReq request. * @brief The FileReq request.
* *
@ -771,7 +746,6 @@ private:
uv_file file{BAD_FD}; uv_file file{BAD_FD};
}; };
/** /**
* @brief The FsReq request. * @brief The FsReq request.
* *
@ -1423,7 +1397,6 @@ private:
uv_dirent_t dirents[1]; uv_dirent_t dirents[1];
}; };
/*! @brief Helper functions. */ /*! @brief Helper functions. */
struct FsHelper { struct FsHelper {
/** /**
@ -1451,13 +1424,10 @@ struct FsHelper {
static FileHandle open(OSFileDescriptor descriptor) noexcept; static FileHandle open(OSFileDescriptor descriptor) noexcept;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "fs.cpp" # include "fs.cpp"
#endif #endif
#endif // UVW_FS_INCLUDE_H #endif // UVW_FS_INCLUDE_H

View File

@ -1,18 +1,14 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "fs_event.h" # include "fs_event.h"
#endif #endif
#include <utility> #include <utility>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE FsEventEvent::FsEventEvent(const char *pathname, Flags<details::UVFsEvent> events)
UVW_INLINE FsEventEvent::FsEventEvent(const char * pathname, Flags<details::UVFsEvent> events) : filename{pathname}, flags{std::move(events)} {}
: filename{pathname}, flags{std::move(events)}
{}
UVW_INLINE void FsEventHandle::startCallback(uv_fs_event_t *handle, const char *filename, int events, int status) { UVW_INLINE void FsEventHandle::startCallback(uv_fs_event_t *handle, const char *filename, int events, int status) {
FsEventHandle &fsEvent = *(static_cast<FsEventHandle *>(handle->data)); FsEventHandle &fsEvent = *(static_cast<FsEventHandle *>(handle->data));
@ -24,30 +20,24 @@ UVW_INLINE void FsEventHandle::startCallback(uv_fs_event_t *handle, const char *
} }
} }
UVW_INLINE bool FsEventHandle::init() { UVW_INLINE bool FsEventHandle::init() {
return initialize(&uv_fs_event_init); return initialize(&uv_fs_event_init);
} }
UVW_INLINE void FsEventHandle::start(const std::string &path, Flags<Event> flags) { UVW_INLINE void FsEventHandle::start(const std::string &path, Flags<Event> flags) {
invoke(&uv_fs_event_start, get(), &startCallback, path.data(), flags); invoke(&uv_fs_event_start, get(), &startCallback, path.data(), flags);
} }
UVW_INLINE void FsEventHandle::start(const std::string &path, FsEventHandle::Event flag) { UVW_INLINE void FsEventHandle::start(const std::string &path, FsEventHandle::Event flag) {
start(std::move(path), Flags<Event>{flag}); start(std::move(path), Flags<Event>{flag});
} }
UVW_INLINE void FsEventHandle::stop() { UVW_INLINE void FsEventHandle::stop() {
invoke(&uv_fs_event_stop, get()); invoke(&uv_fs_event_stop, get());
} }
UVW_INLINE std::string FsEventHandle::path() noexcept { UVW_INLINE std::string FsEventHandle::path() noexcept {
return details::tryRead(&uv_fs_event_getpath, get()); return details::tryRead(&uv_fs_event_getpath, get());
} }
} // namespace uvw
}

View File

@ -1,36 +1,29 @@
#ifndef UVW_FS_EVENT_INCLUDE_H #ifndef UVW_FS_EVENT_INCLUDE_H
#define UVW_FS_EVENT_INCLUDE_H #define UVW_FS_EVENT_INCLUDE_H
#include <type_traits>
#include <string> #include <string>
#include <type_traits>
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "util.h"
#include "loop.h" #include "loop.h"
#include "util.h"
namespace uvw { namespace uvw {
namespace details { namespace details {
enum class UVFsEventFlags : std::underlying_type_t<uv_fs_event_flags> {
enum class UVFsEventFlags: std::underlying_type_t<uv_fs_event_flags> {
WATCH_ENTRY = UV_FS_EVENT_WATCH_ENTRY, WATCH_ENTRY = UV_FS_EVENT_WATCH_ENTRY,
STAT = UV_FS_EVENT_STAT, STAT = UV_FS_EVENT_STAT,
RECURSIVE = UV_FS_EVENT_RECURSIVE RECURSIVE = UV_FS_EVENT_RECURSIVE
}; };
enum class UVFsEvent : std::underlying_type_t<uv_fs_event> {
enum class UVFsEvent: std::underlying_type_t<uv_fs_event> {
RENAME = UV_RENAME, RENAME = UV_RENAME,
CHANGE = UV_CHANGE CHANGE = UV_CHANGE
}; };
} // namespace details
}
/** /**
* @brief FsEventEvent event. * @brief FsEventEvent event.
@ -38,7 +31,7 @@ enum class UVFsEvent: std::underlying_type_t<uv_fs_event> {
* It will be emitted by FsEventHandle according with its functionalities. * It will be emitted by FsEventHandle according with its functionalities.
*/ */
struct FsEventEvent { struct FsEventEvent {
FsEventEvent(const char * pathname, Flags<details::UVFsEvent> events); FsEventEvent(const char *pathname, Flags<details::UVFsEvent> events);
/** /**
* @brief The path to the file being monitored. * @brief The path to the file being monitored.
@ -46,7 +39,7 @@ struct FsEventEvent {
* If the handle was started with a directory, the filename parameter will * If the handle was started with a directory, the filename parameter will
* be a relative path to a file contained in the directory. * be a relative path to a file contained in the directory.
*/ */
const char * filename; const char *filename;
/** /**
* @brief Detected events all in one. * @brief Detected events all in one.
@ -59,7 +52,6 @@ struct FsEventEvent {
Flags<details::UVFsEvent> flags; Flags<details::UVFsEvent> flags;
}; };
/** /**
* @brief The FsEventHandle handle. * @brief The FsEventHandle handle.
* *
@ -138,13 +130,10 @@ public:
std::string path() noexcept; std::string path() noexcept;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "fs_event.cpp" # include "fs_event.cpp"
#endif #endif
#endif // UVW_FS_EVENT_INCLUDE_H #endif // UVW_FS_EVENT_INCLUDE_H

View File

@ -1,19 +1,15 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "fs_poll.h" # include "fs_poll.h"
#endif #endif
#include <utility> #include <utility>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE FsPollEvent::FsPollEvent(Stat previous, Stat current) noexcept UVW_INLINE FsPollEvent::FsPollEvent(Stat previous, Stat current) noexcept
: prev{std::move(previous)}, curr{std::move(current)} : prev{std::move(previous)}, curr{std::move(current)} {}
{}
UVW_INLINE void FsPollHandle::startCallback(uv_fs_poll_t *handle, int status, const uv_stat_t *prev, const uv_stat_t *curr) { UVW_INLINE void FsPollHandle::startCallback(uv_fs_poll_t *handle, int status, const uv_stat_t *prev, const uv_stat_t *curr) {
FsPollHandle &fsPoll = *(static_cast<FsPollHandle *>(handle->data)); FsPollHandle &fsPoll = *(static_cast<FsPollHandle *>(handle->data));
@ -25,25 +21,20 @@ UVW_INLINE void FsPollHandle::startCallback(uv_fs_poll_t *handle, int status, co
} }
} }
UVW_INLINE bool FsPollHandle::init() { UVW_INLINE bool FsPollHandle::init() {
return initialize(&uv_fs_poll_init); return initialize(&uv_fs_poll_init);
} }
UVW_INLINE void FsPollHandle::start(const std::string &file, FsPollHandle::Time interval) { UVW_INLINE void FsPollHandle::start(const std::string &file, FsPollHandle::Time interval) {
invoke(&uv_fs_poll_start, get(), &startCallback, file.data(), interval.count()); invoke(&uv_fs_poll_start, get(), &startCallback, file.data(), interval.count());
} }
UVW_INLINE void FsPollHandle::stop() { UVW_INLINE void FsPollHandle::stop() {
invoke(&uv_fs_poll_stop, get()); invoke(&uv_fs_poll_stop, get());
} }
UVW_INLINE std::string FsPollHandle::path() noexcept { UVW_INLINE std::string FsPollHandle::path() noexcept {
return details::tryRead(&uv_fs_poll_getpath, get()); return details::tryRead(&uv_fs_poll_getpath, get());
} }
} // namespace uvw
}

View File

@ -1,18 +1,15 @@
#ifndef UVW_FS_POLL_INCLUDE_H #ifndef UVW_FS_POLL_INCLUDE_H
#define UVW_FS_POLL_INCLUDE_H #define UVW_FS_POLL_INCLUDE_H
#include <string>
#include <chrono> #include <chrono>
#include <string>
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "util.h"
#include "loop.h" #include "loop.h"
#include "util.h"
namespace uvw { namespace uvw {
/** /**
* @brief FsPollEvent event. * @brief FsPollEvent event.
* *
@ -25,7 +22,6 @@ struct FsPollEvent {
Stat curr; /*!< The new Stat struct. */ Stat curr; /*!< The new Stat struct. */
}; };
/** /**
* @brief The FsPollHandle handle. * @brief The FsPollHandle handle.
* *
@ -72,13 +68,10 @@ public:
std::string path() noexcept; std::string path() noexcept;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "fs_poll.cpp" # include "fs_poll.cpp"
#endif #endif
#endif // UVW_FS_POLL_INCLUDE_H #endif // UVW_FS_POLL_INCLUDE_H

View File

@ -1,18 +1,15 @@
#ifndef UVW_HANDLE_INCLUDE_H #ifndef UVW_HANDLE_INCLUDE_H
#define UVW_HANDLE_INCLUDE_H #define UVW_HANDLE_INCLUDE_H
#include <cstddef> #include <cstddef>
#include <utility>
#include <memory> #include <memory>
#include <utility>
#include <uv.h> #include <uv.h>
#include "resource.hpp" #include "resource.hpp"
#include "util.h" #include "util.h"
namespace uvw { namespace uvw {
/** /**
* @brief CloseEvent event. * @brief CloseEvent event.
* *
@ -20,7 +17,6 @@ namespace uvw {
*/ */
struct CloseEvent {}; struct CloseEvent {};
/** /**
* @brief Handle base class. * @brief Handle base class.
* *
@ -29,249 +25,245 @@ struct CloseEvent {};
template<typename T, typename U> template<typename T, typename U>
class Handle: public Resource<T, U> { class Handle: public Resource<T, U> {
protected: protected:
static void closeCallback(uv_handle_t *handle) { static void closeCallback(uv_handle_t *handle) {
Handle<T, U> &ref = *(static_cast<T*>(handle->data)); Handle<T, U> &ref = *(static_cast<T *>(handle->data));
auto ptr = ref.shared_from_this(); [[maybe_unused]] auto ptr = ref.shared_from_this();
(void)ptr; ref.reset();
ref.reset(); ref.publish(CloseEvent{});
ref.publish(CloseEvent{}); }
}
static void allocCallback(uv_handle_t *, std::size_t suggested, uv_buf_t *buf) { static void allocCallback(uv_handle_t *, std::size_t suggested, uv_buf_t *buf) {
auto size = static_cast<unsigned int>(suggested); auto size = static_cast<unsigned int>(suggested);
*buf = uv_buf_init(new char[size], size); *buf = uv_buf_init(new char[size], size);
} }
template<typename F, typename... Args> template<typename F, typename... Args>
bool initialize(F &&f, Args&&... args) { bool initialize(F &&f, Args &&...args) {
if(!this->self()) { if(!this->self()) {
auto err = std::forward<F>(f)(this->parent(), this->get(), std::forward<Args>(args)...); if(auto err = std::forward<F>(f)(this->parent(), this->get(), std::forward<Args>(args)...); err) {
this->publish(ErrorEvent{err});
} else {
this->leak();
}
}
if(err) { return this->self();
this->publish(ErrorEvent{err}); }
} else {
this->leak();
}
}
return this->self(); template<typename F, typename... Args>
} void invoke(F &&f, Args &&...args) {
auto err = std::forward<F>(f)(std::forward<Args>(args)...);
template<typename F, typename... Args> if(err) { Emitter<T>::publish(ErrorEvent{err}); }
void invoke(F &&f, Args&&... args) { }
auto err = std::forward<F>(f)(std::forward<Args>(args)...);
if(err) { Emitter<T>::publish(ErrorEvent{err}); }
}
public: public:
using Resource<T, U>::Resource; using Resource<T, U>::Resource;
/** /**
* @brief Gets the category of the handle. * @brief Gets the category of the handle.
* *
* A base handle offers no functionality to promote it to the actual handle * A base handle offers no functionality to promote it to the actual handle
* type. By means of this function, an opaque value that identifies the * type. By means of this function, an opaque value that identifies the
* category of the handle is made available to the users. * category of the handle is made available to the users.
* *
* @return The actual category of the handle. * @return The actual category of the handle.
*/ */
HandleCategory category() const noexcept { HandleCategory category() const noexcept {
return HandleCategory{this->template get<uv_handle_t>()->type}; return HandleCategory{this->template get<uv_handle_t>()->type};
} }
/** /**
* @brief Gets the type of the handle. * @brief Gets the type of the handle.
* *
* A base handle offers no functionality to promote it to the actual handle * A base handle offers no functionality to promote it to the actual handle
* type. By means of this function, the type of the underlying handle as * type. By means of this function, the type of the underlying handle as
* specified by HandleType is made available to the users. * specified by HandleType is made available to the users.
* *
* @return The actual type of the handle. * @return The actual type of the handle.
*/ */
HandleType type() const noexcept { HandleType type() const noexcept {
return Utilities::guessHandle(category()); return Utilities::guessHandle(category());
} }
/** /**
* @brief Checks if the handle is active. * @brief Checks if the handle is active.
* *
* What _active_ means depends on the type of handle: * What _active_ means depends on the type of handle:
* *
* * An AsyncHandle handle is always active and cannot be deactivated, * * An AsyncHandle handle is always active and cannot be deactivated,
* except by closing it with uv_close(). * except by closing it with uv_close().
* * A PipeHandle, TCPHandle, UDPHandle, etc. handle - basically any handle * * A PipeHandle, TCPHandle, UDPHandle, etc. handle - basically any handle
* that deals with I/O - is active when it is doing something that involves * that deals with I/O - is active when it is doing something that involves
* I/O, like reading, writing, connecting, accepting new connections, etc. * I/O, like reading, writing, connecting, accepting new connections, etc.
* * A CheckHandle, IdleHandle, TimerHandle, etc. handle is active when it * * A CheckHandle, IdleHandle, TimerHandle, etc. handle is active when it
* has been started with a call to `start()`. * has been started with a call to `start()`.
* *
* Rule of thumb: if a handle of type `FooHandle` has a `start()` member * Rule of thumb: if a handle of type `FooHandle` has a `start()` member
* method, then its active from the moment that method is called. Likewise, * method, then its active from the moment that method is called. Likewise,
* `stop()` deactivates the handle again. * `stop()` deactivates the handle again.
* *
* @return True if the handle is active, false otherwise. * @return True if the handle is active, false otherwise.
*/ */
bool active() const noexcept { bool active() const noexcept {
return !(uv_is_active(this->template get<uv_handle_t>()) == 0); return !(uv_is_active(this->template get<uv_handle_t>()) == 0);
} }
/** /**
* @brief Checks if a handle is closing or closed. * @brief Checks if a handle is closing or closed.
* *
* This function should only be used between the initialization of the * This function should only be used between the initialization of the
* handle and the arrival of the close callback. * handle and the arrival of the close callback.
* *
* @return True if the handle is closing or closed, false otherwise. * @return True if the handle is closing or closed, false otherwise.
*/ */
bool closing() const noexcept { bool closing() const noexcept {
return !(uv_is_closing(this->template get<uv_handle_t>()) == 0); return !(uv_is_closing(this->template get<uv_handle_t>()) == 0);
} }
/** /**
* @brief Request handle to be closed. * @brief Request handle to be closed.
* *
* This **must** be called on each handle before memory is released.<br/> * This **must** be called on each handle before memory is released.<br/>
* In-progress requests are cancelled and this can result in an ErrorEvent * In-progress requests are cancelled and this can result in an ErrorEvent
* emitted. * emitted.
* *
* The handle will emit a CloseEvent when finished. * The handle will emit a CloseEvent when finished.
*/ */
void close() noexcept { void close() noexcept {
if(!closing()) { if(!closing()) {
uv_close(this->template get<uv_handle_t>(), &Handle<T, U>::closeCallback); uv_close(this->template get<uv_handle_t>(), &Handle<T, U>::closeCallback);
} }
} }
/** /**
* @brief Reference the given handle. * @brief Reference the given handle.
* *
* References are idempotent, that is, if a handle is already referenced * References are idempotent, that is, if a handle is already referenced
* calling this function again will have no effect. * calling this function again will have no effect.
*/ */
void reference() noexcept { void reference() noexcept {
uv_ref(this->template get<uv_handle_t>()); uv_ref(this->template get<uv_handle_t>());
} }
/** /**
* @brief Unreference the given handle. * @brief Unreference the given handle.
* *
* References are idempotent, that is, if a handle is not referenced calling * References are idempotent, that is, if a handle is not referenced calling
* this function again will have no effect. * this function again will have no effect.
*/ */
void unreference() noexcept { void unreference() noexcept {
uv_unref(this->template get<uv_handle_t>()); uv_unref(this->template get<uv_handle_t>());
} }
/** /**
* @brief Checks if the given handle referenced. * @brief Checks if the given handle referenced.
* @return True if the handle referenced, false otherwise. * @return True if the handle referenced, false otherwise.
*/ */
bool referenced() const noexcept { bool referenced() const noexcept {
return !(uv_has_ref(this->template get<uv_handle_t>()) == 0); return !(uv_has_ref(this->template get<uv_handle_t>()) == 0);
} }
/** /**
* @brief Returns the size of the underlying handle type. * @brief Returns the size of the underlying handle type.
* @return The size of the underlying handle type. * @return The size of the underlying handle type.
*/ */
std::size_t size() const noexcept { std::size_t size() const noexcept {
return uv_handle_size(this->template get<uv_handle_t>()->type); return uv_handle_size(this->template get<uv_handle_t>()->type);
} }
/** /**
* @brief Gets the size of the send buffer used for the socket. * @brief Gets the size of the send buffer used for the socket.
* *
* Gets the size of the send buffer that the operating system uses for the * Gets the size of the send buffer that the operating system uses for the
* socket.<br/> * socket.<br/>
* This function works for TCPHandle, PipeHandle and UDPHandle handles on * This function works for TCPHandle, PipeHandle and UDPHandle handles on
* Unix and for TCPHandle and UDPHandle handles on Windows.<br/> * Unix and for TCPHandle and UDPHandle handles on Windows.<br/>
* Note that Linux will return double the size of the original set value. * Note that Linux will return double the size of the original set value.
* *
* @return The size of the send buffer, 0 in case of errors. * @return The size of the send buffer, 0 in case of errors.
*/ */
int sendBufferSize() { int sendBufferSize() {
int value = 0; int value = 0;
auto err = uv_send_buffer_size(this->template get<uv_handle_t>(), &value); auto err = uv_send_buffer_size(this->template get<uv_handle_t>(), &value);
return err ? 0 : value; return err ? 0 : value;
} }
/** /**
* @brief Sets the size of the send buffer used for the socket. * @brief Sets the size of the send buffer used for the socket.
* *
* Sets the size of the send buffer that the operating system uses for the * Sets the size of the send buffer that the operating system uses for the
* socket.<br/> * socket.<br/>
* This function works for TCPHandle, PipeHandle and UDPHandle handles on * This function works for TCPHandle, PipeHandle and UDPHandle handles on
* Unix and for TCPHandle and UDPHandle handles on Windows.<br/> * Unix and for TCPHandle and UDPHandle handles on Windows.<br/>
* Note that Linux will set double the size. * Note that Linux will set double the size.
* *
* @return True in case of success, false otherwise. * @return True in case of success, false otherwise.
*/ */
bool sendBufferSize(int value) { bool sendBufferSize(int value) {
return (0 == uv_send_buffer_size(this->template get<uv_handle_t>(), &value)); return (0 == uv_send_buffer_size(this->template get<uv_handle_t>(), &value));
} }
/** /**
* @brief Gets the size of the receive buffer used for the socket. * @brief Gets the size of the receive buffer used for the socket.
* *
* Gets the size of the receive buffer that the operating system uses for * Gets the size of the receive buffer that the operating system uses for
* the socket.<br/> * the socket.<br/>
* This function works for TCPHandle, PipeHandle and UDPHandle handles on * This function works for TCPHandle, PipeHandle and UDPHandle handles on
* Unix and for TCPHandle and UDPHandle handles on Windows.<br/> * Unix and for TCPHandle and UDPHandle handles on Windows.<br/>
* Note that Linux will return double the size of the original set value. * Note that Linux will return double the size of the original set value.
* *
* @return The size of the receive buffer, 0 in case of errors. * @return The size of the receive buffer, 0 in case of errors.
*/ */
int recvBufferSize() { int recvBufferSize() {
int value = 0; int value = 0;
auto err = uv_recv_buffer_size(this->template get<uv_handle_t>(), &value); auto err = uv_recv_buffer_size(this->template get<uv_handle_t>(), &value);
return err ? 0 : value; return err ? 0 : value;
} }
/** /**
* @brief Sets the size of the receive buffer used for the socket. * @brief Sets the size of the receive buffer used for the socket.
* *
* Sets the size of the receive buffer that the operating system uses for * Sets the size of the receive buffer that the operating system uses for
* the socket.<br/> * the socket.<br/>
* This function works for TCPHandle, PipeHandle and UDPHandle handles on * This function works for TCPHandle, PipeHandle and UDPHandle handles on
* Unix and for TCPHandle and UDPHandle handles on Windows.<br/> * Unix and for TCPHandle and UDPHandle handles on Windows.<br/>
* Note that Linux will set double the size. * Note that Linux will set double the size.
* *
* @return True in case of success, false otherwise. * @return True in case of success, false otherwise.
*/ */
bool recvBufferSize(int value) { bool recvBufferSize(int value) {
return (0 == uv_recv_buffer_size(this->template get<uv_handle_t>(), &value)); return (0 == uv_recv_buffer_size(this->template get<uv_handle_t>(), &value));
} }
/** /**
* @brief Gets the platform dependent file descriptor equivalent. * @brief Gets the platform dependent file descriptor equivalent.
* *
* Supported handles: * Supported handles:
* *
* * TCPHandle * * TCPHandle
* * PipeHandle * * PipeHandle
* * TTYHandle * * TTYHandle
* * UDPHandle * * UDPHandle
* * PollHandle * * PollHandle
* *
* It will emit an ErrorEvent event if invoked on any other handle.<br/> * It will emit an ErrorEvent event if invoked on any other handle.<br/>
* If a handle doesnt have an attached file descriptor yet or the handle * If a handle doesnt have an attached file descriptor yet or the handle
* itself has been closed, an ErrorEvent event will be emitted. * itself has been closed, an ErrorEvent event will be emitted.
* *
* See the official * See the official
* [documentation](http://docs.libuv.org/en/v1.x/handle.html#c.uv_fileno) * [documentation](http://docs.libuv.org/en/v1.x/handle.html#c.uv_fileno)
* for further details. * for further details.
* *
* @return The file descriptor attached to the hande or a negative value in * @return The file descriptor attached to the hande or a negative value in
* case of errors. * case of errors.
*/ */
OSFileDescriptor fd() const { OSFileDescriptor fd() const {
uv_os_fd_t fd; uv_os_fd_t fd;
uv_fileno(this->template get<uv_handle_t>(), &fd); uv_fileno(this->template get<uv_handle_t>(), &fd);
return fd; return fd;
} }
}; };
} // namespace uvw
}
#endif // UVW_HANDLE_INCLUDE_H #endif // UVW_HANDLE_INCLUDE_H

View File

@ -1,32 +1,26 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "idle.h" # include "idle.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE void IdleHandle::startCallback(uv_idle_t *handle) { UVW_INLINE void IdleHandle::startCallback(uv_idle_t *handle) {
IdleHandle &idle = *(static_cast<IdleHandle *>(handle->data)); IdleHandle &idle = *(static_cast<IdleHandle *>(handle->data));
idle.publish(IdleEvent{}); idle.publish(IdleEvent{});
} }
UVW_INLINE bool IdleHandle::init() { UVW_INLINE bool IdleHandle::init() {
return initialize(&uv_idle_init); return initialize(&uv_idle_init);
} }
UVW_INLINE void IdleHandle::start() { UVW_INLINE void IdleHandle::start() {
invoke(&uv_idle_start, get(), &startCallback); invoke(&uv_idle_start, get(), &startCallback);
} }
UVW_INLINE void IdleHandle::stop() { UVW_INLINE void IdleHandle::stop() {
invoke(&uv_idle_stop, get()); invoke(&uv_idle_stop, get());
} }
} // namespace uvw
}

View File

@ -1,15 +1,12 @@
#ifndef UVW_IDLE_INCLUDE_H #ifndef UVW_IDLE_INCLUDE_H
#define UVW_IDLE_INCLUDE_H #define UVW_IDLE_INCLUDE_H
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "loop.h" #include "loop.h"
namespace uvw { namespace uvw {
/** /**
* @brief IdleEvent event. * @brief IdleEvent event.
* *
@ -17,7 +14,6 @@ namespace uvw {
*/ */
struct IdleEvent {}; struct IdleEvent {};
/** /**
* @brief The IdleHandle handle. * @brief The IdleHandle handle.
* *
@ -60,12 +56,10 @@ public:
void stop(); void stop();
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "idle.cpp" # include "idle.cpp"
#endif #endif
#endif // UVW_IDLE_INCLUDE_H #endif // UVW_IDLE_INCLUDE_H

View File

@ -1,35 +1,28 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "lib.h" # include "lib.h"
#endif #endif
#include <utility> #include <utility>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE SharedLib::SharedLib(UnderlyingType<SharedLib, uv_lib_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref, const std::string &filename) noexcept UVW_INLINE SharedLib::SharedLib(UnderlyingType<SharedLib, uv_lib_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref, const std::string &filename) noexcept
: UnderlyingType{ca, std::move(ref)} : UnderlyingType{ca, std::move(ref)} {
{
opened = (0 == uv_dlopen(filename.data(), get())); opened = (0 == uv_dlopen(filename.data(), get()));
} }
UVW_INLINE SharedLib::~SharedLib() noexcept { UVW_INLINE SharedLib::~SharedLib() noexcept {
uv_dlclose(get()); uv_dlclose(get());
} }
UVW_INLINE SharedLib::operator bool() const noexcept { UVW_INLINE SharedLib::operator bool() const noexcept {
return opened; return opened;
} }
UVW_INLINE const char *SharedLib::error() const noexcept { UVW_INLINE const char *SharedLib::error() const noexcept {
return uv_dlerror(get()); return uv_dlerror(get());
} }
} // namespace uvw
}

View File

@ -1,7 +1,6 @@
#ifndef UVW_LIB_INCLUDE_H #ifndef UVW_LIB_INCLUDE_H
#define UVW_LIB_INCLUDE_H #define UVW_LIB_INCLUDE_H
#include <memory> #include <memory>
#include <string> #include <string>
#include <type_traits> #include <type_traits>
@ -9,10 +8,8 @@
#include "loop.h" #include "loop.h"
#include "underlying_type.hpp" #include "underlying_type.hpp"
namespace uvw { namespace uvw {
/** /**
* @brief The SharedLib class. * @brief The SharedLib class.
* *
@ -41,10 +38,10 @@ public:
* @return A valid function pointer in case of success, `nullptr` otherwise. * @return A valid function pointer in case of success, `nullptr` otherwise.
*/ */
template<typename F> template<typename F>
F * sym(const std::string &name) { F *sym(const std::string &name) {
static_assert(std::is_function_v<F>); static_assert(std::is_function_v<F>);
F *func; F *func;
auto err = uv_dlsym(get(), name.data(), reinterpret_cast<void**>(&func)); auto err = uv_dlsym(get(), name.data(), reinterpret_cast<void **>(&func));
if(err) { func = nullptr; } if(err) { func = nullptr; }
return func; return func;
} }
@ -53,19 +50,16 @@ public:
* @brief Returns the last error message, if any. * @brief Returns the last error message, if any.
* @return The last error message, if any. * @return The last error message, if any.
*/ */
const char * error() const noexcept; const char *error() const noexcept;
private: private:
bool opened; bool opened;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "lib.cpp" # include "lib.cpp"
#endif #endif
#endif // UVW_LIB_INCLUDE_H #endif // UVW_LIB_INCLUDE_H

View File

@ -1,22 +1,18 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "loop.h" # include "loop.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE Loop::Loop(std::unique_ptr<uv_loop_t, Deleter> ptr) noexcept UVW_INLINE Loop::Loop(std::unique_ptr<uv_loop_t, Deleter> ptr) noexcept
: loop{std::move(ptr)} : loop{std::move(ptr)} {}
{}
UVW_INLINE std::shared_ptr<Loop> Loop::create() { UVW_INLINE std::shared_ptr<Loop> Loop::create() {
auto ptr = std::unique_ptr<uv_loop_t, Deleter>{new uv_loop_t, [](uv_loop_t *l) { auto ptr = std::unique_ptr<uv_loop_t, Deleter>{new uv_loop_t, [](uv_loop_t *l) {
delete l; delete l;
}}; }};
auto loop = std::shared_ptr<Loop>{new Loop{std::move(ptr)}}; auto loop = std::shared_ptr<Loop>{new Loop{std::move(ptr)}};
@ -27,13 +23,11 @@ UVW_INLINE std::shared_ptr<Loop> Loop::create() {
return loop; return loop;
} }
UVW_INLINE std::shared_ptr<Loop> Loop::create(uv_loop_t *loop) { UVW_INLINE std::shared_ptr<Loop> Loop::create(uv_loop_t *loop) {
auto ptr = std::unique_ptr<uv_loop_t, Deleter>{loop, [](uv_loop_t *) {}}; auto ptr = std::unique_ptr<uv_loop_t, Deleter>{loop, [](uv_loop_t *) {}};
return std::shared_ptr<Loop>{new Loop{std::move(ptr)}}; return std::shared_ptr<Loop>{new Loop{std::move(ptr)}};
} }
UVW_INLINE std::shared_ptr<Loop> Loop::getDefault() { UVW_INLINE std::shared_ptr<Loop> Loop::getDefault() {
static std::weak_ptr<Loop> ref; static std::weak_ptr<Loop> ref;
std::shared_ptr<Loop> loop; std::shared_ptr<Loop> loop;
@ -54,20 +48,17 @@ UVW_INLINE std::shared_ptr<Loop> Loop::getDefault() {
return loop; return loop;
} }
UVW_INLINE Loop::~Loop() noexcept { UVW_INLINE Loop::~Loop() noexcept {
if(loop) { if(loop) {
close(); close();
} }
} }
UVW_INLINE void Loop::close() { UVW_INLINE void Loop::close() {
auto err = uv_loop_close(loop.get()); auto err = uv_loop_close(loop.get());
return err ? publish(ErrorEvent{err}) : loop.reset(); return err ? publish(ErrorEvent{err}) : loop.reset();
} }
template<Loop::Mode mode> template<Loop::Mode mode>
bool Loop::run() noexcept { bool Loop::run() noexcept {
auto utm = static_cast<std::underlying_type_t<Mode>>(mode); auto utm = static_cast<std::underlying_type_t<Mode>>(mode);
@ -75,43 +66,35 @@ bool Loop::run() noexcept {
return (uv_run(loop.get(), uvrm) == 0); return (uv_run(loop.get(), uvrm) == 0);
} }
UVW_INLINE bool Loop::alive() const noexcept { UVW_INLINE bool Loop::alive() const noexcept {
return !(uv_loop_alive(loop.get()) == 0); return !(uv_loop_alive(loop.get()) == 0);
} }
UVW_INLINE void Loop::stop() noexcept { UVW_INLINE void Loop::stop() noexcept {
uv_stop(loop.get()); uv_stop(loop.get());
} }
UVW_INLINE int Loop::descriptor() const noexcept { UVW_INLINE int Loop::descriptor() const noexcept {
return uv_backend_fd(loop.get()); return uv_backend_fd(loop.get());
} }
UVW_INLINE std::pair<bool, Loop::Time> Loop::timeout() const noexcept { UVW_INLINE std::pair<bool, Loop::Time> Loop::timeout() const noexcept {
auto to = uv_backend_timeout(loop.get()); auto to = uv_backend_timeout(loop.get());
return std::make_pair(to == -1, Time{to}); return std::make_pair(to == -1, Time{to});
} }
UVW_INLINE Loop::Time Loop::idleTime() const noexcept { UVW_INLINE Loop::Time Loop::idleTime() const noexcept {
return Time{uv_metrics_idle_time(loop.get())}; return Time{uv_metrics_idle_time(loop.get())};
} }
UVW_INLINE Loop::Time Loop::now() const noexcept { UVW_INLINE Loop::Time Loop::now() const noexcept {
return Time{uv_now(loop.get())}; return Time{uv_now(loop.get())};
} }
UVW_INLINE void Loop::update() const noexcept { UVW_INLINE void Loop::update() const noexcept {
return uv_update_time(loop.get()); return uv_update_time(loop.get());
} }
UVW_INLINE void Loop::fork() noexcept { UVW_INLINE void Loop::fork() noexcept {
auto err = uv_loop_fork(loop.get()); auto err = uv_loop_fork(loop.get());
@ -120,22 +103,18 @@ UVW_INLINE void Loop::fork() noexcept {
} }
} }
UVW_INLINE void Loop::data(std::shared_ptr<void> uData) { UVW_INLINE void Loop::data(std::shared_ptr<void> uData) {
userData = std::move(uData); userData = std::move(uData);
} }
UVW_INLINE const uv_loop_t *Loop::raw() const noexcept { UVW_INLINE const uv_loop_t *Loop::raw() const noexcept {
return loop.get(); return loop.get();
} }
UVW_INLINE uv_loop_t *Loop::raw() noexcept { UVW_INLINE uv_loop_t *Loop::raw() noexcept {
return const_cast<uv_loop_t *>(const_cast<const Loop *>(this)->raw()); return const_cast<uv_loop_t *>(const_cast<const Loop *>(this)->raw());
} }
// explicit instantiations // explicit instantiations
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
template bool Loop::run<Loop::Mode::DEFAULT>() noexcept; template bool Loop::run<Loop::Mode::DEFAULT>() noexcept;
@ -143,4 +122,4 @@ template bool Loop::run<Loop::Mode::ONCE>() noexcept;
template bool Loop::run<Loop::Mode::NOWAIT>() noexcept; template bool Loop::run<Loop::Mode::NOWAIT>() noexcept;
#endif // UVW_AS_LIB #endif // UVW_AS_LIB
} } // namespace uvw

View File

@ -1,24 +1,21 @@
#ifndef UVW_LOOP_INCLUDE_H #ifndef UVW_LOOP_INCLUDE_H
#define UVW_LOOP_INCLUDE_H #define UVW_LOOP_INCLUDE_H
#ifdef _WIN32 #ifdef _WIN32
#include <ciso646> # include <ciso646>
#endif #endif
#include <chrono>
#include <functional> #include <functional>
#include <memory> #include <memory>
#include <utility>
#include <type_traits> #include <type_traits>
#include <chrono> #include <utility>
#include <uv.h> #include <uv.h>
#include "emitter.h" #include "emitter.h"
#include "util.h" #include "util.h"
namespace uvw { namespace uvw {
class AsyncHandle; class AsyncHandle;
class CheckHandle; class CheckHandle;
class FsEventHandle; class FsEventHandle;
@ -34,25 +31,20 @@ class TimerHandle;
class TTYHandle; class TTYHandle;
class UDPHandle; class UDPHandle;
namespace details { namespace details {
enum class UVLoopOption : std::underlying_type_t<uv_loop_option> {
enum class UVLoopOption: std::underlying_type_t<uv_loop_option> {
BLOCK_SIGNAL = UV_LOOP_BLOCK_SIGNAL, BLOCK_SIGNAL = UV_LOOP_BLOCK_SIGNAL,
IDLE_TIME = UV_METRICS_IDLE_TIME IDLE_TIME = UV_METRICS_IDLE_TIME
}; };
enum class UVRunMode : std::underlying_type_t<uv_run_mode> {
enum class UVRunMode: std::underlying_type_t<uv_run_mode> {
DEFAULT = UV_RUN_DEFAULT, DEFAULT = UV_RUN_DEFAULT,
ONCE = UV_RUN_ONCE, ONCE = UV_RUN_ONCE,
NOWAIT = UV_RUN_NOWAIT NOWAIT = UV_RUN_NOWAIT
}; };
} // namespace details
}
/** /**
* @brief The Loop class. * @brief The Loop class.
@ -63,20 +55,20 @@ enum class UVRunMode: std::underlying_type_t<uv_run_mode> {
* different sources of events. * different sources of events.
*/ */
class Loop final: public Emitter<Loop>, public std::enable_shared_from_this<Loop> { class Loop final: public Emitter<Loop>, public std::enable_shared_from_this<Loop> {
using Deleter = void(*)(uv_loop_t *); using Deleter = void (*)(uv_loop_t *);
template<typename, typename> template<typename, typename>
friend class Resource; friend class Resource;
template<typename R, typename... Args> template<typename R, typename... Args>
auto create_resource(int, Args&&... args) -> decltype(std::declval<R>().init(), std::shared_ptr<R>{}) { auto create_resource(int, Args &&...args) -> decltype(std::declval<R>().init(), std::shared_ptr<R>{}) {
auto ptr = R::create(shared_from_this(), std::forward<Args>(args)...); auto ptr = R::create(shared_from_this(), std::forward<Args>(args)...);
ptr = ptr->init() ? ptr : nullptr; ptr = ptr->init() ? ptr : nullptr;
return ptr; return ptr;
} }
template<typename R, typename... Args> template<typename R, typename... Args>
std::shared_ptr<R> create_resource(char, Args&&... args) { std::shared_ptr<R> create_resource(char, Args &&...args) {
return R::create(shared_from_this(), std::forward<Args>(args)...); return R::create(shared_from_this(), std::forward<Args>(args)...);
} }
@ -121,8 +113,9 @@ public:
Loop(const Loop &) = delete; Loop(const Loop &) = delete;
Loop(Loop &&other) = delete; Loop(Loop &&other) = delete;
Loop & operator=(const Loop &) = delete;
Loop & operator=(Loop &&other) = delete; Loop &operator=(const Loop &) = delete;
Loop &operator=(Loop &&other) = delete;
~Loop() noexcept; ~Loop() noexcept;
@ -146,7 +139,7 @@ public:
* for further details. * for further details.
*/ */
template<typename... Args> template<typename... Args>
void configure(Configure flag, Args&&... args) { void configure(Configure flag, Args &&...args) {
auto option = static_cast<std::underlying_type_t<Configure>>(flag); auto option = static_cast<std::underlying_type_t<Configure>>(flag);
auto err = uv_loop_configure(loop.get(), static_cast<uv_loop_option>(option), std::forward<Args>(args)...); auto err = uv_loop_configure(loop.get(), static_cast<uv_loop_option>(option), std::forward<Args>(args)...);
if(err) { publish(ErrorEvent{err}); } if(err) { publish(ErrorEvent{err}); }
@ -163,7 +156,7 @@ public:
* @return A pointer to the newly created resource. * @return A pointer to the newly created resource.
*/ */
template<typename R, typename... Args> template<typename R, typename... Args>
std::shared_ptr<R> resource(Args&&... args) { std::shared_ptr<R> resource(Args &&...args) {
return create_resource<R>(0, std::forward<Args>(args)...); return create_resource<R>(0, std::forward<Args>(args)...);
} }
@ -234,10 +227,10 @@ public:
std::pair<bool, Time> timeout() const noexcept; std::pair<bool, Time> timeout() const noexcept;
/** /**
* @brief Returns the amount of time the event loop has been idle. The call * @brief Returns the amount of time the event loop has been idle. The call
* is thread safe. * is thread safe.
* @return The accumulated time spent idle. * @return The accumulated time spent idle.
*/ */
Time idleTime() const noexcept; Time idleTime() const noexcept;
/** /**
@ -274,8 +267,7 @@ public:
*/ */
template<typename Func> template<typename Func>
void walk(Func callback) { void walk(Func callback) {
// remember: non-capturing lambdas decay to pointers to functions auto func = [](uv_handle_t *handle, void *func) {
uv_walk(loop.get(), [](uv_handle_t *handle, void *func) {
if(handle->data) { if(handle->data) {
auto &cb = *static_cast<Func *>(func); auto &cb = *static_cast<Func *>(func);
@ -327,7 +319,9 @@ public:
break; break;
} }
} }
}, &callback); };
uv_walk(loop.get(), func, &callback);
} }
/** /**
@ -392,7 +386,7 @@ public:
* *
* @return The underlying raw data structure. * @return The underlying raw data structure.
*/ */
const uv_loop_t * raw() const noexcept; const uv_loop_t *raw() const noexcept;
/** /**
* @brief Gets the underlying raw data structure. * @brief Gets the underlying raw data structure.
@ -409,14 +403,13 @@ public:
* *
* @return The underlying raw data structure. * @return The underlying raw data structure.
*/ */
uv_loop_t * raw() noexcept; uv_loop_t *raw() noexcept;
private: private:
std::unique_ptr<uv_loop_t, Deleter> loop; std::unique_ptr<uv_loop_t, Deleter> loop;
std::shared_ptr<void> userData{nullptr}; std::shared_ptr<void> userData{nullptr};
}; };
// (extern) explicit instantiations // (extern) explicit instantiations
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
extern template bool Loop::run<Loop::Mode::DEFAULT>() noexcept; extern template bool Loop::run<Loop::Mode::DEFAULT>() noexcept;
@ -424,11 +417,10 @@ extern template bool Loop::run<Loop::Mode::ONCE>() noexcept;
extern template bool Loop::run<Loop::Mode::NOWAIT>() noexcept; extern template bool Loop::run<Loop::Mode::NOWAIT>() noexcept;
#endif // UVW_AS_LIB #endif // UVW_AS_LIB
} } // namespace uvw
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "loop.cpp" # include "loop.cpp"
#endif #endif
#endif // UVW_LOOP_INCLUDE_H #endif // UVW_LOOP_INCLUDE_H

View File

@ -1,34 +1,27 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "pipe.h" # include "pipe.h"
#endif #endif
#include <utility> #include <utility>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE PipeHandle::PipeHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, bool pass) UVW_INLINE PipeHandle::PipeHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, bool pass)
: StreamHandle{ca, std::move(ref)}, ipc{pass} : StreamHandle{ca, std::move(ref)}, ipc{pass} {}
{}
UVW_INLINE bool PipeHandle::init() { UVW_INLINE bool PipeHandle::init() {
return initialize(&uv_pipe_init, ipc); return initialize(&uv_pipe_init, ipc);
} }
UVW_INLINE void PipeHandle::open(FileHandle file) { UVW_INLINE void PipeHandle::open(FileHandle file) {
invoke(&uv_pipe_open, get(), file); invoke(&uv_pipe_open, get(), file);
} }
UVW_INLINE void PipeHandle::bind(const std::string &name) { UVW_INLINE void PipeHandle::bind(const std::string &name) {
invoke(&uv_pipe_bind, get(), name.data()); invoke(&uv_pipe_bind, get(), name.data());
} }
UVW_INLINE void PipeHandle::connect(const std::string &name) { UVW_INLINE void PipeHandle::connect(const std::string &name) {
auto listener = [ptr = shared_from_this()](const auto &event, const auto &) { auto listener = [ptr = shared_from_this()](const auto &event, const auto &) {
ptr->publish(event); ptr->publish(event);
@ -40,36 +33,29 @@ UVW_INLINE void PipeHandle::connect(const std::string &name) {
connect->connect(&uv_pipe_connect, get(), name.data()); connect->connect(&uv_pipe_connect, get(), name.data());
} }
UVW_INLINE std::string PipeHandle::sock() const noexcept { UVW_INLINE std::string PipeHandle::sock() const noexcept {
return details::tryRead(&uv_pipe_getsockname, get()); return details::tryRead(&uv_pipe_getsockname, get());
} }
UVW_INLINE std::string PipeHandle::peer() const noexcept { UVW_INLINE std::string PipeHandle::peer() const noexcept {
return details::tryRead(&uv_pipe_getpeername, get()); return details::tryRead(&uv_pipe_getpeername, get());
} }
UVW_INLINE void PipeHandle::pending(int count) noexcept { UVW_INLINE void PipeHandle::pending(int count) noexcept {
uv_pipe_pending_instances(get(), count); uv_pipe_pending_instances(get(), count);
} }
UVW_INLINE int PipeHandle::pending() noexcept { UVW_INLINE int PipeHandle::pending() noexcept {
return uv_pipe_pending_count(get()); return uv_pipe_pending_count(get());
} }
UVW_INLINE HandleType PipeHandle::receive() noexcept { UVW_INLINE HandleType PipeHandle::receive() noexcept {
HandleCategory category = uv_pipe_pending_type(get()); HandleCategory category = uv_pipe_pending_type(get());
return Utilities::guessHandle(category); return Utilities::guessHandle(category);
} }
UVW_INLINE bool PipeHandle::chmod(Flags<Chmod> flags) noexcept { UVW_INLINE bool PipeHandle::chmod(Flags<Chmod> flags) noexcept {
return (0 == uv_pipe_chmod(get(), flags)); return (0 == uv_pipe_chmod(get(), flags));
} }
} // namespace uvw
}

View File

@ -1,32 +1,26 @@
#ifndef UVW_PIPE_INCLUDE_H #ifndef UVW_PIPE_INCLUDE_H
#define UVW_PIPE_INCLUDE_H #define UVW_PIPE_INCLUDE_H
#include <type_traits>
#include <memory> #include <memory>
#include <string> #include <string>
#include <type_traits>
#include <uv.h> #include <uv.h>
#include "loop.h"
#include "request.hpp" #include "request.hpp"
#include "stream.h" #include "stream.h"
#include "util.h" #include "util.h"
#include "loop.h"
namespace uvw { namespace uvw {
namespace details { namespace details {
enum class UVChmodFlags : std::underlying_type_t<uv_poll_event> {
enum class UVChmodFlags: std::underlying_type_t<uv_poll_event> {
READABLE = UV_READABLE, READABLE = UV_READABLE,
WRITABLE = UV_WRITABLE WRITABLE = UV_WRITABLE
}; };
} }
/** /**
* @brief The PipeHandle handle. * @brief The PipeHandle handle.
* *
@ -156,13 +150,10 @@ private:
bool ipc; bool ipc;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "pipe.cpp" # include "pipe.cpp"
#endif #endif
#endif // UVW_PIPE_INCLUDE_H #endif // UVW_PIPE_INCLUDE_H

View File

@ -1,29 +1,21 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "poll.h" # include "poll.h"
#endif #endif
#include <utility> #include <utility>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE PollEvent::PollEvent(Flags<details::UVPollEvent> events) noexcept UVW_INLINE PollEvent::PollEvent(Flags<details::UVPollEvent> events) noexcept
: flags{std::move(events)} : flags{std::move(events)} {}
{}
UVW_INLINE PollHandle::PollHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, int desc) UVW_INLINE PollHandle::PollHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, int desc)
: Handle{ca, std::move(ref)}, tag{FD}, file_desc{desc} : Handle{ca, std::move(ref)}, tag{FD}, file_desc{desc} {}
{}
UVW_INLINE PollHandle::PollHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, OSSocketHandle sock) UVW_INLINE PollHandle::PollHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, OSSocketHandle sock)
: Handle{ca, std::move(ref)}, tag{SOCKET}, socket{sock} : Handle{ca, std::move(ref)}, tag{SOCKET}, socket{sock} {}
{}
UVW_INLINE void PollHandle::startCallback(uv_poll_t *handle, int status, int events) { UVW_INLINE void PollHandle::startCallback(uv_poll_t *handle, int status, int events) {
PollHandle &poll = *(static_cast<PollHandle *>(handle->data)); PollHandle &poll = *(static_cast<PollHandle *>(handle->data));
@ -35,25 +27,20 @@ UVW_INLINE void PollHandle::startCallback(uv_poll_t *handle, int status, int eve
} }
} }
UVW_INLINE bool PollHandle::init() { UVW_INLINE bool PollHandle::init() {
return (tag == SOCKET) ? initialize(&uv_poll_init_socket, socket) : initialize(&uv_poll_init, file_desc); return (tag == SOCKET) ? initialize(&uv_poll_init_socket, socket) : initialize(&uv_poll_init, file_desc);
} }
UVW_INLINE void PollHandle::start(Flags<PollHandle::Event> flags) { UVW_INLINE void PollHandle::start(Flags<PollHandle::Event> flags) {
invoke(&uv_poll_start, get(), flags, &startCallback); invoke(&uv_poll_start, get(), flags, &startCallback);
} }
UVW_INLINE void PollHandle::start(PollHandle::Event event) { UVW_INLINE void PollHandle::start(PollHandle::Event event) {
start(Flags<Event>{event}); start(Flags<Event>{event});
} }
UVW_INLINE void PollHandle::stop() { UVW_INLINE void PollHandle::stop() {
invoke(&uv_poll_stop, get()); invoke(&uv_poll_stop, get());
} }
} // namespace uvw
}

View File

@ -1,31 +1,25 @@
#ifndef UVW_POLL_INCLUDE_H #ifndef UVW_POLL_INCLUDE_H
#define UVW_POLL_INCLUDE_H #define UVW_POLL_INCLUDE_H
#include <type_traits>
#include <memory> #include <memory>
#include <type_traits>
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "util.h" #include "util.h"
namespace uvw { namespace uvw {
namespace details { namespace details {
enum class UVPollEvent : std::underlying_type_t<uv_poll_event> {
enum class UVPollEvent: std::underlying_type_t<uv_poll_event> {
READABLE = UV_READABLE, READABLE = UV_READABLE,
WRITABLE = UV_WRITABLE, WRITABLE = UV_WRITABLE,
DISCONNECT = UV_DISCONNECT, DISCONNECT = UV_DISCONNECT,
PRIORITIZED = UV_PRIORITIZED PRIORITIZED = UV_PRIORITIZED
}; };
} }
/** /**
* @brief PollEvent event. * @brief PollEvent event.
* *
@ -47,7 +41,6 @@ struct PollEvent {
Flags<details::UVPollEvent> flags; Flags<details::UVPollEvent> flags;
}; };
/** /**
* @brief The PollHandle handle. * @brief The PollHandle handle.
* *
@ -127,19 +120,21 @@ public:
void stop(); void stop();
private: private:
enum { FD, SOCKET } tag; enum {
FD,
SOCKET
} tag;
union { union {
int file_desc; int file_desc;
OSSocketHandle::Type socket; OSSocketHandle::Type socket;
}; };
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "poll.cpp" # include "poll.cpp"
#endif #endif
#endif // UVW_POLL_INCLUDE_H #endif // UVW_POLL_INCLUDE_H

View File

@ -1,32 +1,26 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "prepare.h" # include "prepare.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE void PrepareHandle::startCallback(uv_prepare_t *handle) { UVW_INLINE void PrepareHandle::startCallback(uv_prepare_t *handle) {
PrepareHandle &prepare = *(static_cast<PrepareHandle *>(handle->data)); PrepareHandle &prepare = *(static_cast<PrepareHandle *>(handle->data));
prepare.publish(PrepareEvent{}); prepare.publish(PrepareEvent{});
} }
UVW_INLINE bool PrepareHandle::init() { UVW_INLINE bool PrepareHandle::init() {
return initialize(&uv_prepare_init); return initialize(&uv_prepare_init);
} }
UVW_INLINE void PrepareHandle::start() { UVW_INLINE void PrepareHandle::start() {
invoke(&uv_prepare_start, get(), &startCallback); invoke(&uv_prepare_start, get(), &startCallback);
} }
UVW_INLINE void PrepareHandle::stop() { UVW_INLINE void PrepareHandle::stop() {
invoke(&uv_prepare_stop, get()); invoke(&uv_prepare_stop, get());
} }
} // namespace uvw
}

View File

@ -1,15 +1,12 @@
#ifndef UVW_PREPARE_INCLUDE_H #ifndef UVW_PREPARE_INCLUDE_H
#define UVW_PREPARE_INCLUDE_H #define UVW_PREPARE_INCLUDE_H
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "loop.h" #include "loop.h"
namespace uvw { namespace uvw {
/** /**
* @brief PrepareEvent event. * @brief PrepareEvent event.
* *
@ -17,7 +14,6 @@ namespace uvw {
*/ */
struct PrepareEvent {}; struct PrepareEvent {};
/** /**
* @brief The PrepareHandle handle. * @brief The PrepareHandle handle.
* *
@ -54,12 +50,10 @@ public:
void stop(); void stop();
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "prepare.cpp" # include "prepare.cpp"
#endif #endif
#endif // UVW_PREPARE_INCLUDE_H #endif // UVW_PREPARE_INCLUDE_H

View File

@ -1,47 +1,37 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "process.h" # include "process.h"
#endif #endif
#include <algorithm> #include <algorithm>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE ExitEvent::ExitEvent(int64_t code, int sig) noexcept UVW_INLINE ExitEvent::ExitEvent(int64_t code, int sig) noexcept
: status{code}, signal{sig} : status{code}, signal{sig} {}
{}
UVW_INLINE void ProcessHandle::exitCallback(uv_process_t *handle, int64_t exitStatus, int termSignal) { UVW_INLINE void ProcessHandle::exitCallback(uv_process_t *handle, int64_t exitStatus, int termSignal) {
ProcessHandle &process = *(static_cast<ProcessHandle *>(handle->data)); ProcessHandle &process = *(static_cast<ProcessHandle *>(handle->data));
process.publish(ExitEvent{exitStatus, termSignal}); process.publish(ExitEvent{exitStatus, termSignal});
} }
UVW_INLINE ProcessHandle::ProcessHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref) UVW_INLINE ProcessHandle::ProcessHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref)
: Handle{ca, std::move(ref)} : Handle{ca, std::move(ref)} {}
{}
UVW_INLINE void ProcessHandle::disableStdIOInheritance() noexcept { UVW_INLINE void ProcessHandle::disableStdIOInheritance() noexcept {
uv_disable_stdio_inheritance(); uv_disable_stdio_inheritance();
} }
UVW_INLINE bool ProcessHandle::kill(int pid, int signum) noexcept { UVW_INLINE bool ProcessHandle::kill(int pid, int signum) noexcept {
return (0 == uv_kill(pid, signum)); return (0 == uv_kill(pid, signum));
} }
UVW_INLINE bool ProcessHandle::init() { UVW_INLINE bool ProcessHandle::init() {
// deferred initialization: libuv initializes process handles only when // deferred initialization: libuv initializes process handles only when
// uv_spawn is invoked and uvw stays true to the underlying library // uv_spawn is invoked and uvw stays true to the underlying library
return true; return true;
} }
UVW_INLINE void ProcessHandle::spawn(const char *file, char **args, char **env) { UVW_INLINE void ProcessHandle::spawn(const char *file, char **args, char **env) {
uv_process_options_t po; uv_process_options_t po;
@ -71,29 +61,24 @@ UVW_INLINE void ProcessHandle::spawn(const char *file, char **args, char **env)
invoke(&uv_spawn, parent(), get(), &po); invoke(&uv_spawn, parent(), get(), &po);
} }
UVW_INLINE void ProcessHandle::kill(int signum) { UVW_INLINE void ProcessHandle::kill(int signum) {
invoke(&uv_process_kill, get(), signum); invoke(&uv_process_kill, get(), signum);
} }
UVW_INLINE int ProcessHandle::pid() noexcept { UVW_INLINE int ProcessHandle::pid() noexcept {
return get()->pid; return get()->pid;
} }
UVW_INLINE ProcessHandle &ProcessHandle::cwd(const std::string &path) noexcept { UVW_INLINE ProcessHandle &ProcessHandle::cwd(const std::string &path) noexcept {
poCwd = path; poCwd = path;
return *this; return *this;
} }
UVW_INLINE ProcessHandle &ProcessHandle::flags(Flags<Process> flags) noexcept { UVW_INLINE ProcessHandle &ProcessHandle::flags(Flags<Process> flags) noexcept {
poFlags = flags; poFlags = flags;
return *this; return *this;
} }
UVW_INLINE ProcessHandle &ProcessHandle::stdio(FileHandle fd, Flags<StdIO> flags) { UVW_INLINE ProcessHandle &ProcessHandle::stdio(FileHandle fd, Flags<StdIO> flags) {
auto fgs = static_cast<uv_stdio_flags>(Flags<StdIO>::Type{flags}); auto fgs = static_cast<uv_stdio_flags>(Flags<StdIO>::Type{flags});
@ -116,17 +101,14 @@ UVW_INLINE ProcessHandle &ProcessHandle::stdio(FileHandle fd, Flags<StdIO> flags
return *this; return *this;
} }
UVW_INLINE ProcessHandle &ProcessHandle::uid(Uid id) { UVW_INLINE ProcessHandle &ProcessHandle::uid(Uid id) {
poUid = id; poUid = id;
return *this; return *this;
} }
UVW_INLINE ProcessHandle &ProcessHandle::gid(Gid id) { UVW_INLINE ProcessHandle &ProcessHandle::gid(Gid id) {
poGid = id; poGid = id;
return *this; return *this;
} }
} // namespace uvw
}

View File

@ -1,25 +1,21 @@
#ifndef UVW_PROCESS_INCLUDE_H #ifndef UVW_PROCESS_INCLUDE_H
#define UVW_PROCESS_INCLUDE_H #define UVW_PROCESS_INCLUDE_H
#include <utility>
#include <memory> #include <memory>
#include <string> #include <string>
#include <utility>
#include <vector> #include <vector>
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "loop.h"
#include "stream.h" #include "stream.h"
#include "util.h" #include "util.h"
#include "loop.h"
namespace uvw { namespace uvw {
namespace details { namespace details {
enum class UVProcessFlags : std::underlying_type_t<uv_process_flags> {
enum class UVProcessFlags: std::underlying_type_t<uv_process_flags> {
SETUID = UV_PROCESS_SETUID, SETUID = UV_PROCESS_SETUID,
SETGID = UV_PROCESS_SETGID, SETGID = UV_PROCESS_SETGID,
WINDOWS_VERBATIM_ARGUMENTS = UV_PROCESS_WINDOWS_VERBATIM_ARGUMENTS, WINDOWS_VERBATIM_ARGUMENTS = UV_PROCESS_WINDOWS_VERBATIM_ARGUMENTS,
@ -29,8 +25,7 @@ enum class UVProcessFlags: std::underlying_type_t<uv_process_flags> {
WINDOWS_HIDE_GUI = UV_PROCESS_WINDOWS_HIDE_GUI WINDOWS_HIDE_GUI = UV_PROCESS_WINDOWS_HIDE_GUI
}; };
enum class UVStdIOFlags : std::underlying_type_t<uv_stdio_flags> {
enum class UVStdIOFlags: std::underlying_type_t<uv_stdio_flags> {
IGNORE_STREAM = UV_IGNORE, IGNORE_STREAM = UV_IGNORE,
CREATE_PIPE = UV_CREATE_PIPE, CREATE_PIPE = UV_CREATE_PIPE,
INHERIT_FD = UV_INHERIT_FD, INHERIT_FD = UV_INHERIT_FD,
@ -40,9 +35,7 @@ enum class UVStdIOFlags: std::underlying_type_t<uv_stdio_flags> {
OVERLAPPED_PIPE = UV_OVERLAPPED_PIPE OVERLAPPED_PIPE = UV_OVERLAPPED_PIPE
}; };
} // namespace details
}
/** /**
* @brief ExitEvent event. * @brief ExitEvent event.
@ -53,7 +46,7 @@ struct ExitEvent {
explicit ExitEvent(int64_t code, int sig) noexcept; explicit ExitEvent(int64_t code, int sig) noexcept;
int64_t status; /*!< The exit status. */ int64_t status; /*!< The exit status. */
int signal; /*!< The signal that caused the process to terminate, if any. */ int signal; /*!< The signal that caused the process to terminate, if any. */
}; };
/** /**
@ -137,7 +130,7 @@ public:
* @param path The working directory to be used when `spawn()` is invoked. * @param path The working directory to be used when `spawn()` is invoked.
* @return A reference to this process handle. * @return A reference to this process handle.
*/ */
ProcessHandle & cwd(const std::string &path) noexcept; ProcessHandle &cwd(const std::string &path) noexcept;
/** /**
* @brief Sets flags that control how `spawn()` behaves. * @brief Sets flags that control how `spawn()` behaves.
@ -159,7 +152,7 @@ public:
* @param flags A valid set of flags. * @param flags A valid set of flags.
* @return A reference to this process handle. * @return A reference to this process handle.
*/ */
ProcessHandle & flags(Flags<Process> flags) noexcept; ProcessHandle &flags(Flags<Process> flags) noexcept;
/** /**
* @brief Makes a `stdio` handle available to the child process. * @brief Makes a `stdio` handle available to the child process.
@ -183,7 +176,7 @@ public:
* @return A reference to this process handle. * @return A reference to this process handle.
*/ */
template<typename T, typename U> template<typename T, typename U>
ProcessHandle & stdio(StreamHandle<T, U> &stream, Flags<StdIO> flags) { ProcessHandle &stdio(StreamHandle<T, U> &stream, Flags<StdIO> flags) {
uv_stdio_container_t container; uv_stdio_container_t container;
Flags<StdIO>::Type fgs = flags; Flags<StdIO>::Type fgs = flags;
container.flags = static_cast<uv_stdio_flags>(fgs); container.flags = static_cast<uv_stdio_flags>(fgs);
@ -218,21 +211,21 @@ public:
* @param flags A valid set of flags. * @param flags A valid set of flags.
* @return A reference to this process handle. * @return A reference to this process handle.
*/ */
ProcessHandle & stdio(FileHandle fd, Flags<StdIO> flags); ProcessHandle &stdio(FileHandle fd, Flags<StdIO> flags);
/** /**
* @brief Sets the child process' user id. * @brief Sets the child process' user id.
* @param id A valid user id to be used. * @param id A valid user id to be used.
* @return A reference to this process handle. * @return A reference to this process handle.
*/ */
ProcessHandle & uid(Uid id); ProcessHandle &uid(Uid id);
/** /**
* @brief Sets the child process' group id. * @brief Sets the child process' group id.
* @param id A valid group id to be used. * @param id A valid group id to be used.
* @return A reference to this process handle. * @return A reference to this process handle.
*/ */
ProcessHandle & gid(Gid id); ProcessHandle &gid(Gid id);
private: private:
std::string poCwd; std::string poCwd;
@ -243,13 +236,10 @@ private:
Gid poGid; Gid poGid;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "process.cpp" # include "process.cpp"
#endif #endif
#endif // UVW_PROCESS_INCLUDE_H #endif // UVW_PROCESS_INCLUDE_H

View File

@ -1,17 +1,14 @@
#ifndef UVW_REQUEST_INCLUDE_H #ifndef UVW_REQUEST_INCLUDE_H
#define UVW_REQUEST_INCLUDE_H #define UVW_REQUEST_INCLUDE_H
#include <memory>
#include <type_traits> #include <type_traits>
#include <utility> #include <utility>
#include <memory>
#include <uv.h> #include <uv.h>
#include "resource.hpp" #include "resource.hpp"
namespace uvw { namespace uvw {
/** /**
* @brief Request base class. * @brief Request base class.
* *
@ -21,27 +18,31 @@ template<typename T, typename U>
class Request: public Resource<T, U> { class Request: public Resource<T, U> {
protected: protected:
static auto reserve(U *req) { static auto reserve(U *req) {
auto ptr = static_cast<T*>(req->data)->shared_from_this(); auto ptr = static_cast<T *>(req->data)->shared_from_this();
ptr->reset(); ptr->reset();
return ptr; return ptr;
} }
template<typename E> template<typename E>
static void defaultCallback(U *req, int status) { static void defaultCallback(U *req, int status) {
auto ptr = reserve(req); if(auto ptr = reserve(req); status) {
if(status) { ptr->publish(ErrorEvent{status}); } ptr->publish(ErrorEvent{status});
else { ptr->publish(E{}); } } else {
ptr->publish(E{});
}
} }
template<typename F, typename... Args> template<typename F, typename... Args>
auto invoke(F &&f, Args&&... args) { auto invoke(F &&f, Args &&...args) {
if constexpr(std::is_void_v<std::invoke_result_t<F, Args...>>) { if constexpr(std::is_void_v<std::invoke_result_t<F, Args...>>) {
std::forward<F>(f)(std::forward<Args>(args)...); std::forward<F>(f)(std::forward<Args>(args)...);
this->leak(); this->leak();
} else { } else {
auto err = std::forward<F>(f)(std::forward<Args>(args)...); if(auto err = std::forward<F>(f)(std::forward<Args>(args)...); err) {
if(err) { Emitter<T>::publish(ErrorEvent{err}); } Emitter<T>::publish(ErrorEvent{err});
else { this->leak(); } } else {
this->leak();
}
} }
} }
@ -49,32 +50,31 @@ public:
using Resource<T, U>::Resource; using Resource<T, U>::Resource;
/** /**
* @brief Cancels a pending request. * @brief Cancels a pending request.
* *
* This method fails if the request is executing or has finished * This method fails if the request is executing or has finished
* executing.<br/> * executing.<br/>
* It can emit an ErrorEvent event in case of errors. * It can emit an ErrorEvent event in case of errors.
* *
* See the official * See the official
* [documentation](http://docs.libuv.org/en/v1.x/request.html#c.uv_cancel) * [documentation](http://docs.libuv.org/en/v1.x/request.html#c.uv_cancel)
* for further details. * for further details.
* *
* @return True in case of success, false otherwise. * @return True in case of success, false otherwise.
*/ */
bool cancel() { bool cancel() {
return (0 == uv_cancel(this->template get<uv_req_t>())); return (0 == uv_cancel(this->template get<uv_req_t>()));
} }
/** /**
* @brief Returns the size of the underlying request type. * @brief Returns the size of the underlying request type.
* @return The size of the underlying request type. * @return The size of the underlying request type.
*/ */
std::size_t size() const noexcept { std::size_t size() const noexcept {
return uv_req_size(this->template get<uv_req_t>()->type); return uv_req_size(this->template get<uv_req_t>()->type);
} }
}; };
} // namespace uvw
}
#endif // UVW_REQUEST_INCLUDE_H #endif // UVW_REQUEST_INCLUDE_H

View File

@ -1,16 +1,13 @@
#ifndef UVW_RESOURCE_INCLUDE_H #ifndef UVW_RESOURCE_INCLUDE_H
#define UVW_RESOURCE_INCLUDE_H #define UVW_RESOURCE_INCLUDE_H
#include <memory> #include <memory>
#include <utility> #include <utility>
#include "emitter.h" #include "emitter.h"
#include "underlying_type.hpp" #include "underlying_type.hpp"
namespace uvw { namespace uvw {
/** /**
* @brief Common class for almost all the resources available in `uvw`. * @brief Common class for almost all the resources available in `uvw`.
* *
@ -39,8 +36,7 @@ protected:
public: public:
explicit Resource(ConstructorAccess ca, std::shared_ptr<Loop> ref) explicit Resource(ConstructorAccess ca, std::shared_ptr<Loop> ref)
: UnderlyingType<T, U>{ca, std::move(ref)} : UnderlyingType<T, U>{ca, std::move(ref)} {
{
this->get()->data = this; this->get()->data = this;
} }
@ -66,6 +62,6 @@ private:
std::shared_ptr<void> sPtr{nullptr}; std::shared_ptr<void> sPtr{nullptr};
}; };
} } // namespace uvw
#endif // UVW_RESOURCE_INCLUDE_H #endif // UVW_RESOURCE_INCLUDE_H

View File

@ -1,47 +1,37 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "signal.h" # include "signal.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE SignalEvent::SignalEvent(int sig) noexcept UVW_INLINE SignalEvent::SignalEvent(int sig) noexcept
: signum{sig} : signum{sig} {}
{}
UVW_INLINE void SignalHandle::startCallback(uv_signal_t *handle, int signum) { UVW_INLINE void SignalHandle::startCallback(uv_signal_t *handle, int signum) {
SignalHandle &signal = *(static_cast<SignalHandle *>(handle->data)); SignalHandle &signal = *(static_cast<SignalHandle *>(handle->data));
signal.publish(SignalEvent{signum}); signal.publish(SignalEvent{signum});
} }
UVW_INLINE bool SignalHandle::init() { UVW_INLINE bool SignalHandle::init() {
return initialize(&uv_signal_init); return initialize(&uv_signal_init);
} }
UVW_INLINE void SignalHandle::start(int signum) { UVW_INLINE void SignalHandle::start(int signum) {
invoke(&uv_signal_start, get(), &startCallback, signum); invoke(&uv_signal_start, get(), &startCallback, signum);
} }
UVW_INLINE void SignalHandle::oneShot(int signum) { UVW_INLINE void SignalHandle::oneShot(int signum) {
invoke(&uv_signal_start_oneshot, get(), &startCallback, signum); invoke(&uv_signal_start_oneshot, get(), &startCallback, signum);
} }
UVW_INLINE void SignalHandle::stop() { UVW_INLINE void SignalHandle::stop() {
invoke(&uv_signal_stop, get()); invoke(&uv_signal_stop, get());
} }
UVW_INLINE int SignalHandle::signal() const noexcept { UVW_INLINE int SignalHandle::signal() const noexcept {
return get()->signum; return get()->signum;
} }
} // namespace uvw
}

View File

@ -1,15 +1,12 @@
#ifndef UVW_SIGNAL_INCLUDE_H #ifndef UVW_SIGNAL_INCLUDE_H
#define UVW_SIGNAL_INCLUDE_H #define UVW_SIGNAL_INCLUDE_H
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "loop.h" #include "loop.h"
namespace uvw { namespace uvw {
/** /**
* @brief SignalEvent event. * @brief SignalEvent event.
* *
@ -21,7 +18,6 @@ struct SignalEvent {
int signum; /*!< The signal being monitored by this handle. */ int signum; /*!< The signal being monitored by this handle. */
}; };
/** /**
* @brief The SignalHandle handle. * @brief The SignalHandle handle.
* *
@ -78,12 +74,10 @@ public:
int signal() const noexcept; int signal() const noexcept;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "signal.cpp" # include "signal.cpp"
#endif #endif
#endif // UVW_SIGNAL_INCLUDE_H #endif // UVW_SIGNAL_INCLUDE_H

View File

@ -1,21 +1,16 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "stream.h" # include "stream.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE DataEvent::DataEvent(std::unique_ptr<char[]> buf, std::size_t len) noexcept UVW_INLINE DataEvent::DataEvent(std::unique_ptr<char[]> buf, std::size_t len) noexcept
: data{std::move(buf)}, length{len} : data{std::move(buf)}, length{len} {}
{}
UVW_INLINE void details::ShutdownReq::shutdown(uv_stream_t *handle) { UVW_INLINE void details::ShutdownReq::shutdown(uv_stream_t *handle) {
invoke(&uv_shutdown, get(), handle, &defaultCallback<ShutdownEvent>); invoke(&uv_shutdown, get(), handle, &defaultCallback<ShutdownEvent>);
} }
} // namespace uvw
}

View File

@ -1,21 +1,18 @@
#ifndef UVW_STREAM_INCLUDE_H #ifndef UVW_STREAM_INCLUDE_H
#define UVW_STREAM_INCLUDE_H #define UVW_STREAM_INCLUDE_H
#include <algorithm> #include <algorithm>
#include <iterator>
#include <cstddef> #include <cstddef>
#include <utility> #include <iterator>
#include <memory> #include <memory>
#include <utility>
#include <uv.h> #include <uv.h>
#include "request.hpp"
#include "handle.hpp" #include "handle.hpp"
#include "loop.h" #include "loop.h"
#include "request.hpp"
namespace uvw { namespace uvw {
/** /**
* @brief ConnectEvent event. * @brief ConnectEvent event.
* *
@ -23,7 +20,6 @@ namespace uvw {
*/ */
struct ConnectEvent {}; struct ConnectEvent {};
/** /**
* @brief EndEvent event. * @brief EndEvent event.
* *
@ -31,7 +27,6 @@ struct ConnectEvent {};
*/ */
struct EndEvent {}; struct EndEvent {};
/** /**
* @brief ListenEvent event. * @brief ListenEvent event.
* *
@ -39,7 +34,6 @@ struct EndEvent {};
*/ */
struct ListenEvent {}; struct ListenEvent {};
/** /**
* @brief ShutdownEvent event. * @brief ShutdownEvent event.
* *
@ -47,7 +41,6 @@ struct ListenEvent {};
*/ */
struct ShutdownEvent {}; struct ShutdownEvent {};
/** /**
* @brief WriteEvent event. * @brief WriteEvent event.
* *
@ -55,7 +48,6 @@ struct ShutdownEvent {};
*/ */
struct WriteEvent {}; struct WriteEvent {};
/** /**
* @brief DataEvent event. * @brief DataEvent event.
* *
@ -65,30 +57,26 @@ struct DataEvent {
explicit DataEvent(std::unique_ptr<char[]> buf, std::size_t len) noexcept; explicit DataEvent(std::unique_ptr<char[]> buf, std::size_t len) noexcept;
std::unique_ptr<char[]> data; /*!< A bunch of data read on the stream. */ std::unique_ptr<char[]> data; /*!< A bunch of data read on the stream. */
std::size_t length; /*!< The amount of data read on the stream. */ std::size_t length; /*!< The amount of data read on the stream. */
}; };
namespace details { namespace details {
struct ConnectReq final: public Request<ConnectReq, uv_connect_t> { struct ConnectReq final: public Request<ConnectReq, uv_connect_t> {
using Request::Request; using Request::Request;
template<typename F, typename... Args> template<typename F, typename... Args>
void connect(F &&f, Args&&... args) { void connect(F &&f, Args &&...args) {
invoke(std::forward<F>(f), get(), std::forward<Args>(args)..., &defaultCallback<ConnectEvent>); invoke(std::forward<F>(f), get(), std::forward<Args>(args)..., &defaultCallback<ConnectEvent>);
} }
}; };
struct ShutdownReq final: public Request<ShutdownReq, uv_shutdown_t> { struct ShutdownReq final: public Request<ShutdownReq, uv_shutdown_t> {
using Request::Request; using Request::Request;
void shutdown(uv_stream_t *handle); void shutdown(uv_stream_t *handle);
}; };
template<typename Deleter> template<typename Deleter>
class WriteReq final: public Request<WriteReq<Deleter>, uv_write_t> { class WriteReq final: public Request<WriteReq<Deleter>, uv_write_t> {
using ConstructorAccess = typename Request<WriteReq<Deleter>, uv_write_t>::ConstructorAccess; using ConstructorAccess = typename Request<WriteReq<Deleter>, uv_write_t>::ConstructorAccess;
@ -97,8 +85,7 @@ public:
WriteReq(ConstructorAccess ca, std::shared_ptr<Loop> loop, std::unique_ptr<char[], Deleter> dt, unsigned int len) WriteReq(ConstructorAccess ca, std::shared_ptr<Loop> loop, std::unique_ptr<char[], Deleter> dt, unsigned int len)
: Request<WriteReq<Deleter>, uv_write_t>{ca, std::move(loop)}, : Request<WriteReq<Deleter>, uv_write_t>{ca, std::move(loop)},
data{std::move(dt)}, data{std::move(dt)},
buf{uv_buf_init(data.get(), len)} buf{uv_buf_init(data.get(), len)} {}
{}
void write(uv_stream_t *handle) { void write(uv_stream_t *handle) {
this->invoke(&uv_write, this->get(), handle, &buf, 1, &this->template defaultCallback<WriteEvent>); this->invoke(&uv_write, this->get(), handle, &buf, 1, &this->template defaultCallback<WriteEvent>);
@ -113,9 +100,7 @@ private:
uv_buf_t buf; uv_buf_t buf;
}; };
} // namespace details
}
/** /**
* @brief The StreamHandle handle. * @brief The StreamHandle handle.
@ -129,7 +114,7 @@ class StreamHandle: public Handle<T, U> {
static constexpr unsigned int DEFAULT_BACKLOG = 128; static constexpr unsigned int DEFAULT_BACKLOG = 128;
static void readCallback(uv_stream_t *handle, ssize_t nread, const uv_buf_t *buf) { static void readCallback(uv_stream_t *handle, ssize_t nread, const uv_buf_t *buf) {
T &ref = *(static_cast<T*>(handle->data)); T &ref = *(static_cast<T *>(handle->data));
// data will be destroyed no matter of what the value of nread is // data will be destroyed no matter of what the value of nread is
std::unique_ptr<char[]> data{buf->base}; std::unique_ptr<char[]> data{buf->base};
@ -150,16 +135,17 @@ class StreamHandle: public Handle<T, U> {
} }
static void listenCallback(uv_stream_t *handle, int status) { static void listenCallback(uv_stream_t *handle, int status) {
T &ref = *(static_cast<T*>(handle->data)); if(T &ref = *(static_cast<T *>(handle->data)); status) {
if(status) { ref.publish(ErrorEvent{status}); } ref.publish(ErrorEvent{status});
else { ref.publish(ListenEvent{}); } } else {
ref.publish(ListenEvent{});
}
} }
public: public:
#ifdef _MSC_VER #ifdef _MSC_VER
StreamHandle(typename Handle<T, U>::ConstructorAccess ca, std::shared_ptr<Loop> ref) StreamHandle(typename Handle<T, U>::ConstructorAccess ca, std::shared_ptr<Loop> ref)
: Handle<T, U>{ca, std::move(ref)} : Handle<T, U>{ca, std::move(ref)} {}
{}
#else #else
using Handle<T, U>::Handle; using Handle<T, U>::Handle;
#endif #endif
@ -277,7 +263,7 @@ public:
* @param len The lenght of the submitted data. * @param len The lenght of the submitted data.
*/ */
void write(char *data, unsigned int len) { void write(char *data, unsigned int len) {
auto req = this->loop().template resource<details::WriteReq<void(*)(char *)>>(std::unique_ptr<char[], void(*)(char *)>{data, [](char *) {}}, len); auto req = this->loop().template resource<details::WriteReq<void (*)(char *)>>(std::unique_ptr<char[], void (*)(char *)>{data, [](char *) {}}, len);
auto listener = [ptr = this->shared_from_this()](const auto &event, const auto &) { auto listener = [ptr = this->shared_from_this()](const auto &event, const auto &) {
ptr->publish(event); ptr->publish(event);
}; };
@ -339,7 +325,7 @@ public:
*/ */
template<typename S> template<typename S>
void write(S &send, char *data, unsigned int len) { void write(S &send, char *data, unsigned int len) {
auto req = this->loop().template resource<details::WriteReq<void(*)(char *)>>(std::unique_ptr<char[], void(*)(char *)>{data, [](char *) {}}, len); auto req = this->loop().template resource<details::WriteReq<void (*)(char *)>>(std::unique_ptr<char[], void (*)(char *)>{data, [](char *) {}}, len);
auto listener = [ptr = this->shared_from_this()](const auto &event, const auto &) { auto listener = [ptr = this->shared_from_this()](const auto &event, const auto &) {
ptr->publish(event); ptr->publish(event);
}; };
@ -361,7 +347,7 @@ public:
* @return Number of bytes written. * @return Number of bytes written.
*/ */
int tryWrite(std::unique_ptr<char[]> data, unsigned int len) { int tryWrite(std::unique_ptr<char[]> data, unsigned int len) {
uv_buf_t bufs[] = { uv_buf_init(data.get(), len) }; uv_buf_t bufs[] = {uv_buf_init(data.get(), len)};
auto bw = uv_try_write(this->template get<uv_stream_t>(), bufs, 1); auto bw = uv_try_write(this->template get<uv_stream_t>(), bufs, 1);
if(bw < 0) { if(bw < 0) {
@ -377,7 +363,7 @@ public:
* *
* Same as `tryWrite` for sending handles over a pipe.<br/> * Same as `tryWrite` for sending handles over a pipe.<br/>
* An ErrorEvent event will be emitted in case of errors. * An ErrorEvent event will be emitted in case of errors.
* *
* @param data The data to be written to the stream. * @param data The data to be written to the stream.
* @param len The lenght of the submitted data. * @param len The lenght of the submitted data.
* @param send A valid handle suitable for the purpose. * @param send A valid handle suitable for the purpose.
@ -385,7 +371,7 @@ public:
*/ */
template<typename V, typename W> template<typename V, typename W>
int tryWrite(std::unique_ptr<char[]> data, unsigned int len, StreamHandle<V, W> &send) { int tryWrite(std::unique_ptr<char[]> data, unsigned int len, StreamHandle<V, W> &send) {
uv_buf_t bufs[] = { uv_buf_init(data.get(), len) }; uv_buf_t bufs[] = {uv_buf_init(data.get(), len)};
auto bw = uv_try_write2(this->template get<uv_stream_t>(), bufs, 1, send.raw()); auto bw = uv_try_write2(this->template get<uv_stream_t>(), bufs, 1, send.raw());
if(bw < 0) { if(bw < 0) {
@ -408,7 +394,7 @@ public:
* @return Number of bytes written. * @return Number of bytes written.
*/ */
int tryWrite(char *data, unsigned int len) { int tryWrite(char *data, unsigned int len) {
uv_buf_t bufs[] = { uv_buf_init(data, len) }; uv_buf_t bufs[] = {uv_buf_init(data, len)};
auto bw = uv_try_write(this->template get<uv_stream_t>(), bufs, 1); auto bw = uv_try_write(this->template get<uv_stream_t>(), bufs, 1);
if(bw < 0) { if(bw < 0) {
@ -432,7 +418,7 @@ public:
*/ */
template<typename V, typename W> template<typename V, typename W>
int tryWrite(char *data, unsigned int len, StreamHandle<V, W> &send) { int tryWrite(char *data, unsigned int len, StreamHandle<V, W> &send) {
uv_buf_t bufs[] = { uv_buf_init(data, len) }; uv_buf_t bufs[] = {uv_buf_init(data, len)};
auto bw = uv_try_write2(this->template get<uv_stream_t>(), bufs, 1, send.raw()); auto bw = uv_try_write2(this->template get<uv_stream_t>(), bufs, 1, send.raw());
if(bw < 0) { if(bw < 0) {
@ -487,12 +473,10 @@ public:
} }
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "stream.cpp" # include "stream.cpp"
#endif #endif
#endif // UVW_STREAM_INCLUDE_H #endif // UVW_STREAM_INCLUDE_H

View File

@ -1,75 +1,60 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "tcp.h" # include "tcp.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE TCPHandle::TCPHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, unsigned int f) UVW_INLINE TCPHandle::TCPHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, unsigned int f)
: StreamHandle{ca, std::move(ref)}, tag{f ? FLAGS : DEFAULT}, flags{f} : StreamHandle{ca, std::move(ref)}, tag{f ? FLAGS : DEFAULT}, flags{f} {}
{}
UVW_INLINE bool TCPHandle::init() { UVW_INLINE bool TCPHandle::init() {
return (tag == FLAGS) ? initialize(&uv_tcp_init_ex, flags) : initialize(&uv_tcp_init); return (tag == FLAGS) ? initialize(&uv_tcp_init_ex, flags) : initialize(&uv_tcp_init);
} }
UVW_INLINE void TCPHandle::open(OSSocketHandle socket) { UVW_INLINE void TCPHandle::open(OSSocketHandle socket) {
invoke(&uv_tcp_open, get(), socket); invoke(&uv_tcp_open, get(), socket);
} }
UVW_INLINE bool TCPHandle::noDelay(bool value) { UVW_INLINE bool TCPHandle::noDelay(bool value) {
return (0 == uv_tcp_nodelay(get(), value)); return (0 == uv_tcp_nodelay(get(), value));
} }
UVW_INLINE bool TCPHandle::keepAlive(bool enable, TCPHandle::Time time) { UVW_INLINE bool TCPHandle::keepAlive(bool enable, TCPHandle::Time time) {
return (0 == uv_tcp_keepalive(get(), enable, time.count())); return (0 == uv_tcp_keepalive(get(), enable, time.count()));
} }
UVW_INLINE bool TCPHandle::simultaneousAccepts(bool enable) { UVW_INLINE bool TCPHandle::simultaneousAccepts(bool enable) {
return (0 == uv_tcp_simultaneous_accepts(get(), enable)); return (0 == uv_tcp_simultaneous_accepts(get(), enable));
} }
UVW_INLINE void TCPHandle::bind(const sockaddr &addr, Flags<Bind> opts) { UVW_INLINE void TCPHandle::bind(const sockaddr &addr, Flags<Bind> opts) {
invoke(&uv_tcp_bind, get(), &addr, opts); invoke(&uv_tcp_bind, get(), &addr, opts);
} }
template<typename I> template<typename I>
UVW_INLINE void TCPHandle::bind(const std::string &ip, unsigned int port, Flags<Bind> opts) UVW_INLINE void TCPHandle::bind(const std::string &ip, unsigned int port, Flags<Bind> opts) {
{
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
details::IpTraits<I>::addrFunc(ip.data(), port, &addr); details::IpTraits<I>::addrFunc(ip.data(), port, &addr);
bind(reinterpret_cast<const sockaddr &>(addr), std::move(opts)); bind(reinterpret_cast<const sockaddr &>(addr), std::move(opts));
} }
template<typename I> template<typename I>
UVW_INLINE void TCPHandle::bind(Addr addr, Flags<Bind> opts) { UVW_INLINE void TCPHandle::bind(Addr addr, Flags<Bind> opts) {
bind<I>(std::move(addr.ip), addr.port, std::move(opts)); bind<I>(std::move(addr.ip), addr.port, std::move(opts));
} }
template<typename I> template<typename I>
UVW_INLINE Addr TCPHandle::sock() const noexcept { UVW_INLINE Addr TCPHandle::sock() const noexcept {
return details::address<I>(&uv_tcp_getsockname, get()); return details::address<I>(&uv_tcp_getsockname, get());
} }
template<typename I> template<typename I>
UVW_INLINE Addr TCPHandle::peer() const noexcept { UVW_INLINE Addr TCPHandle::peer() const noexcept {
return details::address<I>(&uv_tcp_getpeername, get()); return details::address<I>(&uv_tcp_getpeername, get());
} }
template<typename I> template<typename I>
UVW_INLINE void TCPHandle::connect(const std::string &ip, unsigned int port) { UVW_INLINE void TCPHandle::connect(const std::string &ip, unsigned int port) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -77,13 +62,11 @@ UVW_INLINE void TCPHandle::connect(const std::string &ip, unsigned int port) {
connect(reinterpret_cast<const sockaddr &>(addr)); connect(reinterpret_cast<const sockaddr &>(addr));
} }
template<typename I> template<typename I>
UVW_INLINE void TCPHandle::connect(Addr addr) { UVW_INLINE void TCPHandle::connect(Addr addr) {
connect<I>(std::move(addr.ip), addr.port); connect<I>(std::move(addr.ip), addr.port);
} }
UVW_INLINE void TCPHandle::connect(const sockaddr &addr) { UVW_INLINE void TCPHandle::connect(const sockaddr &addr) {
auto listener = [ptr = shared_from_this()](const auto &event, const auto &) { auto listener = [ptr = shared_from_this()](const auto &event, const auto &) {
ptr->publish(event); ptr->publish(event);
@ -95,12 +78,10 @@ UVW_INLINE void TCPHandle::connect(const sockaddr &addr) {
req->connect(&uv_tcp_connect, get(), &addr); req->connect(&uv_tcp_connect, get(), &addr);
} }
UVW_INLINE void TCPHandle::closeReset() { UVW_INLINE void TCPHandle::closeReset() {
invoke(&uv_tcp_close_reset, get(), &this->closeCallback); invoke(&uv_tcp_close_reset, get(), &this->closeCallback);
} }
// explicit instantiations // explicit instantiations
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
template void TCPHandle::bind<IPv4>(const std::string &, unsigned int, Flags<Bind>); template void TCPHandle::bind<IPv4>(const std::string &, unsigned int, Flags<Bind>);
@ -122,5 +103,4 @@ template void TCPHandle::connect<IPv4>(Addr addr);
template void TCPHandle::connect<IPv6>(Addr addr); template void TCPHandle::connect<IPv6>(Addr addr);
#endif // UVW_AS_LIB #endif // UVW_AS_LIB
} // namespace uvw
}

View File

@ -1,32 +1,26 @@
#ifndef UVW_TCP_INCLUDE_H #ifndef UVW_TCP_INCLUDE_H
#define UVW_TCP_INCLUDE_H #define UVW_TCP_INCLUDE_H
#include <chrono>
#include <type_traits>
#include <utility>
#include <memory> #include <memory>
#include <string> #include <string>
#include <chrono> #include <type_traits>
#include <utility>
#include <uv.h> #include <uv.h>
#include "request.hpp" #include "request.hpp"
#include "stream.h" #include "stream.h"
#include "util.h" #include "util.h"
namespace uvw { namespace uvw {
namespace details { namespace details {
enum class UVTCPFlags : std::underlying_type_t<uv_tcp_flags> {
enum class UVTCPFlags: std::underlying_type_t<uv_tcp_flags> {
IPV6ONLY = UV_TCP_IPV6ONLY IPV6ONLY = UV_TCP_IPV6ONLY
}; };
} }
/** /**
* @brief The TCPHandle handle. * @brief The TCPHandle handle.
* *
@ -225,17 +219,19 @@ public:
void closeReset(); void closeReset();
private: private:
enum { DEFAULT, FLAGS } tag; enum {
DEFAULT,
FLAGS
} tag;
unsigned int flags; unsigned int flags;
}; };
/** /**
* @cond TURN_OFF_DOXYGEN * @cond TURN_OFF_DOXYGEN
* Internal details not to be documented. * Internal details not to be documented.
*/ */
// (extern) explicit instantiations // (extern) explicit instantiations
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
extern template void TCPHandle::bind<IPv4>(const std::string &, unsigned int, Flags<Bind>); extern template void TCPHandle::bind<IPv4>(const std::string &, unsigned int, Flags<Bind>);
@ -257,19 +253,15 @@ extern template void TCPHandle::connect<IPv4>(Addr addr);
extern template void TCPHandle::connect<IPv6>(Addr addr); extern template void TCPHandle::connect<IPv6>(Addr addr);
#endif // UVW_AS_LIB #endif // UVW_AS_LIB
/** /**
* Internal details not to be documented. * Internal details not to be documented.
* @endcond * @endcond
*/ */
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "tcp.cpp" # include "tcp.cpp"
#endif #endif
#endif // UVW_TCP_INCLUDE_H #endif // UVW_TCP_INCLUDE_H

View File

@ -1,76 +1,60 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "thread.h" # include "thread.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE Thread::Thread(ConstructorAccess ca, std::shared_ptr<Loop> ref, Task t, std::shared_ptr<void> d) noexcept UVW_INLINE Thread::Thread(ConstructorAccess ca, std::shared_ptr<Loop> ref, Task t, std::shared_ptr<void> d) noexcept
: UnderlyingType{ca, std::move(ref)}, data{std::move(d)}, task{std::move(t)} : UnderlyingType{ca, std::move(ref)}, data{std::move(d)}, task{std::move(t)} {}
{}
UVW_INLINE void Thread::createCallback(void *arg) { UVW_INLINE void Thread::createCallback(void *arg) {
Thread &thread = *(static_cast<Thread *>(arg)); Thread &thread = *(static_cast<Thread *>(arg));
thread.task(thread.data); thread.task(thread.data);
} }
UVW_INLINE Thread::Type Thread::self() noexcept { UVW_INLINE Thread::Type Thread::self() noexcept {
return uv_thread_self(); return uv_thread_self();
} }
UVW_INLINE bool Thread::equal(const Thread &tl, const Thread &tr) noexcept { UVW_INLINE bool Thread::equal(const Thread &tl, const Thread &tr) noexcept {
return !(0 == uv_thread_equal(tl.get(), tr.get())); return !(0 == uv_thread_equal(tl.get(), tr.get()));
} }
UVW_INLINE Thread::~Thread() noexcept { UVW_INLINE Thread::~Thread() noexcept {
join(); join();
} }
UVW_INLINE bool Thread::run() noexcept { UVW_INLINE bool Thread::run() noexcept {
return (0 == uv_thread_create(get(), &createCallback, this)); return (0 == uv_thread_create(get(), &createCallback, this));
} }
UVW_INLINE bool Thread::run(Flags<Options> opts, std::size_t stack) noexcept { UVW_INLINE bool Thread::run(Flags<Options> opts, std::size_t stack) noexcept {
uv_thread_options_t params{static_cast<unsigned int>(opts), stack}; uv_thread_options_t params{static_cast<unsigned int>(opts), stack};
return (0 == uv_thread_create_ex(get(), &params, &createCallback, this)); return (0 == uv_thread_create_ex(get(), &params, &createCallback, this));
} }
UVW_INLINE bool Thread::join() noexcept { UVW_INLINE bool Thread::join() noexcept {
return (0 == uv_thread_join(get())); return (0 == uv_thread_join(get()));
} }
UVW_INLINE ThreadLocalStorage::ThreadLocalStorage(UnderlyingType<ThreadLocalStorage, uv_key_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref) noexcept UVW_INLINE ThreadLocalStorage::ThreadLocalStorage(UnderlyingType<ThreadLocalStorage, uv_key_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref) noexcept
:UnderlyingType{ca, std::move(ref)} : UnderlyingType{ca, std::move(ref)} {
{
uv_key_create(UnderlyingType::get()); uv_key_create(UnderlyingType::get());
} }
UVW_INLINE ThreadLocalStorage::~ThreadLocalStorage() noexcept { UVW_INLINE ThreadLocalStorage::~ThreadLocalStorage() noexcept {
uv_key_delete(UnderlyingType::get()); uv_key_delete(UnderlyingType::get());
} }
UVW_INLINE uv_once_t *Once::guard() noexcept { UVW_INLINE uv_once_t *Once::guard() noexcept {
static uv_once_t once = UV_ONCE_INIT; static uv_once_t once = UV_ONCE_INIT;
return &once; return &once;
} }
UVW_INLINE Mutex::Mutex(UnderlyingType<Mutex, uv_mutex_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref, bool recursive) noexcept UVW_INLINE Mutex::Mutex(UnderlyingType<Mutex, uv_mutex_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref, bool recursive) noexcept
: UnderlyingType{ca, std::move(ref)} : UnderlyingType{ca, std::move(ref)} {
{
if(recursive) { if(recursive) {
uv_mutex_init_recursive(get()); uv_mutex_init_recursive(get());
} else { } else {
@ -78,143 +62,112 @@ UVW_INLINE Mutex::Mutex(UnderlyingType<Mutex, uv_mutex_t>::ConstructorAccess ca,
} }
} }
UVW_INLINE Mutex::~Mutex() noexcept { UVW_INLINE Mutex::~Mutex() noexcept {
uv_mutex_destroy(get()); uv_mutex_destroy(get());
} }
UVW_INLINE void Mutex::lock() noexcept { UVW_INLINE void Mutex::lock() noexcept {
uv_mutex_lock(get()); uv_mutex_lock(get());
} }
UVW_INLINE bool Mutex::tryLock() noexcept { UVW_INLINE bool Mutex::tryLock() noexcept {
return (0 == uv_mutex_trylock(get())); return (0 == uv_mutex_trylock(get()));
} }
UVW_INLINE void Mutex::unlock() noexcept { UVW_INLINE void Mutex::unlock() noexcept {
uv_mutex_unlock(get()); uv_mutex_unlock(get());
} }
UVW_INLINE RWLock::RWLock(UnderlyingType<RWLock, uv_rwlock_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref) noexcept UVW_INLINE RWLock::RWLock(UnderlyingType<RWLock, uv_rwlock_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref) noexcept
: UnderlyingType{ca, std::move(ref)} : UnderlyingType{ca, std::move(ref)} {
{
uv_rwlock_init(get()); uv_rwlock_init(get());
} }
UVW_INLINE RWLock::~RWLock() noexcept { UVW_INLINE RWLock::~RWLock() noexcept {
uv_rwlock_destroy(get()); uv_rwlock_destroy(get());
} }
UVW_INLINE void RWLock::rdLock() noexcept { UVW_INLINE void RWLock::rdLock() noexcept {
uv_rwlock_rdlock(get()); uv_rwlock_rdlock(get());
} }
UVW_INLINE bool RWLock::tryRdLock() noexcept { UVW_INLINE bool RWLock::tryRdLock() noexcept {
return (0 == uv_rwlock_tryrdlock(get())); return (0 == uv_rwlock_tryrdlock(get()));
} }
UVW_INLINE void RWLock::rdUnlock() noexcept { UVW_INLINE void RWLock::rdUnlock() noexcept {
uv_rwlock_rdunlock(get()); uv_rwlock_rdunlock(get());
} }
UVW_INLINE void RWLock::wrLock() noexcept { UVW_INLINE void RWLock::wrLock() noexcept {
uv_rwlock_wrlock(get()); uv_rwlock_wrlock(get());
} }
UVW_INLINE bool RWLock::tryWrLock() noexcept { UVW_INLINE bool RWLock::tryWrLock() noexcept {
return (0 == uv_rwlock_trywrlock(get())); return (0 == uv_rwlock_trywrlock(get()));
} }
UVW_INLINE void RWLock::wrUnlock() noexcept { UVW_INLINE void RWLock::wrUnlock() noexcept {
uv_rwlock_wrunlock(get()); uv_rwlock_wrunlock(get());
} }
UVW_INLINE Semaphore::Semaphore(UnderlyingType<Semaphore, uv_sem_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref, unsigned int value) noexcept UVW_INLINE Semaphore::Semaphore(UnderlyingType<Semaphore, uv_sem_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref, unsigned int value) noexcept
: UnderlyingType{ca, std::move(ref)} : UnderlyingType{ca, std::move(ref)} {
{
uv_sem_init(get(), value); uv_sem_init(get(), value);
} }
UVW_INLINE Semaphore::~Semaphore() noexcept { UVW_INLINE Semaphore::~Semaphore() noexcept {
uv_sem_destroy(get()); uv_sem_destroy(get());
} }
UVW_INLINE void Semaphore::post() noexcept { UVW_INLINE void Semaphore::post() noexcept {
uv_sem_post(get()); uv_sem_post(get());
} }
UVW_INLINE void Semaphore::wait() noexcept { UVW_INLINE void Semaphore::wait() noexcept {
uv_sem_wait(get()); uv_sem_wait(get());
} }
UVW_INLINE bool Semaphore::tryWait() noexcept { UVW_INLINE bool Semaphore::tryWait() noexcept {
return (0 == uv_sem_trywait(get())); return (0 == uv_sem_trywait(get()));
} }
UVW_INLINE Condition::Condition(UnderlyingType<Condition, uv_cond_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref) noexcept UVW_INLINE Condition::Condition(UnderlyingType<Condition, uv_cond_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref) noexcept
: UnderlyingType{ca, std::move(ref)} : UnderlyingType{ca, std::move(ref)} {
{
uv_cond_init(get()); uv_cond_init(get());
} }
UVW_INLINE Condition::~Condition() noexcept { UVW_INLINE Condition::~Condition() noexcept {
uv_cond_destroy(get()); uv_cond_destroy(get());
} }
UVW_INLINE void Condition::signal() noexcept { UVW_INLINE void Condition::signal() noexcept {
uv_cond_signal(get()); uv_cond_signal(get());
} }
UVW_INLINE void Condition::broadcast() noexcept { UVW_INLINE void Condition::broadcast() noexcept {
uv_cond_broadcast(get()); uv_cond_broadcast(get());
} }
UVW_INLINE void Condition::wait(Mutex &mutex) noexcept { UVW_INLINE void Condition::wait(Mutex &mutex) noexcept {
uv_cond_wait(get(), mutex.get()); uv_cond_wait(get(), mutex.get());
} }
UVW_INLINE bool Condition::timedWait(Mutex &mutex, uint64_t timeout) noexcept { UVW_INLINE bool Condition::timedWait(Mutex &mutex, uint64_t timeout) noexcept {
return (0 == uv_cond_timedwait(get(), mutex.get(), timeout)); return (0 == uv_cond_timedwait(get(), mutex.get(), timeout));
} }
UVW_INLINE Barrier::Barrier(UnderlyingType<Barrier, uv_barrier_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref, unsigned int count) noexcept UVW_INLINE Barrier::Barrier(UnderlyingType<Barrier, uv_barrier_t>::ConstructorAccess ca, std::shared_ptr<Loop> ref, unsigned int count) noexcept
: UnderlyingType{ca, std::move(ref)} : UnderlyingType{ca, std::move(ref)} {
{
uv_barrier_init(get(), count); uv_barrier_init(get(), count);
} }
UVW_INLINE Barrier::~Barrier() noexcept { UVW_INLINE Barrier::~Barrier() noexcept {
uv_barrier_destroy(get()); uv_barrier_destroy(get());
} }
UVW_INLINE bool Barrier::wait() noexcept { UVW_INLINE bool Barrier::wait() noexcept {
return (0 == uv_barrier_wait(get())); return (0 == uv_barrier_wait(get()));
} }
} // namespace uvw
}

View File

@ -1,32 +1,26 @@
#ifndef UVW_THREAD_INCLUDE_H #ifndef UVW_THREAD_INCLUDE_H
#define UVW_THREAD_INCLUDE_H #define UVW_THREAD_INCLUDE_H
#include <cstddef>
#include <memory> #include <memory>
#include <string> #include <string>
#include <cstddef>
#include <type_traits> #include <type_traits>
#include <utility> #include <utility>
#include <uv.h> #include <uv.h>
#include "loop.h" #include "loop.h"
#include "underlying_type.hpp" #include "underlying_type.hpp"
namespace uvw { namespace uvw {
namespace details { namespace details {
enum class UVThreadCreateFlags : std::underlying_type_t<uv_thread_create_flags> {
enum class UVThreadCreateFlags: std::underlying_type_t<uv_thread_create_flags> {
THREAD_NO_FLAGS = UV_THREAD_NO_FLAGS, THREAD_NO_FLAGS = UV_THREAD_NO_FLAGS,
THREAD_HAS_STACK_SIZE = UV_THREAD_HAS_STACK_SIZE THREAD_HAS_STACK_SIZE = UV_THREAD_HAS_STACK_SIZE
}; };
} }
class Thread; class Thread;
class ThreadLocalStorage; class ThreadLocalStorage;
class Once; class Once;
@ -36,7 +30,6 @@ class Semaphore;
class Condition; class Condition;
class Barrier; class Barrier;
/** /**
* @brief The Thread wrapper. * @brief The Thread wrapper.
* *
@ -106,7 +99,6 @@ private:
Task task; Task task;
}; };
/** /**
* @brief The ThreadLocalStorage wrapper. * @brief The ThreadLocalStorage wrapper.
* *
@ -126,8 +118,8 @@ public:
* @return A pointer to the given variable. * @return A pointer to the given variable.
*/ */
template<typename T> template<typename T>
T* get() noexcept { T *get() noexcept {
return static_cast<T*>(uv_key_get(UnderlyingType::get())); return static_cast<T *>(uv_key_get(UnderlyingType::get()));
} }
/** /**
@ -141,7 +133,6 @@ public:
} }
}; };
/** /**
* @brief The Once wrapper. * @brief The Once wrapper.
* *
@ -149,7 +140,7 @@ public:
* callers except one (its unspecified which one). * callers except one (its unspecified which one).
*/ */
class Once final: public UnderlyingType<Once, uv_once_t> { class Once final: public UnderlyingType<Once, uv_once_t> {
static uv_once_t* guard() noexcept; static uv_once_t *guard() noexcept;
public: public:
using UnderlyingType::UnderlyingType; using UnderlyingType::UnderlyingType;
@ -165,14 +156,13 @@ public:
*/ */
template<typename F> template<typename F>
static void once(F &&f) noexcept { static void once(F &&f) noexcept {
using CallbackType = void(*)(void); using CallbackType = void (*)(void);
static_assert(std::is_convertible_v<F, CallbackType>); static_assert(std::is_convertible_v<F, CallbackType>);
CallbackType cb = f; CallbackType cb = f;
uv_once(guard(), cb); uv_once(guard(), cb);
} }
}; };
/** /**
* @brief The Mutex wrapper. * @brief The Mutex wrapper.
* *
@ -206,7 +196,6 @@ public:
void unlock() noexcept; void unlock() noexcept;
}; };
/** /**
* @brief The RWLock wrapper. * @brief The RWLock wrapper.
*/ */
@ -249,7 +238,6 @@ public:
void wrUnlock() noexcept; void wrUnlock() noexcept;
}; };
/** /**
* @brief The Semaphore wrapper. * @brief The Semaphore wrapper.
* *
@ -280,7 +268,6 @@ public:
bool tryWait() noexcept; bool tryWait() noexcept;
}; };
/** /**
* @brief The Condition wrapper. * @brief The Condition wrapper.
*/ */
@ -334,7 +321,6 @@ public:
bool timedWait(Mutex &mutex, uint64_t timeout) noexcept; bool timedWait(Mutex &mutex, uint64_t timeout) noexcept;
}; };
/** /**
* @brief The Barrier wrapper. * @brief The Barrier wrapper.
* *
@ -357,12 +343,10 @@ public:
bool wait() noexcept; bool wait() noexcept;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "thread.cpp" # include "thread.cpp"
#endif #endif
#endif // UVW_THREAD_INCLUDE_H #endif // UVW_THREAD_INCLUDE_H

View File

@ -1,52 +1,42 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "timer.h" # include "timer.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE void TimerHandle::startCallback(uv_timer_t *handle) { UVW_INLINE void TimerHandle::startCallback(uv_timer_t *handle) {
TimerHandle &timer = *(static_cast<TimerHandle *>(handle->data)); TimerHandle &timer = *(static_cast<TimerHandle *>(handle->data));
timer.publish(TimerEvent{}); timer.publish(TimerEvent{});
} }
UVW_INLINE bool TimerHandle::init() { UVW_INLINE bool TimerHandle::init() {
return initialize(&uv_timer_init); return initialize(&uv_timer_init);
} }
UVW_INLINE void TimerHandle::start(TimerHandle::Time timeout, TimerHandle::Time repeat) { UVW_INLINE void TimerHandle::start(TimerHandle::Time timeout, TimerHandle::Time repeat) {
invoke(&uv_timer_start, get(), &startCallback, timeout.count(), repeat.count()); invoke(&uv_timer_start, get(), &startCallback, timeout.count(), repeat.count());
} }
UVW_INLINE void TimerHandle::stop() { UVW_INLINE void TimerHandle::stop() {
invoke(&uv_timer_stop, get()); invoke(&uv_timer_stop, get());
} }
UVW_INLINE void TimerHandle::again() { UVW_INLINE void TimerHandle::again() {
invoke(&uv_timer_again, get()); invoke(&uv_timer_again, get());
} }
UVW_INLINE void TimerHandle::repeat(TimerHandle::Time repeat) { UVW_INLINE void TimerHandle::repeat(TimerHandle::Time repeat) {
uv_timer_set_repeat(get(), repeat.count()); uv_timer_set_repeat(get(), repeat.count());
} }
UVW_INLINE TimerHandle::Time TimerHandle::repeat() { UVW_INLINE TimerHandle::Time TimerHandle::repeat() {
return Time{uv_timer_get_repeat(get())}; return Time{uv_timer_get_repeat(get())};
} }
UVW_INLINE TimerHandle::Time TimerHandle::dueIn() { UVW_INLINE TimerHandle::Time TimerHandle::dueIn() {
return Time{uv_timer_get_due_in(get())}; return Time{uv_timer_get_due_in(get())};
} }
} // namespace uvw
}

View File

@ -1,16 +1,13 @@
#ifndef UVW_TIMER_INCLUDE_H #ifndef UVW_TIMER_INCLUDE_H
#define UVW_TIMER_INCLUDE_H #define UVW_TIMER_INCLUDE_H
#include <chrono> #include <chrono>
#include <uv.h> #include <uv.h>
#include "handle.hpp" #include "handle.hpp"
#include "loop.h" #include "loop.h"
namespace uvw { namespace uvw {
/** /**
* @brief TimerEvent event. * @brief TimerEvent event.
* *
@ -18,7 +15,6 @@ namespace uvw {
*/ */
struct TimerEvent {}; struct TimerEvent {};
/** /**
* @brief The TimerHandle handle. * @brief The TimerHandle handle.
* *
@ -97,20 +93,18 @@ public:
/** /**
* @brief Gets the timer due value. * @brief Gets the timer due value.
* *
* The time is relative to `Loop::now()`. * The time is relative to `Loop::now()`.
* *
* @return The timer due value or 0 if it has expired. * @return The timer due value or 0 if it has expired.
*/ */
Time dueIn(); Time dueIn();
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "timer.cpp" # include "timer.cpp"
#endif #endif
#endif // UVW_TIMER_INCLUDE_H #endif // UVW_TIMER_INCLUDE_H

View File

@ -1,27 +1,22 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "tty.h" # include "tty.h"
#endif #endif
#include <utility> #include <utility>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE details::ResetModeMemo::~ResetModeMemo() { UVW_INLINE details::ResetModeMemo::~ResetModeMemo() {
uv_tty_reset_mode(); uv_tty_reset_mode();
} }
UVW_INLINE TTYHandle::TTYHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, FileHandle desc, bool readable) UVW_INLINE TTYHandle::TTYHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, FileHandle desc, bool readable)
: StreamHandle{ca, std::move(ref)}, : StreamHandle{ca, std::move(ref)},
memo{resetModeMemo()}, memo{resetModeMemo()},
fd{desc}, fd{desc},
rw{readable} rw{readable} {}
{}
UVW_INLINE std::shared_ptr<details::ResetModeMemo> TTYHandle::resetModeMemo() { UVW_INLINE std::shared_ptr<details::ResetModeMemo> TTYHandle::resetModeMemo() {
static std::weak_ptr<details::ResetModeMemo> weak; static std::weak_ptr<details::ResetModeMemo> weak;
@ -30,22 +25,18 @@ UVW_INLINE std::shared_ptr<details::ResetModeMemo> TTYHandle::resetModeMemo() {
return shared; return shared;
}; };
UVW_INLINE bool TTYHandle::init() { UVW_INLINE bool TTYHandle::init() {
return initialize(&uv_tty_init, fd, rw); return initialize(&uv_tty_init, fd, rw);
} }
UVW_INLINE bool TTYHandle::mode(TTYHandle::Mode m) { UVW_INLINE bool TTYHandle::mode(TTYHandle::Mode m) {
return (0 == uv_tty_set_mode(get(), static_cast<std::underlying_type_t<Mode>>(m))); return (0 == uv_tty_set_mode(get(), static_cast<std::underlying_type_t<Mode>>(m)));
} }
UVW_INLINE bool TTYHandle::reset() noexcept { UVW_INLINE bool TTYHandle::reset() noexcept {
return (0 == uv_tty_reset_mode()); return (0 == uv_tty_reset_mode());
} }
UVW_INLINE WinSize TTYHandle::getWinSize() { UVW_INLINE WinSize TTYHandle::getWinSize() {
WinSize size; WinSize size;
@ -57,24 +48,21 @@ UVW_INLINE WinSize TTYHandle::getWinSize() {
return size; return size;
} }
UVW_INLINE void TTYHandle::vtermState(TTYHandle::VTermState s) const noexcept { UVW_INLINE void TTYHandle::vtermState(TTYHandle::VTermState s) const noexcept {
switch(s) { switch(s) {
case VTermState::SUPPORTED: case VTermState::SUPPORTED:
uv_tty_set_vterm_state(uv_tty_vtermstate_t::UV_TTY_SUPPORTED); uv_tty_set_vterm_state(uv_tty_vtermstate_t::UV_TTY_SUPPORTED);
break; break;
case VTermState::UNSUPPORTED: case VTermState::UNSUPPORTED:
uv_tty_set_vterm_state(uv_tty_vtermstate_t::UV_TTY_UNSUPPORTED); uv_tty_set_vterm_state(uv_tty_vtermstate_t::UV_TTY_UNSUPPORTED);
break; break;
} }
} }
UVW_INLINE TTYHandle::VTermState TTYHandle::vtermState() const noexcept { UVW_INLINE TTYHandle::VTermState TTYHandle::vtermState() const noexcept {
uv_tty_vtermstate_t state; uv_tty_vtermstate_t state;
uv_tty_get_vterm_state(&state); uv_tty_get_vterm_state(&state);
return VTermState{state}; return VTermState{state};
} }
} // namespace uvw
}

View File

@ -1,40 +1,32 @@
#ifndef UVW_TTY_INCLUDE_H #ifndef UVW_TTY_INCLUDE_H
#define UVW_TTY_INCLUDE_H #define UVW_TTY_INCLUDE_H
#include <type_traits>
#include <memory> #include <memory>
#include <type_traits>
#include <uv.h> #include <uv.h>
#include "stream.h" #include "stream.h"
#include "util.h" #include "util.h"
namespace uvw { namespace uvw {
namespace details { namespace details {
struct ResetModeMemo { struct ResetModeMemo {
~ResetModeMemo(); ~ResetModeMemo();
}; };
enum class UVTTYModeT : std::underlying_type_t<uv_tty_mode_t> {
enum class UVTTYModeT: std::underlying_type_t<uv_tty_mode_t> {
NORMAL = UV_TTY_MODE_NORMAL, NORMAL = UV_TTY_MODE_NORMAL,
RAW = UV_TTY_MODE_RAW, RAW = UV_TTY_MODE_RAW,
IO = UV_TTY_MODE_IO IO = UV_TTY_MODE_IO
}; };
enum class UVTTYVTermStateT : std::underlying_type_t<uv_tty_vtermstate_t> {
enum class UVTTYVTermStateT: std::underlying_type_t<uv_tty_vtermstate_t> {
SUPPORTED = UV_TTY_SUPPORTED, SUPPORTED = UV_TTY_SUPPORTED,
UNSUPPORTED = UV_TTY_UNSUPPORTED UNSUPPORTED = UV_TTY_UNSUPPORTED
}; };
} // namespace details
}
/** /**
* @brief The TTYHandle handle. * @brief The TTYHandle handle.
@ -144,12 +136,10 @@ private:
int rw; int rw;
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "tty.cpp" # include "tty.cpp"
#endif #endif
#endif // UVW_TTY_INCLUDE_H #endif // UVW_TTY_INCLUDE_H

View File

@ -1,23 +1,18 @@
#ifndef UVW_TYPE_INFO_INCLUDE_HPP #ifndef UVW_TYPE_INFO_INCLUDE_HPP
#define UVW_TYPE_INFO_INCLUDE_HPP #define UVW_TYPE_INFO_INCLUDE_HPP
#include <cstddef> #include <cstddef>
#include <string_view> #include <string_view>
namespace uvw { namespace uvw {
/** /**
* @cond TURN_OFF_DOXYGEN * @cond TURN_OFF_DOXYGEN
* Internal details not to be documented. * Internal details not to be documented.
*/ */
namespace internal { namespace internal {
// Fowler-Noll-Vo hash function v. 1a - the good // Fowler-Noll-Vo hash function v. 1a - the good
[[nodiscard]] static constexpr std::uint32_t fnv1a(const char *curr) noexcept { [[nodiscard]] static constexpr std::uint32_t fnv1a(const char *curr) noexcept {
constexpr std::uint32_t offset = 2166136261; constexpr std::uint32_t offset = 2166136261;
@ -31,29 +26,24 @@ namespace internal {
return value; return value;
} }
[[nodiscard]] static inline std::uint32_t counter() noexcept { [[nodiscard]] static inline std::uint32_t counter() noexcept {
static std::uint32_t cnt{}; static std::uint32_t cnt{};
return cnt++; return cnt++;
} }
template<typename Type> template<typename Type>
[[nodiscard]] static std::uint32_t fake() noexcept { [[nodiscard]] static std::uint32_t fake() noexcept {
static std::uint32_t local = counter(); static std::uint32_t local = counter();
return local; return local;
} }
} // namespace internal
}
/** /**
* Internal details not to be documented. * Internal details not to be documented.
* @endcond * @endcond
*/ */
/** /**
* @brief Returns a numerical identifier for a given type. * @brief Returns a numerical identifier for a given type.
* @tparam Type The type for which to return the numerical identifier. * @tparam Type The type for which to return the numerical identifier.
@ -70,7 +60,6 @@ template<typename Type>
#endif #endif
} }
} // namespace uvw
}
#endif // UVW_TYPE_INFO_INCLUDE_HPP #endif // UVW_TYPE_INFO_INCLUDE_HPP

View File

@ -1,55 +1,42 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "udp.h" # include "udp.h"
#endif #endif
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE UDPDataEvent::UDPDataEvent(Addr sndr, std::unique_ptr<char[]> buf, std::size_t len, bool part) noexcept UVW_INLINE UDPDataEvent::UDPDataEvent(Addr sndr, std::unique_ptr<char[]> buf, std::size_t len, bool part) noexcept
: data{std::move(buf)}, length{len}, sender{std::move(sndr)}, partial{part} : data{std::move(buf)}, length{len}, sender{std::move(sndr)}, partial{part} {}
{}
UVW_INLINE details::SendReq::SendReq(ConstructorAccess ca, std::shared_ptr<Loop> loop, std::unique_ptr<char[], Deleter> dt, unsigned int len) UVW_INLINE details::SendReq::SendReq(ConstructorAccess ca, std::shared_ptr<Loop> loop, std::unique_ptr<char[], Deleter> dt, unsigned int len)
: Request<SendReq, uv_udp_send_t>{ca, std::move(loop)}, : Request<SendReq, uv_udp_send_t>{ca, std::move(loop)},
data{std::move(dt)}, data{std::move(dt)},
buf{uv_buf_init(data.get(), len)} buf{uv_buf_init(data.get(), len)} {}
{}
UVW_INLINE void details::SendReq::send(uv_udp_t *handle, const struct sockaddr *addr) { UVW_INLINE void details::SendReq::send(uv_udp_t *handle, const struct sockaddr *addr) {
invoke(&uv_udp_send, get(), handle, &buf, 1, addr, &defaultCallback<SendEvent>); invoke(&uv_udp_send, get(), handle, &buf, 1, addr, &defaultCallback<SendEvent>);
} }
UVW_INLINE UDPHandle::UDPHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, unsigned int f) UVW_INLINE UDPHandle::UDPHandle(ConstructorAccess ca, std::shared_ptr<Loop> ref, unsigned int f)
: Handle{ca, std::move(ref)}, tag{FLAGS}, flags{f} : Handle{ca, std::move(ref)}, tag{FLAGS}, flags{f} {}
{}
UVW_INLINE bool UDPHandle::init() { UVW_INLINE bool UDPHandle::init() {
return (tag == FLAGS) ? initialize(&uv_udp_init_ex, flags) : initialize(&uv_udp_init); return (tag == FLAGS) ? initialize(&uv_udp_init_ex, flags) : initialize(&uv_udp_init);
} }
UVW_INLINE void UDPHandle::open(OSSocketHandle socket) { UVW_INLINE void UDPHandle::open(OSSocketHandle socket) {
invoke(&uv_udp_open, get(), socket); invoke(&uv_udp_open, get(), socket);
} }
UVW_INLINE void UDPHandle::bind(const sockaddr &addr, Flags<UDPHandle::Bind> opts) { UVW_INLINE void UDPHandle::bind(const sockaddr &addr, Flags<UDPHandle::Bind> opts) {
invoke(&uv_udp_bind, get(), &addr, opts); invoke(&uv_udp_bind, get(), &addr, opts);
} }
UVW_INLINE void UDPHandle::connect(const sockaddr &addr) { UVW_INLINE void UDPHandle::connect(const sockaddr &addr) {
invoke(&uv_udp_connect, get(), &addr); invoke(&uv_udp_connect, get(), &addr);
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::connect(const std::string &ip, unsigned int port) { UVW_INLINE void UDPHandle::connect(const std::string &ip, unsigned int port) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -57,24 +44,20 @@ UVW_INLINE void UDPHandle::connect(const std::string &ip, unsigned int port) {
connect(reinterpret_cast<const sockaddr &>(addr)); connect(reinterpret_cast<const sockaddr &>(addr));
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::connect(Addr addr) { UVW_INLINE void UDPHandle::connect(Addr addr) {
connect<I>(std::move(addr.ip), addr.port); connect<I>(std::move(addr.ip), addr.port);
} }
UVW_INLINE void UDPHandle::disconnect() { UVW_INLINE void UDPHandle::disconnect() {
invoke(&uv_udp_connect, get(), nullptr); invoke(&uv_udp_connect, get(), nullptr);
} }
template<typename I> template<typename I>
UVW_INLINE Addr UDPHandle::peer() const noexcept { UVW_INLINE Addr UDPHandle::peer() const noexcept {
return details::address<I>(&uv_udp_getpeername, get()); return details::address<I>(&uv_udp_getpeername, get());
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::bind(const std::string &ip, unsigned int port, Flags<Bind> opts) { UVW_INLINE void UDPHandle::bind(const std::string &ip, unsigned int port, Flags<Bind> opts) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -82,56 +65,44 @@ UVW_INLINE void UDPHandle::bind(const std::string &ip, unsigned int port, Flags<
bind(reinterpret_cast<const sockaddr &>(addr), std::move(opts)); bind(reinterpret_cast<const sockaddr &>(addr), std::move(opts));
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::bind(Addr addr, Flags<Bind> opts) { UVW_INLINE void UDPHandle::bind(Addr addr, Flags<Bind> opts) {
bind<I>(std::move(addr.ip), addr.port, std::move(opts)); bind<I>(std::move(addr.ip), addr.port, std::move(opts));
} }
template<typename I> template<typename I>
UVW_INLINE Addr UDPHandle::sock() const noexcept { UVW_INLINE Addr UDPHandle::sock() const noexcept {
return details::address<I>(&uv_udp_getsockname, get()); return details::address<I>(&uv_udp_getsockname, get());
} }
template<typename I> template<typename I>
UVW_INLINE bool UDPHandle::multicastMembership(const std::string &multicast, const std::string &iface, Membership membership) { UVW_INLINE bool UDPHandle::multicastMembership(const std::string &multicast, const std::string &iface, Membership membership) {
return (0 == uv_udp_set_membership(get(), multicast.data(), iface.data(), static_cast<uv_membership>(membership))); return (0 == uv_udp_set_membership(get(), multicast.data(), iface.data(), static_cast<uv_membership>(membership)));
} }
UVW_INLINE bool UDPHandle::multicastLoop(bool enable) { UVW_INLINE bool UDPHandle::multicastLoop(bool enable) {
return (0 == uv_udp_set_multicast_loop(get(), enable)); return (0 == uv_udp_set_multicast_loop(get(), enable));
} }
UVW_INLINE bool UDPHandle::multicastTtl(int val) { UVW_INLINE bool UDPHandle::multicastTtl(int val) {
return (0 == uv_udp_set_multicast_ttl(get(), val > 255 ? 255 : val)); return (0 == uv_udp_set_multicast_ttl(get(), val > 255 ? 255 : val));
} }
template<typename I> template<typename I>
UVW_INLINE bool UDPHandle::multicastInterface(const std::string &iface) { UVW_INLINE bool UDPHandle::multicastInterface(const std::string &iface) {
return (0 == uv_udp_set_multicast_interface(get(), iface.data())); return (0 == uv_udp_set_multicast_interface(get(), iface.data()));
} }
UVW_INLINE bool UDPHandle::broadcast(bool enable) { UVW_INLINE bool UDPHandle::broadcast(bool enable) {
return (0 == uv_udp_set_broadcast(get(), enable)); return (0 == uv_udp_set_broadcast(get(), enable));
} }
UVW_INLINE bool UDPHandle::ttl(int val) { UVW_INLINE bool UDPHandle::ttl(int val) {
return (0 == uv_udp_set_ttl(get(), val > 255 ? 255 : val)); return (0 == uv_udp_set_ttl(get(), val > 255 ? 255 : val));
} }
UVW_INLINE void UDPHandle::send(const sockaddr &addr, std::unique_ptr<char[]> data, unsigned int len) { UVW_INLINE void UDPHandle::send(const sockaddr &addr, std::unique_ptr<char[]> data, unsigned int len) {
auto req = loop().resource<details::SendReq>( auto req = loop().resource<details::SendReq>(std::unique_ptr<char[], details::SendReq::Deleter>{data.release(), [](char *ptr) { delete[] ptr; }}, len);
std::unique_ptr<char[], details::SendReq::Deleter>{data.release(), [](char *ptr) {
delete[] ptr;
}}, len);
auto listener = [ptr = shared_from_this()](const auto &event, const auto &) { auto listener = [ptr = shared_from_this()](const auto &event, const auto &) {
ptr->publish(event); ptr->publish(event);
@ -142,7 +113,6 @@ UVW_INLINE void UDPHandle::send(const sockaddr &addr, std::unique_ptr<char[]> da
req->send(get(), &addr); req->send(get(), &addr);
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::send(const std::string &ip, unsigned int port, std::unique_ptr<char[]> data, unsigned int len) { UVW_INLINE void UDPHandle::send(const std::string &ip, unsigned int port, std::unique_ptr<char[]> data, unsigned int len) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -150,17 +120,13 @@ UVW_INLINE void UDPHandle::send(const std::string &ip, unsigned int port, std::u
send(reinterpret_cast<const sockaddr &>(addr), std::move(data), len); send(reinterpret_cast<const sockaddr &>(addr), std::move(data), len);
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::send(Addr addr, std::unique_ptr<char[]> data, unsigned int len) { UVW_INLINE void UDPHandle::send(Addr addr, std::unique_ptr<char[]> data, unsigned int len) {
send<I>(std::move(addr.ip), addr.port, std::move(data), len); send<I>(std::move(addr.ip), addr.port, std::move(data), len);
} }
UVW_INLINE void UDPHandle::send(const sockaddr &addr, char *data, unsigned int len) { UVW_INLINE void UDPHandle::send(const sockaddr &addr, char *data, unsigned int len) {
auto req = loop().resource<details::SendReq>( auto req = loop().resource<details::SendReq>(std::unique_ptr<char[], details::SendReq::Deleter>{data, [](char *) {}}, len);
std::unique_ptr<char[], details::SendReq::Deleter>{data, [](char *) {
}}, len);
auto listener = [ptr = shared_from_this()](const auto &event, const auto &) { auto listener = [ptr = shared_from_this()](const auto &event, const auto &) {
ptr->publish(event); ptr->publish(event);
@ -171,7 +137,6 @@ UVW_INLINE void UDPHandle::send(const sockaddr &addr, char *data, unsigned int l
req->send(get(), &addr); req->send(get(), &addr);
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::send(const std::string &ip, unsigned int port, char *data, unsigned int len) { UVW_INLINE void UDPHandle::send(const std::string &ip, unsigned int port, char *data, unsigned int len) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -179,16 +144,14 @@ UVW_INLINE void UDPHandle::send(const std::string &ip, unsigned int port, char *
send(reinterpret_cast<const sockaddr &>(addr), data, len); send(reinterpret_cast<const sockaddr &>(addr), data, len);
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::send(Addr addr, char *data, unsigned int len) { UVW_INLINE void UDPHandle::send(Addr addr, char *data, unsigned int len) {
send<I>(std::move(addr.ip), addr.port, data, len); send<I>(std::move(addr.ip), addr.port, data, len);
} }
template<typename I> template<typename I>
UVW_INLINE int UDPHandle::trySend(const sockaddr &addr, std::unique_ptr<char[]> data, unsigned int len) { UVW_INLINE int UDPHandle::trySend(const sockaddr &addr, std::unique_ptr<char[]> data, unsigned int len) {
uv_buf_t bufs[] = { uv_buf_init(data.get(), len) }; uv_buf_t bufs[] = {uv_buf_init(data.get(), len)};
auto bw = uv_udp_try_send(get(), bufs, 1, &addr); auto bw = uv_udp_try_send(get(), bufs, 1, &addr);
if(bw < 0) { if(bw < 0) {
@ -199,7 +162,6 @@ UVW_INLINE int UDPHandle::trySend(const sockaddr &addr, std::unique_ptr<char[]>
return bw; return bw;
} }
template<typename I> template<typename I>
UVW_INLINE int UDPHandle::trySend(const std::string &ip, unsigned int port, std::unique_ptr<char[]> data, unsigned int len) { UVW_INLINE int UDPHandle::trySend(const std::string &ip, unsigned int port, std::unique_ptr<char[]> data, unsigned int len) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -207,16 +169,14 @@ UVW_INLINE int UDPHandle::trySend(const std::string &ip, unsigned int port, std:
return trySend(reinterpret_cast<const sockaddr &>(addr), std::move(data), len); return trySend(reinterpret_cast<const sockaddr &>(addr), std::move(data), len);
} }
template<typename I> template<typename I>
UVW_INLINE int UDPHandle::trySend(Addr addr, std::unique_ptr<char[]> data, unsigned int len) { UVW_INLINE int UDPHandle::trySend(Addr addr, std::unique_ptr<char[]> data, unsigned int len) {
return trySend<I>(std::move(addr.ip), addr.port, std::move(data), len); return trySend<I>(std::move(addr.ip), addr.port, std::move(data), len);
} }
template<typename I> template<typename I>
UVW_INLINE int UDPHandle::trySend(const sockaddr &addr, char *data, unsigned int len) { UVW_INLINE int UDPHandle::trySend(const sockaddr &addr, char *data, unsigned int len) {
uv_buf_t bufs[] = { uv_buf_init(data, len) }; uv_buf_t bufs[] = {uv_buf_init(data, len)};
auto bw = uv_udp_try_send(get(), bufs, 1, &addr); auto bw = uv_udp_try_send(get(), bufs, 1, &addr);
if(bw < 0) { if(bw < 0) {
@ -227,7 +187,6 @@ UVW_INLINE int UDPHandle::trySend(const sockaddr &addr, char *data, unsigned int
return bw; return bw;
} }
template<typename I> template<typename I>
UVW_INLINE int UDPHandle::trySend(const std::string &ip, unsigned int port, char *data, unsigned int len) { UVW_INLINE int UDPHandle::trySend(const std::string &ip, unsigned int port, char *data, unsigned int len) {
typename details::IpTraits<I>::Type addr; typename details::IpTraits<I>::Type addr;
@ -235,34 +194,28 @@ UVW_INLINE int UDPHandle::trySend(const std::string &ip, unsigned int port, char
return trySend(reinterpret_cast<const sockaddr &>(addr), data, len); return trySend(reinterpret_cast<const sockaddr &>(addr), data, len);
} }
template<typename I> template<typename I>
UVW_INLINE int UDPHandle::trySend(Addr addr, char *data, unsigned int len) { UVW_INLINE int UDPHandle::trySend(Addr addr, char *data, unsigned int len) {
return trySend<I>(std::move(addr.ip), addr.port, data, len); return trySend<I>(std::move(addr.ip), addr.port, data, len);
} }
template<typename I> template<typename I>
UVW_INLINE void UDPHandle::recv() { UVW_INLINE void UDPHandle::recv() {
invoke(&uv_udp_recv_start, get(), &allocCallback, &recvCallback<I>); invoke(&uv_udp_recv_start, get(), &allocCallback, &recvCallback<I>);
} }
UVW_INLINE void UDPHandle::stop() { UVW_INLINE void UDPHandle::stop() {
invoke(&uv_udp_recv_stop, get()); invoke(&uv_udp_recv_stop, get());
} }
UVW_INLINE size_t UDPHandle::sendQueueSize() const noexcept { UVW_INLINE size_t UDPHandle::sendQueueSize() const noexcept {
return uv_udp_get_send_queue_size(get()); return uv_udp_get_send_queue_size(get());
} }
UVW_INLINE size_t UDPHandle::sendQueueCount() const noexcept { UVW_INLINE size_t UDPHandle::sendQueueCount() const noexcept {
return uv_udp_get_send_queue_count(get()); return uv_udp_get_send_queue_count(get());
} }
// explicit instantiations // explicit instantiations
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
template void UDPHandle::connect<IPv4>(const std::string &, unsigned int); template void UDPHandle::connect<IPv4>(const std::string &, unsigned int);
@ -323,5 +276,4 @@ template void UDPHandle::recv<IPv4>();
template void UDPHandle::recv<IPv6>(); template void UDPHandle::recv<IPv6>();
#endif // UVW_AS_LIB #endif // UVW_AS_LIB
} // namespace uvw
}

View File

@ -1,21 +1,18 @@
#ifndef UVW_UDP_INCLUDE_H #ifndef UVW_UDP_INCLUDE_H
#define UVW_UDP_INCLUDE_H #define UVW_UDP_INCLUDE_H
#include <type_traits>
#include <utility>
#include <cstddef> #include <cstddef>
#include <memory> #include <memory>
#include <string> #include <string>
#include <type_traits>
#include <utility>
#include <uv.h> #include <uv.h>
#include "request.hpp"
#include "handle.hpp" #include "handle.hpp"
#include "request.hpp"
#include "util.h" #include "util.h"
namespace uvw { namespace uvw {
/** /**
* @brief SendEvent event. * @brief SendEvent event.
* *
@ -23,7 +20,6 @@ namespace uvw {
*/ */
struct SendEvent {}; struct SendEvent {};
/** /**
* @brief UDPDataEvent event. * @brief UDPDataEvent event.
* *
@ -33,16 +29,14 @@ struct UDPDataEvent {
explicit UDPDataEvent(Addr sndr, std::unique_ptr<char[]> buf, std::size_t len, bool part) noexcept; explicit UDPDataEvent(Addr sndr, std::unique_ptr<char[]> buf, std::size_t len, bool part) noexcept;
std::unique_ptr<char[]> data; /*!< A bunch of data read on the stream. */ std::unique_ptr<char[]> data; /*!< A bunch of data read on the stream. */
std::size_t length; /*!< The amount of data read on the stream. */ std::size_t length; /*!< The amount of data read on the stream. */
Addr sender; /*!< A valid instance of Addr. */ Addr sender; /*!< A valid instance of Addr. */
bool partial; /*!< True if the message was truncated, false otherwise. */ bool partial; /*!< True if the message was truncated, false otherwise. */
}; };
namespace details { namespace details {
enum class UVUDPFlags : std::underlying_type_t<uv_udp_flags> {
enum class UVUDPFlags: std::underlying_type_t<uv_udp_flags> {
IPV6ONLY = UV_UDP_IPV6ONLY, IPV6ONLY = UV_UDP_IPV6ONLY,
UDP_PARTIAL = UV_UDP_PARTIAL, UDP_PARTIAL = UV_UDP_PARTIAL,
REUSEADDR = UV_UDP_REUSEADDR, REUSEADDR = UV_UDP_REUSEADDR,
@ -52,29 +46,25 @@ enum class UVUDPFlags: std::underlying_type_t<uv_udp_flags> {
UDP_RECVMMSG = UV_UDP_RECVMMSG UDP_RECVMMSG = UV_UDP_RECVMMSG
}; };
enum class UVMembership : std::underlying_type_t<uv_membership> {
enum class UVMembership: std::underlying_type_t<uv_membership> {
LEAVE_GROUP = UV_LEAVE_GROUP, LEAVE_GROUP = UV_LEAVE_GROUP,
JOIN_GROUP = UV_JOIN_GROUP JOIN_GROUP = UV_JOIN_GROUP
}; };
class SendReq final: public Request<SendReq, uv_udp_send_t> { class SendReq final: public Request<SendReq, uv_udp_send_t> {
public: public:
using Deleter = void(*)(char *); using Deleter = void (*)(char *);
SendReq(ConstructorAccess ca, std::shared_ptr<Loop> loop, std::unique_ptr<char[], Deleter> dt, unsigned int len); SendReq(ConstructorAccess ca, std::shared_ptr<Loop> loop, std::unique_ptr<char[], Deleter> dt, unsigned int len);
void send(uv_udp_t *handle, const struct sockaddr* addr); void send(uv_udp_t *handle, const struct sockaddr *addr);
private: private:
std::unique_ptr<char[], Deleter> data; std::unique_ptr<char[], Deleter> data;
uv_buf_t buf; uv_buf_t buf;
}; };
} // namespace details
}
/** /**
* @brief The UDPHandle handle. * @brief The UDPHandle handle.
@ -97,7 +87,7 @@ class UDPHandle final: public Handle<UDPHandle, uv_udp_t> {
static void recvCallback(uv_udp_t *handle, ssize_t nread, const uv_buf_t *buf, const sockaddr *addr, unsigned flags) { static void recvCallback(uv_udp_t *handle, ssize_t nread, const uv_buf_t *buf, const sockaddr *addr, unsigned flags) {
const typename details::IpTraits<I>::Type *aptr = reinterpret_cast<const typename details::IpTraits<I>::Type *>(addr); const typename details::IpTraits<I>::Type *aptr = reinterpret_cast<const typename details::IpTraits<I>::Type *>(addr);
UDPHandle &udp = *(static_cast<UDPHandle*>(handle->data)); UDPHandle &udp = *(static_cast<UDPHandle *>(handle->data));
// data will be destroyed no matter of what the value of nread is // data will be destroyed no matter of what the value of nread is
std::unique_ptr<char[]> data{buf->base}; std::unique_ptr<char[]> data{buf->base};
@ -578,17 +568,19 @@ public:
size_t sendQueueCount() const noexcept; size_t sendQueueCount() const noexcept;
private: private:
enum { DEFAULT, FLAGS } tag{DEFAULT}; enum {
DEFAULT,
FLAGS
} tag{DEFAULT};
unsigned int flags{}; unsigned int flags{};
}; };
/** /**
* @cond TURN_OFF_DOXYGEN * @cond TURN_OFF_DOXYGEN
* Internal details not to be documented. * Internal details not to be documented.
*/ */
// (extern) explicit instantiations // (extern) explicit instantiations
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
extern template void UDPHandle::connect<IPv4>(const std::string &, unsigned int); extern template void UDPHandle::connect<IPv4>(const std::string &, unsigned int);
@ -649,19 +641,15 @@ extern template void UDPHandle::recv<IPv4>();
extern template void UDPHandle::recv<IPv6>(); extern template void UDPHandle::recv<IPv6>();
#endif // UVW_AS_LIB #endif // UVW_AS_LIB
/** /**
* Internal details not to be documented. * Internal details not to be documented.
* @endcond * @endcond
*/ */
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "udp.cpp" # include "udp.cpp"
#endif #endif
#endif // UVW_UDP_INCLUDE_H #endif // UVW_UDP_INCLUDE_H

View File

@ -1,16 +1,13 @@
#ifndef UVW_UNDERLYING_TYPE_INCLUDE_H #ifndef UVW_UNDERLYING_TYPE_INCLUDE_H
#define UVW_UNDERLYING_TYPE_INCLUDE_H #define UVW_UNDERLYING_TYPE_INCLUDE_H
#include <memory> #include <memory>
#include <type_traits> #include <type_traits>
#include <utility> #include <utility>
#include "loop.h" #include "loop.h"
namespace uvw { namespace uvw {
/** /**
* @brief Wrapper class for underlying types. * @brief Wrapper class for underlying types.
* *
@ -22,7 +19,9 @@ class UnderlyingType {
friend class UnderlyingType; friend class UnderlyingType;
protected: protected:
struct ConstructorAccess { explicit ConstructorAccess(int) {} }; struct ConstructorAccess {
explicit ConstructorAccess(int) {}
};
template<typename R = U> template<typename R = U>
auto get() noexcept { auto get() noexcept {
@ -41,8 +40,7 @@ protected:
public: public:
explicit UnderlyingType(ConstructorAccess, std::shared_ptr<Loop> ref) noexcept explicit UnderlyingType(ConstructorAccess, std::shared_ptr<Loop> ref) noexcept
: pLoop{std::move(ref)}, resource{} : pLoop{std::move(ref)}, resource{} {}
{}
UnderlyingType(const UnderlyingType &) = delete; UnderlyingType(const UnderlyingType &) = delete;
UnderlyingType(UnderlyingType &&) = delete; UnderlyingType(UnderlyingType &&) = delete;
@ -51,8 +49,8 @@ public:
static_assert(std::is_base_of_v<UnderlyingType<T, U>, T>); static_assert(std::is_base_of_v<UnderlyingType<T, U>, T>);
} }
UnderlyingType & operator=(const UnderlyingType &) = delete; UnderlyingType &operator=(const UnderlyingType &) = delete;
UnderlyingType & operator=(UnderlyingType &&) = delete; UnderlyingType &operator=(UnderlyingType &&) = delete;
/** /**
* @brief Creates a new resource of the given type. * @brief Creates a new resource of the given type.
@ -60,7 +58,7 @@ public:
* @return A pointer to the newly created resource. * @return A pointer to the newly created resource.
*/ */
template<typename... Args> template<typename... Args>
static std::shared_ptr<T> create(Args&&... args) { static std::shared_ptr<T> create(Args &&...args) {
return std::make_shared<T>(ConstructorAccess{0}, std::forward<Args>(args)...); return std::make_shared<T>(ConstructorAccess{0}, std::forward<Args>(args)...);
} }
@ -68,7 +66,9 @@ public:
* @brief Gets the loop from which the resource was originated. * @brief Gets the loop from which the resource was originated.
* @return A reference to a loop instance. * @return A reference to a loop instance.
*/ */
Loop & loop() const noexcept { return *pLoop; } Loop &loop() const noexcept {
return *pLoop;
}
/** /**
* @brief Gets the underlying raw data structure. * @brief Gets the underlying raw data structure.
@ -85,7 +85,7 @@ public:
* *
* @return The underlying raw data structure. * @return The underlying raw data structure.
*/ */
const U * raw() const noexcept { const U *raw() const noexcept {
return &resource; return &resource;
} }
@ -104,7 +104,7 @@ public:
* *
* @return The underlying raw data structure. * @return The underlying raw data structure.
*/ */
U * raw() noexcept { U *raw() noexcept {
return const_cast<U *>(const_cast<const UnderlyingType *>(this)->raw()); return const_cast<U *>(const_cast<const UnderlyingType *>(this)->raw());
} }
@ -113,7 +113,6 @@ private:
U resource; U resource;
}; };
} // namespace uvw
}
#endif // UVW_UNDERLYING_TYPE_INCLUDE_H #endif // UVW_UNDERLYING_TYPE_INCLUDE_H

View File

@ -1,119 +1,95 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "util.h" # include "util.h"
#endif #endif
#include <algorithm> #include <algorithm>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE Passwd::Passwd(std::shared_ptr<uv_passwd_t> pwd) UVW_INLINE Passwd::Passwd(std::shared_ptr<uv_passwd_t> pwd)
: passwd{pwd} : passwd{pwd} {}
{}
UVW_INLINE std::string Passwd::username() const noexcept { UVW_INLINE std::string Passwd::username() const noexcept {
return ((passwd && passwd->username) ? passwd->username : ""); return ((passwd && passwd->username) ? passwd->username : "");
} }
UVW_INLINE decltype(uv_passwd_t::uid) Passwd::uid() const noexcept { UVW_INLINE decltype(uv_passwd_t::uid) Passwd::uid() const noexcept {
return (passwd ? passwd->uid : decltype(uv_passwd_t::uid){}); return (passwd ? passwd->uid : decltype(uv_passwd_t::uid){});
} }
UVW_INLINE decltype(uv_passwd_t::gid) Passwd::gid() const noexcept { UVW_INLINE decltype(uv_passwd_t::gid) Passwd::gid() const noexcept {
return (passwd ? passwd->gid : decltype(uv_passwd_t::gid){}); return (passwd ? passwd->gid : decltype(uv_passwd_t::gid){});
} }
UVW_INLINE std::string Passwd::shell() const noexcept { UVW_INLINE std::string Passwd::shell() const noexcept {
return ((passwd && passwd->shell) ? passwd->shell : ""); return ((passwd && passwd->shell) ? passwd->shell : "");
} }
UVW_INLINE std::string Passwd::homedir() const noexcept { UVW_INLINE std::string Passwd::homedir() const noexcept {
return ((passwd && passwd->homedir) ? passwd->homedir: ""); return ((passwd && passwd->homedir) ? passwd->homedir : "");
} }
UVW_INLINE Passwd::operator bool() const noexcept { UVW_INLINE Passwd::operator bool() const noexcept {
return static_cast<bool>(passwd); return static_cast<bool>(passwd);
} }
UVW_INLINE UtsName::UtsName(std::shared_ptr<uv_utsname_t> utsname) UVW_INLINE UtsName::UtsName(std::shared_ptr<uv_utsname_t> utsname)
: utsname{utsname} : utsname{utsname} {}
{}
UVW_INLINE std::string UtsName::sysname() const noexcept { UVW_INLINE std::string UtsName::sysname() const noexcept {
return utsname ? utsname->sysname : ""; return utsname ? utsname->sysname : "";
} }
UVW_INLINE std::string UtsName::release() const noexcept { UVW_INLINE std::string UtsName::release() const noexcept {
return utsname ? utsname->release : ""; return utsname ? utsname->release : "";
} }
UVW_INLINE std::string UtsName::version() const noexcept { UVW_INLINE std::string UtsName::version() const noexcept {
return utsname ? utsname->version : ""; return utsname ? utsname->version : "";
} }
UVW_INLINE std::string UtsName::machine() const noexcept { UVW_INLINE std::string UtsName::machine() const noexcept {
return utsname ? utsname->machine : ""; return utsname ? utsname->machine : "";
} }
UVW_INLINE PidType Utilities::OS::pid() noexcept { UVW_INLINE PidType Utilities::OS::pid() noexcept {
return uv_os_getpid(); return uv_os_getpid();
} }
UVW_INLINE PidType Utilities::OS::parent() noexcept { UVW_INLINE PidType Utilities::OS::parent() noexcept {
return uv_os_getppid(); return uv_os_getppid();
} }
UVW_INLINE std::string Utilities::OS::homedir() noexcept { UVW_INLINE std::string Utilities::OS::homedir() noexcept {
return details::tryRead(&uv_os_homedir); return details::tryRead(&uv_os_homedir);
} }
UVW_INLINE std::string Utilities::OS::tmpdir() noexcept { UVW_INLINE std::string Utilities::OS::tmpdir() noexcept {
return details::tryRead(&uv_os_tmpdir); return details::tryRead(&uv_os_tmpdir);
} }
UVW_INLINE std::string Utilities::OS::env(const std::string &name) noexcept { UVW_INLINE std::string Utilities::OS::env(const std::string &name) noexcept {
return details::tryRead(&uv_os_getenv, name.c_str()); return details::tryRead(&uv_os_getenv, name.c_str());
} }
UVW_INLINE bool Utilities::OS::env(const std::string &name, const std::string &value) noexcept { UVW_INLINE bool Utilities::OS::env(const std::string &name, const std::string &value) noexcept {
return (0 == (value.empty() ? uv_os_unsetenv(name.c_str()) : uv_os_setenv(name.c_str(), value.c_str()))); return (0 == (value.empty() ? uv_os_unsetenv(name.c_str()) : uv_os_setenv(name.c_str(), value.c_str())));
} }
UVW_INLINE std::string Utilities::OS::hostname() noexcept { UVW_INLINE std::string Utilities::OS::hostname() noexcept {
return details::tryRead(&uv_os_gethostname); return details::tryRead(&uv_os_gethostname);
} }
UVW_INLINE UtsName Utilities::OS::uname() noexcept { UVW_INLINE UtsName Utilities::OS::uname() noexcept {
auto ptr = std::make_shared<uv_utsname_t>(); auto ptr = std::make_shared<uv_utsname_t>();
uv_os_uname(ptr.get()); uv_os_uname(ptr.get());
return ptr; return ptr;
} }
UVW_INLINE Passwd Utilities::OS::passwd() noexcept { UVW_INLINE Passwd Utilities::OS::passwd() noexcept {
auto deleter = [](uv_passwd_t *passwd){ auto deleter = [](uv_passwd_t *passwd) {
uv_os_free_passwd(passwd); uv_os_free_passwd(passwd);
delete passwd; delete passwd;
}; };
@ -123,7 +99,6 @@ UVW_INLINE Passwd Utilities::OS::passwd() noexcept {
return ptr; return ptr;
} }
UVW_INLINE int Utilities::OS::priority(PidType pid) { UVW_INLINE int Utilities::OS::priority(PidType pid) {
int prio = 0; int prio = 0;
@ -134,12 +109,10 @@ UVW_INLINE int Utilities::OS::priority(PidType pid) {
return prio; return prio;
} }
UVW_INLINE bool Utilities::OS::priority(PidType pid, int prio) { UVW_INLINE bool Utilities::OS::priority(PidType pid, int prio) {
return 0 == uv_os_setpriority(pid, prio); return 0 == uv_os_setpriority(pid, prio);
} }
UVW_INLINE HandleType Utilities::guessHandle(HandleCategory category) noexcept { UVW_INLINE HandleType Utilities::guessHandle(HandleCategory category) noexcept {
switch(category) { switch(category) {
case UV_ASYNC: case UV_ASYNC:
@ -181,13 +154,11 @@ UVW_INLINE HandleType Utilities::guessHandle(HandleCategory category) noexcept {
} }
} }
UVW_INLINE HandleType Utilities::guessHandle(FileHandle file) noexcept { UVW_INLINE HandleType Utilities::guessHandle(FileHandle file) noexcept {
HandleCategory category = uv_guess_handle(file); HandleCategory category = uv_guess_handle(file);
return guessHandle(category); return guessHandle(category);
} }
UVW_INLINE std::vector<CPUInfo> Utilities::cpuInfo() noexcept { UVW_INLINE std::vector<CPUInfo> Utilities::cpuInfo() noexcept {
std::vector<CPUInfo> cpuinfos; std::vector<CPUInfo> cpuinfos;
@ -195,8 +166,8 @@ UVW_INLINE std::vector<CPUInfo> Utilities::cpuInfo() noexcept {
int count; int count;
if(0 == uv_cpu_info(&infos, &count)) { if(0 == uv_cpu_info(&infos, &count)) {
std::for_each(infos, infos+count, [&cpuinfos](const auto &info) { std::for_each(infos, infos + count, [&cpuinfos](const auto &info) {
cpuinfos.push_back({ info.model, info.speed, info.cpu_times }); cpuinfos.push_back({info.model, info.speed, info.cpu_times});
}); });
uv_free_cpu_info(infos, count); uv_free_cpu_info(infos, count);
@ -205,7 +176,6 @@ UVW_INLINE std::vector<CPUInfo> Utilities::cpuInfo() noexcept {
return cpuinfos; return cpuinfos;
} }
UVW_INLINE std::vector<InterfaceAddress> Utilities::interfaceAddresses() noexcept { UVW_INLINE std::vector<InterfaceAddress> Utilities::interfaceAddresses() noexcept {
std::vector<InterfaceAddress> interfaces; std::vector<InterfaceAddress> interfaces;
@ -213,11 +183,11 @@ UVW_INLINE std::vector<InterfaceAddress> Utilities::interfaceAddresses() noexcep
int count{0}; int count{0};
if(0 == uv_interface_addresses(&ifaces, &count)) { if(0 == uv_interface_addresses(&ifaces, &count)) {
std::for_each(ifaces, ifaces+count, [&interfaces](const auto &iface) { std::for_each(ifaces, ifaces + count, [&interfaces](const auto &iface) {
InterfaceAddress interfaceAddress; InterfaceAddress interfaceAddress;
interfaceAddress.name = iface.name; interfaceAddress.name = iface.name;
std::copy(iface.phys_addr, (iface.phys_addr+6), interfaceAddress.physical); std::copy(iface.phys_addr, (iface.phys_addr + 6), interfaceAddress.physical);
interfaceAddress.internal = iface.is_internal == 0 ? false : true; interfaceAddress.internal = iface.is_internal == 0 ? false : true;
if(iface.address.address4.sin_family == AF_INET) { if(iface.address.address4.sin_family == AF_INET) {
@ -237,34 +207,28 @@ UVW_INLINE std::vector<InterfaceAddress> Utilities::interfaceAddresses() noexcep
return interfaces; return interfaces;
} }
UVW_INLINE std::string Utilities::indexToName(unsigned int index) noexcept { UVW_INLINE std::string Utilities::indexToName(unsigned int index) noexcept {
return details::tryRead(&uv_if_indextoname, index); return details::tryRead(&uv_if_indextoname, index);
} }
UVW_INLINE std::string Utilities::indexToIid(unsigned int index) noexcept { UVW_INLINE std::string Utilities::indexToIid(unsigned int index) noexcept {
return details::tryRead(&uv_if_indextoiid, index); return details::tryRead(&uv_if_indextoiid, index);
} }
UVW_INLINE bool Utilities::replaceAllocator(MallocFuncType mallocFunc, ReallocFuncType reallocFunc, CallocFuncType callocFunc, FreeFuncType freeFunc) noexcept { UVW_INLINE bool Utilities::replaceAllocator(MallocFuncType mallocFunc, ReallocFuncType reallocFunc, CallocFuncType callocFunc, FreeFuncType freeFunc) noexcept {
return (0 == uv_replace_allocator(mallocFunc, reallocFunc, callocFunc, freeFunc)); return (0 == uv_replace_allocator(mallocFunc, reallocFunc, callocFunc, freeFunc));
} }
UVW_INLINE std::array<double, 3> Utilities::loadAverage() noexcept { UVW_INLINE std::array<double, 3> Utilities::loadAverage() noexcept {
std::array<double, 3> avg; std::array<double, 3> avg;
uv_loadavg(avg.data()); uv_loadavg(avg.data());
return avg; return avg;
} }
UVW_INLINE char **Utilities::setupArgs(int argc, char **argv) {
UVW_INLINE char ** Utilities::setupArgs(int argc, char** argv) {
return uv_setup_args(argc, argv); return uv_setup_args(argc, argv);
} }
UVW_INLINE std::string Utilities::processTitle() { UVW_INLINE std::string Utilities::processTitle() {
std::size_t size = details::DEFAULT_SIZE; std::size_t size = details::DEFAULT_SIZE;
char buf[details::DEFAULT_SIZE]; char buf[details::DEFAULT_SIZE];
@ -277,22 +241,18 @@ UVW_INLINE std::string Utilities::processTitle() {
return str; return str;
} }
UVW_INLINE bool Utilities::processTitle(const std::string &title) { UVW_INLINE bool Utilities::processTitle(const std::string &title) {
return (0 == uv_set_process_title(title.c_str())); return (0 == uv_set_process_title(title.c_str()));
} }
UVW_INLINE uint64_t Utilities::totalMemory() noexcept { UVW_INLINE uint64_t Utilities::totalMemory() noexcept {
return uv_get_total_memory(); return uv_get_total_memory();
} }
UVW_INLINE uint64_t Utilities::constrainedMemory() noexcept { UVW_INLINE uint64_t Utilities::constrainedMemory() noexcept {
return uv_get_constrained_memory(); return uv_get_constrained_memory();
} }
UVW_INLINE double Utilities::uptime() noexcept { UVW_INLINE double Utilities::uptime() noexcept {
double ret; double ret;
@ -303,44 +263,36 @@ UVW_INLINE double Utilities::uptime() noexcept {
return ret; return ret;
} }
UVW_INLINE RUsage Utilities::rusage() noexcept { UVW_INLINE RUsage Utilities::rusage() noexcept {
RUsage ru; RUsage ru;
auto err = uv_getrusage(&ru); auto err = uv_getrusage(&ru);
return err ? RUsage{} : ru; return err ? RUsage{} : ru;
} }
UVW_INLINE uint64_t Utilities::hrtime() noexcept { UVW_INLINE uint64_t Utilities::hrtime() noexcept {
return uv_hrtime(); return uv_hrtime();
} }
UVW_INLINE std::string Utilities::path() noexcept { UVW_INLINE std::string Utilities::path() noexcept {
return details::tryRead(&uv_exepath); return details::tryRead(&uv_exepath);
} }
UVW_INLINE std::string Utilities::cwd() noexcept { UVW_INLINE std::string Utilities::cwd() noexcept {
return details::tryRead(&uv_cwd); return details::tryRead(&uv_cwd);
} }
UVW_INLINE bool Utilities::chdir(const std::string &dir) noexcept { UVW_INLINE bool Utilities::chdir(const std::string &dir) noexcept {
return (0 == uv_chdir(dir.data())); return (0 == uv_chdir(dir.data()));
} }
UVW_INLINE TimeVal64 Utilities::timeOfDay() noexcept { UVW_INLINE TimeVal64 Utilities::timeOfDay() noexcept {
uv_timeval64_t ret; uv_timeval64_t ret;
uv_gettimeofday(&ret); uv_gettimeofday(&ret);
return ret; return ret;
} }
UVW_INLINE void Utilities::sleep(unsigned int msec) noexcept { UVW_INLINE void Utilities::sleep(unsigned int msec) noexcept {
uv_sleep(msec); uv_sleep(msec);
} }
} // namespace uvw
}

View File

@ -1,25 +1,21 @@
#ifndef UVW_UTIL_INCLUDE_H #ifndef UVW_UTIL_INCLUDE_H
#define UVW_UTIL_INCLUDE_H #define UVW_UTIL_INCLUDE_H
#include <array>
#include <cstddef>
#include <memory>
#include <string>
#include <string_view> #include <string_view>
#include <type_traits> #include <type_traits>
#include <cstddef>
#include <utility> #include <utility>
#include <string>
#include <vector> #include <vector>
#include <memory>
#include <array>
#include <uv.h> #include <uv.h>
namespace uvw { namespace uvw {
namespace details { namespace details {
enum class UVHandleType : std::underlying_type_t<uv_handle_type> {
enum class UVHandleType: std::underlying_type_t<uv_handle_type> {
UNKNOWN = UV_UNKNOWN_HANDLE, UNKNOWN = UV_UNKNOWN_HANDLE,
ASYNC = UV_ASYNC, ASYNC = UV_ASYNC,
CHECK = UV_CHECK, CHECK = UV_CHECK,
@ -40,15 +36,19 @@ enum class UVHandleType: std::underlying_type_t<uv_handle_type> {
FILE = UV_FILE FILE = UV_FILE
}; };
template<typename T> template<typename T>
struct UVTypeWrapper { struct UVTypeWrapper {
using Type = T; using Type = T;
constexpr UVTypeWrapper(): value{} {} constexpr UVTypeWrapper()
constexpr UVTypeWrapper(Type val): value{val} {} : value{} {}
constexpr operator Type() const noexcept { return value; } constexpr UVTypeWrapper(Type val)
: value{val} {}
constexpr operator Type() const noexcept {
return value;
}
bool operator==(UVTypeWrapper other) const noexcept { bool operator==(UVTypeWrapper other) const noexcept {
return value == other.value; return value == other.value;
@ -58,15 +58,12 @@ private:
const Type value; const Type value;
}; };
template<typename T> template<typename T>
bool operator==(UVTypeWrapper<T> lhs, UVTypeWrapper<T> rhs) { bool operator==(UVTypeWrapper<T> lhs, UVTypeWrapper<T> rhs) {
return !(lhs == rhs); return !(lhs == rhs);
} }
} // namespace details
}
/** /**
* @brief Utility class to handle flags. * @brief Utility class to handle flags.
@ -80,9 +77,13 @@ bool operator==(UVTypeWrapper<T> lhs, UVTypeWrapper<T> rhs) {
*/ */
template<typename E> template<typename E>
class Flags final { class Flags final {
static_assert(std::is_enum_v<E>);
using InnerType = std::underlying_type_t<E>; using InnerType = std::underlying_type_t<E>;
constexpr InnerType toInnerType(E flag) const noexcept { return static_cast<InnerType>(flag); } constexpr InnerType toInnerType(E flag) const noexcept {
return static_cast<InnerType>(flag);
}
public: public:
using Type = InnerType; using Type = InnerType;
@ -100,31 +101,35 @@ public:
* @brief Constructs a Flags object from a value of the enum `E`. * @brief Constructs a Flags object from a value of the enum `E`.
* @param flag A value of the enum `E`. * @param flag A value of the enum `E`.
*/ */
constexpr Flags(E flag) noexcept: flags{toInnerType(flag)} {} constexpr Flags(E flag) noexcept
: flags{toInnerType(flag)} {}
/** /**
* @brief Constructs a Flags object from an instance of the underlying type * @brief Constructs a Flags object from an instance of the underlying type
* of the enum `E`. * of the enum `E`.
* @param f An instance of the underlying type of the enum `E`. * @param f An instance of the underlying type of the enum `E`.
*/ */
constexpr Flags(Type f): flags{f} {} constexpr Flags(Type f)
: flags{f} {}
/** /**
* @brief Constructs an uninitialized Flags object. * @brief Constructs an uninitialized Flags object.
*/ */
constexpr Flags(): flags{} {} constexpr Flags()
: flags{} {}
constexpr Flags(const Flags &f) noexcept: flags{f.flags} { } constexpr Flags(const Flags &f) noexcept
constexpr Flags(Flags &&f) noexcept: flags{std::move(f.flags)} { } : flags{f.flags} {}
~Flags() noexcept { static_assert(std::is_enum_v<E>); } constexpr Flags(Flags &&f) noexcept
: flags{std::move(f.flags)} {}
constexpr Flags & operator=(const Flags &f) noexcept { constexpr Flags &operator=(const Flags &f) noexcept {
flags = f.flags; flags = f.flags;
return *this; return *this;
} }
constexpr Flags & operator=(Flags &&f) noexcept { constexpr Flags &operator=(Flags &&f) noexcept {
flags = std::move(f.flags); flags = std::move(f.flags);
return *this; return *this;
} }
@ -134,77 +139,86 @@ public:
* @param f A valid instance of Flags. * @param f A valid instance of Flags.
* @return This instance _or-ed_ with `f`. * @return This instance _or-ed_ with `f`.
*/ */
constexpr Flags operator|(const Flags &f) const noexcept { return Flags{flags | f.flags}; } constexpr Flags operator|(const Flags &f) const noexcept {
return Flags{flags | f.flags};
}
/** /**
* @brief Or operator. * @brief Or operator.
* @param flag A value of the enum `E`. * @param flag A value of the enum `E`.
* @return This instance _or-ed_ with `flag`. * @return This instance _or-ed_ with `flag`.
*/ */
constexpr Flags operator|(E flag) const noexcept { return Flags{flags | toInnerType(flag)}; } constexpr Flags operator|(E flag) const noexcept {
return Flags{flags | toInnerType(flag)};
}
/** /**
* @brief And operator. * @brief And operator.
* @param f A valid instance of Flags. * @param f A valid instance of Flags.
* @return This instance _and-ed_ with `f`. * @return This instance _and-ed_ with `f`.
*/ */
constexpr Flags operator&(const Flags &f) const noexcept { return Flags{flags & f.flags}; } constexpr Flags operator&(const Flags &f) const noexcept {
return Flags{flags & f.flags};
}
/** /**
* @brief And operator. * @brief And operator.
* @param flag A value of the enum `E`. * @param flag A value of the enum `E`.
* @return This instance _and-ed_ with `flag`. * @return This instance _and-ed_ with `flag`.
*/ */
constexpr Flags operator&(E flag) const noexcept { return Flags{flags & toInnerType(flag)}; } constexpr Flags operator&(E flag) const noexcept {
return Flags{flags & toInnerType(flag)};
}
/** /**
* @brief Checks if this instance is initialized. * @brief Checks if this instance is initialized.
* @return False if it's uninitialized, true otherwise. * @return False if it's uninitialized, true otherwise.
*/ */
explicit constexpr operator bool() const noexcept { return !(flags == InnerType{}); } explicit constexpr operator bool() const noexcept {
return !(flags == InnerType{});
}
/** /**
* @brief Casts the instance to the underlying type of `E`. * @brief Casts the instance to the underlying type of `E`.
* @return An integral representation of the contained flags. * @return An integral representation of the contained flags.
*/ */
constexpr operator Type() const noexcept { return flags; } constexpr operator Type() const noexcept {
return flags;
}
private: private:
InnerType flags; InnerType flags;
}; };
/** /**
* @brief Windows size representation. * @brief Windows size representation.
*/ */
struct WinSize { struct WinSize {
int width; /*!< The _width_ of the given window. */ int width; /*!< The _width_ of the given window. */
int height; /*!< The _height_ of the given window. */ int height; /*!< The _height_ of the given window. */
}; };
using HandleType = details::UVHandleType; /*!< The type of a handle. */ using HandleType = details::UVHandleType; /*!< The type of a handle. */
using HandleCategory = details::UVTypeWrapper<uv_handle_type>; /*!< Utility class that wraps an internal handle type. */ using HandleCategory = details::UVTypeWrapper<uv_handle_type>; /*!< Utility class that wraps an internal handle type. */
using FileHandle = details::UVTypeWrapper<uv_file>; /*!< Utility class that wraps an internal file handle. */ using FileHandle = details::UVTypeWrapper<uv_file>; /*!< Utility class that wraps an internal file handle. */
using OSSocketHandle = details::UVTypeWrapper<uv_os_sock_t>; /*!< Utility class that wraps an os socket handle. */ using OSSocketHandle = details::UVTypeWrapper<uv_os_sock_t>; /*!< Utility class that wraps an os socket handle. */
using OSFileDescriptor = details::UVTypeWrapper<uv_os_fd_t>; /*!< Utility class that wraps an os file descriptor. */ using OSFileDescriptor = details::UVTypeWrapper<uv_os_fd_t>; /*!< Utility class that wraps an os file descriptor. */
using PidType = details::UVTypeWrapper<uv_pid_t>; /*!< Utility class that wraps a cross platform representation of a pid. */ using PidType = details::UVTypeWrapper<uv_pid_t>; /*!< Utility class that wraps a cross platform representation of a pid. */
constexpr FileHandle StdIN{0}; /*!< Placeholder for stdin descriptor. */ constexpr FileHandle StdIN{0}; /*!< Placeholder for stdin descriptor. */
constexpr FileHandle StdOUT{1}; /*!< Placeholder for stdout descriptor. */ constexpr FileHandle StdOUT{1}; /*!< Placeholder for stdout descriptor. */
constexpr FileHandle StdERR{2}; /*!< Placeholder for stderr descriptor. */ constexpr FileHandle StdERR{2}; /*!< Placeholder for stderr descriptor. */
using TimeSpec = uv_timespec_t; /*!< Library equivalent for uv_timespec_t. */ using TimeSpec = uv_timespec_t; /*!< Library equivalent for uv_timespec_t. */
using Stat = uv_stat_t; /*!< Library equivalent for uv_stat_t. */ using Stat = uv_stat_t; /*!< Library equivalent for uv_stat_t. */
using Statfs = uv_statfs_t; /*!< Library equivalent for uv_statfs_t. */ using Statfs = uv_statfs_t; /*!< Library equivalent for uv_statfs_t. */
using Uid = uv_uid_t; /*!< Library equivalent for uv_uid_t. */ using Uid = uv_uid_t; /*!< Library equivalent for uv_uid_t. */
using Gid = uv_gid_t; /*!< Library equivalent for uv_gid_t. */ using Gid = uv_gid_t; /*!< Library equivalent for uv_gid_t. */
using TimeVal = uv_timeval_t; /*!< Library equivalent for uv_timeval_t. */ using TimeVal = uv_timeval_t; /*!< Library equivalent for uv_timeval_t. */
using TimeVal64 = uv_timeval64_t; /*!< Library equivalent for uv_timeval64_t. */ using TimeVal64 = uv_timeval64_t; /*!< Library equivalent for uv_timeval64_t. */
using RUsage = uv_rusage_t; /*!< Library equivalent for uv_rusage_t. */ using RUsage = uv_rusage_t; /*!< Library equivalent for uv_rusage_t. */
/** /**
* @brief Utility class. * @brief Utility class.
@ -257,7 +271,6 @@ private:
std::shared_ptr<uv_passwd_t> passwd; std::shared_ptr<uv_passwd_t> passwd;
}; };
/** /**
* @brief Utility class. * @brief Utility class.
* *
@ -298,7 +311,6 @@ private:
std::shared_ptr<uv_utsname_t> utsname; std::shared_ptr<uv_utsname_t> utsname;
}; };
/** /**
* @brief The IPv4 tag. * @brief The IPv4 tag.
* *
@ -306,7 +318,6 @@ private:
*/ */
struct IPv4 {}; struct IPv4 {};
/** /**
* @brief The IPv6 tag. * @brief The IPv6 tag.
* *
@ -314,16 +325,14 @@ struct IPv4 {};
*/ */
struct IPv6 {}; struct IPv6 {};
/** /**
* @brief Address representation. * @brief Address representation.
*/ */
struct Addr { struct Addr {
std::string ip; /*!< Either an IPv4 or an IPv6. */ std::string ip; /*!< Either an IPv4 or an IPv6. */
unsigned int port; /*!< A valid service identifier. */ unsigned int port; /*!< A valid service identifier. */
}; };
/** /**
* \brief CPU information. * \brief CPU information.
*/ */
@ -331,7 +340,7 @@ struct CPUInfo {
using CPUTime = decltype(uv_cpu_info_t::cpu_times); using CPUTime = decltype(uv_cpu_info_t::cpu_times);
std::string model; /*!< The model of the CPU. */ std::string model; /*!< The model of the CPU. */
int speed; /*!< The frequency of the CPU. */ int speed; /*!< The frequency of the CPU. */
/** /**
* @brief CPU times. * @brief CPU times.
@ -342,50 +351,51 @@ struct CPUInfo {
CPUTime times; CPUTime times;
}; };
/** /**
* \brief Interface address. * \brief Interface address.
*/ */
struct InterfaceAddress { struct InterfaceAddress {
std::string name; /*!< The name of the interface (as an example _eth0_). */ std::string name; /*!< The name of the interface (as an example _eth0_). */
char physical[6]; /*!< The physical address. */ char physical[6]; /*!< The physical address. */
bool internal; /*!< True if it is an internal interface (as an example _loopback_), false otherwise. */ bool internal; /*!< True if it is an internal interface (as an example _loopback_), false otherwise. */
Addr address; /*!< The address of the given interface. */ Addr address; /*!< The address of the given interface. */
Addr netmask; /*!< The netmask of the given interface. */ Addr netmask; /*!< The netmask of the given interface. */
}; };
namespace details { namespace details {
static constexpr std::size_t DEFAULT_SIZE = 128; static constexpr std::size_t DEFAULT_SIZE = 128;
template<typename> template<typename>
struct IpTraits; struct IpTraits;
template<> template<>
struct IpTraits<IPv4> { struct IpTraits<IPv4> {
using Type = sockaddr_in; using Type = sockaddr_in;
using AddrFuncType = int(*)(const char *, int, Type *); using AddrFuncType = int (*)(const char *, int, Type *);
using NameFuncType = int(*)(const Type *, char *, std::size_t); using NameFuncType = int (*)(const Type *, char *, std::size_t);
inline static const AddrFuncType addrFunc = &uv_ip4_addr; inline static const AddrFuncType addrFunc = &uv_ip4_addr;
inline static const NameFuncType nameFunc = &uv_ip4_name; inline static const NameFuncType nameFunc = &uv_ip4_name;
static constexpr auto sinPort(const Type *addr) { return addr->sin_port; }
};
static constexpr auto sinPort(const Type *addr) {
return addr->sin_port;
}
};
template<> template<>
struct IpTraits<IPv6> { struct IpTraits<IPv6> {
using Type = sockaddr_in6; using Type = sockaddr_in6;
using AddrFuncType = int(*)(const char *, int, Type *); using AddrFuncType = int (*)(const char *, int, Type *);
using NameFuncType = int(*)(const Type *, char *, std::size_t); using NameFuncType = int (*)(const Type *, char *, std::size_t);
inline static const AddrFuncType addrFunc = &uv_ip6_addr; inline static const AddrFuncType addrFunc = &uv_ip6_addr;
inline static const NameFuncType nameFunc = &uv_ip6_name; inline static const NameFuncType nameFunc = &uv_ip6_name;
static constexpr auto sinPort(const Type *addr) { return addr->sin6_port; }
};
static constexpr auto sinPort(const Type *addr) {
return addr->sin6_port;
}
};
template<typename I> template<typename I>
Addr address(const typename details::IpTraits<I>::Type *aptr) noexcept { Addr address(const typename details::IpTraits<I>::Type *aptr) noexcept {
@ -402,7 +412,6 @@ Addr address(const typename details::IpTraits<I>::Type *aptr) noexcept {
return addr; return addr;
} }
template<typename I, typename F, typename H> template<typename I, typename F, typename H>
Addr address(F &&f, const H *handle) noexcept { Addr address(F &&f, const H *handle) noexcept {
sockaddr_storage ssto; sockaddr_storage ssto;
@ -419,9 +428,8 @@ Addr address(F &&f, const H *handle) noexcept {
return addr; return addr;
} }
template<typename F, typename... Args> template<typename F, typename... Args>
std::string tryRead(F &&f, Args&&... args) noexcept { std::string tryRead(F &&f, Args &&...args) noexcept {
std::size_t size = DEFAULT_SIZE; std::size_t size = DEFAULT_SIZE;
char buf[DEFAULT_SIZE]; char buf[DEFAULT_SIZE];
std::string str{}; std::string str{};
@ -441,9 +449,7 @@ std::string tryRead(F &&f, Args&&... args) noexcept {
return str; return str;
} }
} // namespace details
}
/** /**
* @brief Miscellaneous utilities. * @brief Miscellaneous utilities.
@ -451,10 +457,10 @@ std::string tryRead(F &&f, Args&&... args) noexcept {
* Miscellaneous functions that dont really belong to any other class. * Miscellaneous functions that dont really belong to any other class.
*/ */
struct Utilities { struct Utilities {
using MallocFuncType = void*(*)(size_t); using MallocFuncType = void *(*)(size_t);
using ReallocFuncType = void*(*)(void*, size_t); using ReallocFuncType = void *(*)(void *, size_t);
using CallocFuncType = void*(*)(size_t, size_t); using CallocFuncType = void *(*)(size_t, size_t);
using FreeFuncType = void(*)(void*); using FreeFuncType = void (*)(void *);
/** /**
* @brief OS dedicated utilities. * @brief OS dedicated utilities.
@ -729,7 +735,7 @@ struct Utilities {
* *
* @return Arguments that haven't been consumed internally. * @return Arguments that haven't been consumed internally.
*/ */
static char ** setupArgs(int argc, char** argv); static char **setupArgs(int argc, char **argv);
/** /**
* @brief Gets the title of the current process. * @brief Gets the title of the current process.
@ -820,7 +826,6 @@ struct Utilities {
static void sleep(unsigned int msec) noexcept; static void sleep(unsigned int msec) noexcept;
}; };
/** /**
* @brief Helper type for visitors. * @brief Helper type for visitors.
* @tparam Func Types of function objects. * @tparam Func Types of function objects.
@ -830,7 +835,6 @@ struct Overloaded: Func... {
using Func::operator()...; using Func::operator()...;
}; };
/** /**
* @brief Deduction guide. * @brief Deduction guide.
* @tparam Func Types of function objects. * @tparam Func Types of function objects.
@ -838,13 +842,10 @@ struct Overloaded: Func... {
template<class... Func> template<class... Func>
Overloaded(Func...) -> Overloaded<Func...>; Overloaded(Func...) -> Overloaded<Func...>;
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "util.cpp" # include "util.cpp"
#endif #endif
#endif // UVW_UTIL_INCLUDE_H #endif // UVW_UTIL_INCLUDE_H

View File

@ -1,29 +1,22 @@
#ifdef UVW_AS_LIB #ifdef UVW_AS_LIB
#include "work.h" # include "work.h"
#endif #endif
#include <utility> #include <utility>
#include "config.h" #include "config.h"
namespace uvw { namespace uvw {
UVW_INLINE WorkReq::WorkReq(ConstructorAccess ca, std::shared_ptr<Loop> ref, InternalTask t) UVW_INLINE WorkReq::WorkReq(ConstructorAccess ca, std::shared_ptr<Loop> ref, InternalTask t)
: Request{ca, std::move(ref)}, task{t} : Request{ca, std::move(ref)}, task{t} {}
{}
UVW_INLINE void WorkReq::workCallback(uv_work_t *req) { UVW_INLINE void WorkReq::workCallback(uv_work_t *req) {
static_cast<WorkReq*>(req->data)->task(); static_cast<WorkReq *>(req->data)->task();
} }
UVW_INLINE void WorkReq::queue() { UVW_INLINE void WorkReq::queue() {
invoke(&uv_queue_work, parent(), get(), &workCallback, &defaultCallback<WorkEvent>); invoke(&uv_queue_work, parent(), get(), &workCallback, &defaultCallback<WorkEvent>);
} }
} // namespace uvw
}

View File

@ -1,17 +1,14 @@
#ifndef UVW_WORK_INCLUDE_H #ifndef UVW_WORK_INCLUDE_H
#define UVW_WORK_INCLUDE_H #define UVW_WORK_INCLUDE_H
#include <functional> #include <functional>
#include <memory> #include <memory>
#include <uv.h> #include <uv.h>
#include "request.hpp"
#include "loop.h" #include "loop.h"
#include "request.hpp"
namespace uvw { namespace uvw {
/** /**
* @brief WorkEvent event. * @brief WorkEvent event.
* *
@ -19,7 +16,6 @@ namespace uvw {
*/ */
struct WorkEvent {}; struct WorkEvent {};
/** /**
* @brief The WorkReq request. * @brief The WorkReq request.
* *
@ -57,12 +53,10 @@ private:
Task task{}; Task task{};
}; };
} // namespace uvw
}
#ifndef UVW_AS_LIB #ifndef UVW_AS_LIB
#include "work.cpp" # include "work.cpp"
#endif #endif
#endif // UVW_WORK_INCLUDE_H #endif // UVW_WORK_INCLUDE_H

View File

@ -1,9 +1,8 @@
#include <uvw.hpp>
#include <cassert> #include <cassert>
#include <chrono>
#include <iostream> #include <iostream>
#include <memory> #include <memory>
#include <chrono> #include <uvw.hpp>
void listen(uvw::Loop &loop) { void listen(uvw::Loop &loop) {
std::shared_ptr<uvw::TCPHandle> tcp = loop.resource<uvw::TCPHandle>(); std::shared_ptr<uvw::TCPHandle> tcp = loop.resource<uvw::TCPHandle>();
@ -52,7 +51,6 @@ void listen(uvw::Loop &loop) {
tcp->listen(); tcp->listen();
} }
void conn(uvw::Loop &loop) { void conn(uvw::Loop &loop) {
auto tcp = loop.resource<uvw::TCPHandle>(); auto tcp = loop.resource<uvw::TCPHandle>();
tcp->on<uvw::ErrorEvent>([](const uvw::ErrorEvent &, uvw::TCPHandle &) { assert(false); }); tcp->on<uvw::ErrorEvent>([](const uvw::ErrorEvent &, uvw::TCPHandle &) { assert(false); });
@ -65,11 +63,11 @@ void conn(uvw::Loop &loop) {
tcp->once<uvw::ConnectEvent>([](const uvw::ConnectEvent &, uvw::TCPHandle &handle) { tcp->once<uvw::ConnectEvent>([](const uvw::ConnectEvent &, uvw::TCPHandle &handle) {
std::cout << "connect" << std::endl; std::cout << "connect" << std::endl;
auto dataTryWrite = std::unique_ptr<char[]>(new char[1]{ 'a' }); auto dataTryWrite = std::unique_ptr<char[]>(new char[1]{'a'});
int bw = handle.tryWrite(std::move(dataTryWrite), 1); int bw = handle.tryWrite(std::move(dataTryWrite), 1);
std::cout << "written: " << ((int)bw) << std::endl; std::cout << "written: " << ((int)bw) << std::endl;
auto dataWrite = std::unique_ptr<char[]>(new char[2]{ 'b', 'c' }); auto dataWrite = std::unique_ptr<char[]>(new char[2]{'b', 'c'});
handle.write(std::move(dataWrite), 2); handle.write(std::move(dataWrite), 2);
}); });

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/async.h> #include <uvw/async.h>
TEST(Async, Send) { TEST(Async, Send) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::AsyncHandle>(); auto handle = loop->resource<uvw::AsyncHandle>();
@ -27,7 +26,6 @@ TEST(Async, Send) {
ASSERT_TRUE(checkAsyncEvent); ASSERT_TRUE(checkAsyncEvent);
} }
TEST(Async, Fake) { TEST(Async, Fake) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::AsyncHandle>(); auto handle = loop->resource<uvw::AsyncHandle>();

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/check.h> #include <uvw/check.h>
TEST(Check, StartAndStop) { TEST(Check, StartAndStop) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::CheckHandle>(); auto handle = loop->resource<uvw::CheckHandle>();
@ -28,7 +27,6 @@ TEST(Check, StartAndStop) {
ASSERT_TRUE(checkCheckEvent); ASSERT_TRUE(checkCheckEvent);
} }
TEST(Check, Fake) { TEST(Check, Fake) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::CheckHandle>(); auto handle = loop->resource<uvw::CheckHandle>();

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/dns.h> #include <uvw/dns.h>
TEST(GetAddrInfo, GetNodeAddrInfo) { TEST(GetAddrInfo, GetNodeAddrInfo) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto request = loop->resource<uvw::GetAddrInfoReq>(); auto request = loop->resource<uvw::GetAddrInfoReq>();
@ -22,7 +21,6 @@ TEST(GetAddrInfo, GetNodeAddrInfo) {
ASSERT_TRUE(checkAddrInfoEvent); ASSERT_TRUE(checkAddrInfoEvent);
} }
TEST(GetAddrInfo, GetNodeAddrInfoSync) { TEST(GetAddrInfo, GetNodeAddrInfoSync) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto request = loop->resource<uvw::GetAddrInfoReq>(); auto request = loop->resource<uvw::GetAddrInfoReq>();
@ -33,7 +31,6 @@ TEST(GetAddrInfo, GetNodeAddrInfoSync) {
loop->run(); loop->run();
} }
TEST(GetAddrInfo, GetServiceAddrInfo) { TEST(GetAddrInfo, GetServiceAddrInfo) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto request = loop->resource<uvw::GetAddrInfoReq>(); auto request = loop->resource<uvw::GetAddrInfoReq>();
@ -52,7 +49,6 @@ TEST(GetAddrInfo, GetServiceAddrInfo) {
ASSERT_TRUE(checkErrorEvent); ASSERT_TRUE(checkErrorEvent);
} }
TEST(GetAddrInfo, GetServiceAddrInfoSync) { TEST(GetAddrInfo, GetServiceAddrInfoSync) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto request = loop->resource<uvw::GetAddrInfoReq>(); auto request = loop->resource<uvw::GetAddrInfoReq>();
@ -62,7 +58,6 @@ TEST(GetAddrInfo, GetServiceAddrInfoSync) {
loop->run(); loop->run();
} }
TEST(GetAddrInfo, GetAddrInfo) { TEST(GetAddrInfo, GetAddrInfo) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto request = loop->resource<uvw::GetAddrInfoReq>(); auto request = loop->resource<uvw::GetAddrInfoReq>();
@ -83,7 +78,6 @@ TEST(GetAddrInfo, GetAddrInfo) {
ASSERT_TRUE(checkAddrInfoEvent); ASSERT_TRUE(checkAddrInfoEvent);
} }
TEST(GetAddrInfo, GetAddrInfoSync) { TEST(GetAddrInfo, GetAddrInfoSync) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto request = loop->resource<uvw::GetAddrInfoReq>(); auto request = loop->resource<uvw::GetAddrInfoReq>();
@ -94,7 +88,6 @@ TEST(GetAddrInfo, GetAddrInfoSync) {
loop->run(); loop->run();
} }
TEST(GetNameInfo, GetNameInfo) { TEST(GetNameInfo, GetNameInfo) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto koRequest = loop->resource<uvw::GetNameInfoReq>(); auto koRequest = loop->resource<uvw::GetNameInfoReq>();
@ -113,7 +106,7 @@ TEST(GetNameInfo, GetNameInfo) {
checkNameInfoEvent = true; checkNameInfoEvent = true;
}); });
koRequest->nameInfo(uvw::Addr{ "", 0 }, -1); koRequest->nameInfo(uvw::Addr{"", 0}, -1);
okRequest->nameInfo("irc.freenode.net", 6667); okRequest->nameInfo("irc.freenode.net", 6667);
loop->run(); loop->run();
@ -122,12 +115,11 @@ TEST(GetNameInfo, GetNameInfo) {
ASSERT_TRUE(checkNameInfoEvent); ASSERT_TRUE(checkNameInfoEvent);
} }
TEST(GetNameInfo, GetNameInfoSync) { TEST(GetNameInfo, GetNameInfoSync) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto request = loop->resource<uvw::GetNameInfoReq>(); auto request = loop->resource<uvw::GetNameInfoReq>();
ASSERT_FALSE(request->nameInfoSync(uvw::Addr{ "", 0 }, -1).first); ASSERT_FALSE(request->nameInfoSync(uvw::Addr{"", 0}, -1).first);
ASSERT_TRUE(request->nameInfoSync("irc.freenode.net", 6667).first); ASSERT_TRUE(request->nameInfoSync("irc.freenode.net", 6667).first);
loop->run(); loop->run();

View File

@ -2,14 +2,14 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/emitter.h> #include <uvw/emitter.h>
struct FakeEvent {};
struct FakeEvent { };
struct TestEmitter: uvw::Emitter<TestEmitter> { struct TestEmitter: uvw::Emitter<TestEmitter> {
void emit() { publish(FakeEvent{}); } void emit() {
publish(FakeEvent{});
}
}; };
TEST(ErrorEvent, Functionalities) { TEST(ErrorEvent, Functionalities) {
auto ecode = static_cast<std::underlying_type_t<uv_errno_t>>(UV_EADDRINUSE); auto ecode = static_cast<std::underlying_type_t<uv_errno_t>>(UV_EADDRINUSE);
@ -24,13 +24,12 @@ TEST(ErrorEvent, Functionalities) {
ASSERT_TRUE(static_cast<bool>(uvw::ErrorEvent{ecode})); ASSERT_TRUE(static_cast<bool>(uvw::ErrorEvent{ecode}));
} }
TEST(Emitter, EmptyAndClear) { TEST(Emitter, EmptyAndClear) {
TestEmitter emitter{}; TestEmitter emitter{};
ASSERT_TRUE(emitter.empty()); ASSERT_TRUE(emitter.empty());
emitter.on<uvw::ErrorEvent>([](const auto &, auto &){}); emitter.on<uvw::ErrorEvent>([](const auto &, auto &) {});
ASSERT_FALSE(emitter.empty()); ASSERT_FALSE(emitter.empty());
ASSERT_FALSE(emitter.empty<uvw::ErrorEvent>()); ASSERT_FALSE(emitter.empty<uvw::ErrorEvent>());
@ -48,8 +47,8 @@ TEST(Emitter, EmptyAndClear) {
ASSERT_TRUE(emitter.empty<uvw::ErrorEvent>()); ASSERT_TRUE(emitter.empty<uvw::ErrorEvent>());
ASSERT_TRUE(emitter.empty<FakeEvent>()); ASSERT_TRUE(emitter.empty<FakeEvent>());
emitter.on<uvw::ErrorEvent>([](const auto &, auto &){}); emitter.on<uvw::ErrorEvent>([](const auto &, auto &) {});
emitter.on<FakeEvent>([](const auto &, auto &){}); emitter.on<FakeEvent>([](const auto &, auto &) {});
ASSERT_FALSE(emitter.empty()); ASSERT_FALSE(emitter.empty());
ASSERT_FALSE(emitter.empty<uvw::ErrorEvent>()); ASSERT_FALSE(emitter.empty<uvw::ErrorEvent>());
@ -62,11 +61,10 @@ TEST(Emitter, EmptyAndClear) {
ASSERT_TRUE(emitter.empty<FakeEvent>()); ASSERT_TRUE(emitter.empty<FakeEvent>());
} }
TEST(Emitter, On) { TEST(Emitter, On) {
TestEmitter emitter{}; TestEmitter emitter{};
emitter.on<FakeEvent>([](const auto &, auto &){}); emitter.on<FakeEvent>([](const auto &, auto &) {});
ASSERT_FALSE(emitter.empty()); ASSERT_FALSE(emitter.empty());
ASSERT_FALSE(emitter.empty<FakeEvent>()); ASSERT_FALSE(emitter.empty<FakeEvent>());
@ -77,11 +75,10 @@ TEST(Emitter, On) {
ASSERT_FALSE(emitter.empty<FakeEvent>()); ASSERT_FALSE(emitter.empty<FakeEvent>());
} }
TEST(Emitter, Once) { TEST(Emitter, Once) {
TestEmitter emitter{}; TestEmitter emitter{};
emitter.once<FakeEvent>([](const auto &, auto &){}); emitter.once<FakeEvent>([](const auto &, auto &) {});
ASSERT_FALSE(emitter.empty()); ASSERT_FALSE(emitter.empty());
ASSERT_FALSE(emitter.empty<FakeEvent>()); ASSERT_FALSE(emitter.empty<FakeEvent>());
@ -92,11 +89,10 @@ TEST(Emitter, Once) {
ASSERT_TRUE(emitter.empty<FakeEvent>()); ASSERT_TRUE(emitter.empty<FakeEvent>());
} }
TEST(Emitter, OnceAndErase) { TEST(Emitter, OnceAndErase) {
TestEmitter emitter{}; TestEmitter emitter{};
auto conn = emitter.once<FakeEvent>([](const auto &, auto &){}); auto conn = emitter.once<FakeEvent>([](const auto &, auto &) {});
ASSERT_FALSE(emitter.empty()); ASSERT_FALSE(emitter.empty());
ASSERT_FALSE(emitter.empty<FakeEvent>()); ASSERT_FALSE(emitter.empty<FakeEvent>());
@ -107,11 +103,10 @@ TEST(Emitter, OnceAndErase) {
ASSERT_TRUE(emitter.empty<FakeEvent>()); ASSERT_TRUE(emitter.empty<FakeEvent>());
} }
TEST(Emitter, OnAndErase) { TEST(Emitter, OnAndErase) {
TestEmitter emitter{}; TestEmitter emitter{};
auto conn = emitter.on<FakeEvent>([](const auto &, auto &){}); auto conn = emitter.on<FakeEvent>([](const auto &, auto &) {});
ASSERT_FALSE(emitter.empty()); ASSERT_FALSE(emitter.empty());
ASSERT_FALSE(emitter.empty<FakeEvent>()); ASSERT_FALSE(emitter.empty<FakeEvent>());
@ -122,12 +117,11 @@ TEST(Emitter, OnAndErase) {
ASSERT_TRUE(emitter.empty<FakeEvent>()); ASSERT_TRUE(emitter.empty<FakeEvent>());
} }
TEST(Emitter, CallbackClear) { TEST(Emitter, CallbackClear) {
TestEmitter emitter{}; TestEmitter emitter{};
emitter.on<FakeEvent>([](const auto &, auto &ref) { emitter.on<FakeEvent>([](const auto &, auto &ref) {
ref.template on<FakeEvent>([](const auto &, auto &){}); ref.template on<FakeEvent>([](const auto &, auto &) {});
ref.clear(); ref.clear();
}); });
@ -141,7 +135,7 @@ TEST(Emitter, CallbackClear) {
emitter.on<FakeEvent>([](const auto &, auto &ref) { emitter.on<FakeEvent>([](const auto &, auto &ref) {
ref.clear(); ref.clear();
ref.template on<FakeEvent>([](const auto &, auto &){}); ref.template on<FakeEvent>([](const auto &, auto &) {});
}); });
ASSERT_FALSE(emitter.empty()); ASSERT_FALSE(emitter.empty());

View File

@ -1,13 +1,12 @@
#include <chrono>
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/fs.h> #include <uvw/fs.h>
#include <chrono>
#ifdef _WIN32 #ifdef _WIN32
#define _CRT_DECLARE_NONSTDC_NAMES 1 # define _CRT_DECLARE_NONSTDC_NAMES 1
#include <fcntl.h> # include <fcntl.h>
#endif #endif
TEST(FileReq, OpenAndCloseErr) { TEST(FileReq, OpenAndCloseErr) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/err.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/err.file"};
@ -38,7 +37,6 @@ TEST(FileReq, OpenAndCloseErr) {
ASSERT_TRUE(checkFileCloseErrorEvent); ASSERT_TRUE(checkFileCloseErrorEvent);
} }
TEST(FileReq, OpenAndCloseErrSync) { TEST(FileReq, OpenAndCloseErrSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/err.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/err.file"};
@ -51,7 +49,6 @@ TEST(FileReq, OpenAndCloseErrSync) {
loop->run(); loop->run();
} }
TEST(FileReq, OpenAndClose) { TEST(FileReq, OpenAndClose) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -83,7 +80,6 @@ TEST(FileReq, OpenAndClose) {
ASSERT_TRUE(checkFileCloseEvent); ASSERT_TRUE(checkFileCloseEvent);
} }
TEST(FileReq, OpenAndCloseSync) { TEST(FileReq, OpenAndCloseSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -96,7 +92,6 @@ TEST(FileReq, OpenAndCloseSync) {
loop->run(); loop->run();
} }
TEST(FileReq, RWChecked) { TEST(FileReq, RWChecked) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -122,7 +117,7 @@ TEST(FileReq, RWChecked) {
}); });
request->on<uvw::FsEvent<uvw::FileReq::Type::OPEN>>([](const auto &, auto &req) { request->on<uvw::FsEvent<uvw::FileReq::Type::OPEN>>([](const auto &, auto &req) {
req.write(std::unique_ptr<char[]>{new char[1]{ 42 }}, 1, 0); req.write(std::unique_ptr<char[]>{new char[1]{42}}, 1, 0);
}); });
auto flags = uvw::Flags<uvw::FileReq::FileOpen>::from<uvw::FileReq::FileOpen::CREAT, uvw::FileReq::FileOpen::RDWR, uvw::FileReq::FileOpen::TRUNC>(); auto flags = uvw::Flags<uvw::FileReq::FileOpen>::from<uvw::FileReq::FileOpen::CREAT, uvw::FileReq::FileOpen::RDWR, uvw::FileReq::FileOpen::TRUNC>();
@ -134,10 +129,9 @@ TEST(FileReq, RWChecked) {
ASSERT_TRUE(checkFileReadEvent); ASSERT_TRUE(checkFileReadEvent);
} }
TEST(FileReq, RWUnchecked) { TEST(FileReq, RWUnchecked) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
std::unique_ptr<char[]> data{new char[1]{ 42 }}; std::unique_ptr<char[]> data{new char[1]{42}};
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto request = loop->resource<uvw::FileReq>(); auto request = loop->resource<uvw::FileReq>();
@ -173,7 +167,6 @@ TEST(FileReq, RWUnchecked) {
ASSERT_TRUE(checkFileReadEvent); ASSERT_TRUE(checkFileReadEvent);
} }
TEST(FileReq, RWSync) { TEST(FileReq, RWSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -182,7 +175,7 @@ TEST(FileReq, RWSync) {
ASSERT_TRUE(request->openSync(filename, O_CREAT | O_RDWR | O_TRUNC, 0644)); ASSERT_TRUE(request->openSync(filename, O_CREAT | O_RDWR | O_TRUNC, 0644));
auto writeR = request->writeSync(std::unique_ptr<char[]>{new char[1]{ 42 }}, 1, 0); auto writeR = request->writeSync(std::unique_ptr<char[]>{new char[1]{42}}, 1, 0);
ASSERT_TRUE(writeR.first); ASSERT_TRUE(writeR.first);
ASSERT_EQ(writeR.second, std::size_t{1}); ASSERT_EQ(writeR.second, std::size_t{1});
@ -197,7 +190,6 @@ TEST(FileReq, RWSync) {
loop->run(); loop->run();
} }
TEST(FileReq, Stat) { TEST(FileReq, Stat) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -226,7 +218,6 @@ TEST(FileReq, Stat) {
ASSERT_TRUE(checkFileStatEvent); ASSERT_TRUE(checkFileStatEvent);
} }
TEST(FileReq, StatSync) { TEST(FileReq, StatSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -243,7 +234,6 @@ TEST(FileReq, StatSync) {
loop->run(); loop->run();
} }
TEST(FileReq, Sync) { TEST(FileReq, Sync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -272,7 +262,6 @@ TEST(FileReq, Sync) {
ASSERT_TRUE(checkFileSyncEvent); ASSERT_TRUE(checkFileSyncEvent);
} }
TEST(FileReq, SyncSync) { TEST(FileReq, SyncSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -286,7 +275,6 @@ TEST(FileReq, SyncSync) {
loop->run(); loop->run();
} }
TEST(FileReq, Datasync) { TEST(FileReq, Datasync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -315,7 +303,6 @@ TEST(FileReq, Datasync) {
ASSERT_TRUE(checkFileDatasyncEvent); ASSERT_TRUE(checkFileDatasyncEvent);
} }
TEST(FileReq, DatasyncSync) { TEST(FileReq, DatasyncSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -329,7 +316,6 @@ TEST(FileReq, DatasyncSync) {
loop->run(); loop->run();
} }
TEST(FileReq, Truncate) { TEST(FileReq, Truncate) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -358,7 +344,6 @@ TEST(FileReq, Truncate) {
ASSERT_TRUE(checkFileTruncateEvent); ASSERT_TRUE(checkFileTruncateEvent);
} }
TEST(FileReq, TruncateSync) { TEST(FileReq, TruncateSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -372,7 +357,6 @@ TEST(FileReq, TruncateSync) {
loop->run(); loop->run();
} }
TEST(FileReq, Chmod) { TEST(FileReq, Chmod) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -401,7 +385,6 @@ TEST(FileReq, Chmod) {
ASSERT_TRUE(checkFileChmodEvent); ASSERT_TRUE(checkFileChmodEvent);
} }
TEST(FileReq, ChmodSync) { TEST(FileReq, ChmodSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -415,7 +398,6 @@ TEST(FileReq, ChmodSync) {
loop->run(); loop->run();
} }
TEST(FileReq, Futime) { TEST(FileReq, Futime) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -447,7 +429,6 @@ TEST(FileReq, Futime) {
ASSERT_TRUE(checkFileUtimeEvent); ASSERT_TRUE(checkFileUtimeEvent);
} }
TEST(FileReq, FutimeSync) { TEST(FileReq, FutimeSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -467,7 +448,6 @@ TEST(FileReq, FutimeSync) {
loop->run(); loop->run();
} }
TEST(FileReq, Chown) { TEST(FileReq, Chown) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};
@ -502,7 +482,6 @@ TEST(FileReq, Chown) {
ASSERT_TRUE(checkFileChownEvent); ASSERT_TRUE(checkFileChownEvent);
} }
TEST(FileReq, ChownSync) { TEST(FileReq, ChownSync) {
const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FILE_REQ_DIR} + std::string{"/test.file"};

View File

@ -1,10 +1,10 @@
#include <chrono>
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/fs.h> #include <uvw/fs.h>
#include <chrono>
#ifdef _WIN32 #ifdef _WIN32
#define _CRT_DECLARE_NONSTDC_NAMES 1 # define _CRT_DECLARE_NONSTDC_NAMES 1
#include <fcntl.h> # include <fcntl.h>
#endif #endif
TEST(FileReq, SendFile) { TEST(FileReq, SendFile) {
@ -44,7 +44,6 @@ TEST(FileReq, SendFile) {
ASSERT_TRUE(checkFileSendFileEvent); ASSERT_TRUE(checkFileSendFileEvent);
} }
TEST(FileReq, SendFileSync) { TEST(FileReq, SendFileSync) {
const std::string srcFilename = std::string{TARGET_FILE_REQ_SENDFILE_DIR} + std::string{"/src.file"}; const std::string srcFilename = std::string{TARGET_FILE_REQ_SENDFILE_DIR} + std::string{"/src.file"};
const std::string dstFilename = std::string{TARGET_FILE_REQ_SENDFILE_DIR} + std::string{"/dst.file"}; const std::string dstFilename = std::string{TARGET_FILE_REQ_SENDFILE_DIR} + std::string{"/dst.file"};
@ -64,4 +63,3 @@ TEST(FileReq, SendFileSync) {
loop->run(); loop->run();
} }

View File

@ -2,7 +2,6 @@
#include <uvw/fs.h> #include <uvw/fs.h>
#include <uvw/fs_event.h> #include <uvw/fs_event.h>
TEST(FsEvent, Functionalities) { TEST(FsEvent, Functionalities) {
const std::string filename = std::string{TARGET_FS_EVENT_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_EVENT_DIR} + std::string{"/test.file"};
@ -29,7 +28,7 @@ TEST(FsEvent, Functionalities) {
}); });
request->on<uvw::FsEvent<uvw::FileReq::Type::OPEN>>([](const auto &, auto &req) { request->on<uvw::FsEvent<uvw::FileReq::Type::OPEN>>([](const auto &, auto &req) {
req.write(std::unique_ptr<char[]>{new char[1]{ 42 }}, 1, 0); req.write(std::unique_ptr<char[]>{new char[1]{42}}, 1, 0);
}); });
handle->start(std::string{TARGET_FS_EVENT_DIR}, uvw::FsEventHandle::Event::RECURSIVE); handle->start(std::string{TARGET_FS_EVENT_DIR}, uvw::FsEventHandle::Event::RECURSIVE);

View File

@ -3,7 +3,6 @@
#include <uvw/fs_event.h> #include <uvw/fs_event.h>
#include <uvw/fs_poll.h> #include <uvw/fs_poll.h>
TEST(FsPoll, Functionalities) { TEST(FsPoll, Functionalities) {
const std::string filename = std::string{TARGET_FS_POLL_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_POLL_DIR} + std::string{"/test.file"};
@ -30,7 +29,7 @@ TEST(FsPoll, Functionalities) {
request->openSync(filename, O_CREAT | O_RDWR | O_TRUNC, 0755); request->openSync(filename, O_CREAT | O_RDWR | O_TRUNC, 0755);
handle->start(filename, uvw::FsPollHandle::Time{1000}); handle->start(filename, uvw::FsPollHandle::Time{1000});
request->write(std::unique_ptr<char[]>{new char[1]{ 42 }}, 1, 0); request->write(std::unique_ptr<char[]>{new char[1]{42}}, 1, 0);
ASSERT_EQ(handle->path(), filename); ASSERT_EQ(handle->path(), filename);
ASSERT_TRUE(handle->active()); ASSERT_TRUE(handle->active());

View File

@ -1,13 +1,12 @@
#include <chrono>
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/fs.h> #include <uvw/fs.h>
#include <chrono>
#ifdef _WIN32 #ifdef _WIN32
#define _CRT_DECLARE_NONSTDC_NAMES 1 # define _CRT_DECLARE_NONSTDC_NAMES 1
#include <fcntl.h> # include <fcntl.h>
#endif #endif
TEST(FsReq, MkdirAndRmdir) { TEST(FsReq, MkdirAndRmdir) {
const std::string dirname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.dir"}; const std::string dirname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.dir"};
@ -38,7 +37,6 @@ TEST(FsReq, MkdirAndRmdir) {
ASSERT_TRUE(checkFsRmdirEvent); ASSERT_TRUE(checkFsRmdirEvent);
} }
TEST(FsReq, MkdirAndRmdirSync) { TEST(FsReq, MkdirAndRmdirSync) {
const std::string dirname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.dir"}; const std::string dirname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.dir"};
@ -51,7 +49,6 @@ TEST(FsReq, MkdirAndRmdirSync) {
loop->run(); loop->run();
} }
TEST(FsReq, MkdtempAndRmdir) { TEST(FsReq, MkdtempAndRmdir) {
const std::string dirname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.dir.XXXXXX"}; const std::string dirname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.dir.XXXXXX"};
@ -83,7 +80,6 @@ TEST(FsReq, MkdtempAndRmdir) {
ASSERT_TRUE(checkFsRmdirEvent); ASSERT_TRUE(checkFsRmdirEvent);
} }
TEST(FsReq, MkdtempAndRmdirSync) { TEST(FsReq, MkdtempAndRmdirSync) {
const std::string dirname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.dir.XXXXXX"}; const std::string dirname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.dir.XXXXXX"};
@ -99,7 +95,6 @@ TEST(FsReq, MkdtempAndRmdirSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Stat) { TEST(FsReq, Stat) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -133,7 +128,6 @@ TEST(FsReq, Stat) {
ASSERT_TRUE(checkFsStatEvent); ASSERT_TRUE(checkFsStatEvent);
} }
TEST(FsReq, StatSync) { TEST(FsReq, StatSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -151,7 +145,6 @@ TEST(FsReq, StatSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Lstat) { TEST(FsReq, Lstat) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -185,7 +178,6 @@ TEST(FsReq, Lstat) {
ASSERT_TRUE(checkFsLstatEvent); ASSERT_TRUE(checkFsLstatEvent);
} }
TEST(FsReq, LstatSync) { TEST(FsReq, LstatSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -203,7 +195,6 @@ TEST(FsReq, LstatSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Rename) { TEST(FsReq, Rename) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
const std::string rename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.rename"}; const std::string rename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.rename"};
@ -238,7 +229,6 @@ TEST(FsReq, Rename) {
ASSERT_TRUE(checkFsRenameEvent); ASSERT_TRUE(checkFsRenameEvent);
} }
TEST(FsReq, RenameSync) { TEST(FsReq, RenameSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
const std::string rename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.rename"}; const std::string rename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.rename"};
@ -254,7 +244,6 @@ TEST(FsReq, RenameSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Access) { TEST(FsReq, Access) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -288,7 +277,6 @@ TEST(FsReq, Access) {
ASSERT_TRUE(checkFsAccessEvent); ASSERT_TRUE(checkFsAccessEvent);
} }
TEST(FsReq, AccessSync) { TEST(FsReq, AccessSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -303,7 +291,6 @@ TEST(FsReq, AccessSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Chmod) { TEST(FsReq, Chmod) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -337,7 +324,6 @@ TEST(FsReq, Chmod) {
ASSERT_TRUE(checkFsChmodEvent); ASSERT_TRUE(checkFsChmodEvent);
} }
TEST(FsReq, ChmodSync) { TEST(FsReq, ChmodSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -352,7 +338,6 @@ TEST(FsReq, ChmodSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Utime) { TEST(FsReq, Utime) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -389,7 +374,6 @@ TEST(FsReq, Utime) {
ASSERT_TRUE(checkFsUtimeEvent); ASSERT_TRUE(checkFsUtimeEvent);
} }
TEST(FsReq, UtimeSync) { TEST(FsReq, UtimeSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -409,7 +393,6 @@ TEST(FsReq, UtimeSync) {
loop->run(); loop->run();
} }
TEST(FsReq, LinkAndUnlink) { TEST(FsReq, LinkAndUnlink) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"}; const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"};
@ -452,7 +435,6 @@ TEST(FsReq, LinkAndUnlink) {
ASSERT_TRUE(checkFsUnlinkEvent); ASSERT_TRUE(checkFsUnlinkEvent);
} }
TEST(FsReq, LinkAndUnlinkSync) { TEST(FsReq, LinkAndUnlinkSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"}; const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"};
@ -469,7 +451,6 @@ TEST(FsReq, LinkAndUnlinkSync) {
loop->run(); loop->run();
} }
TEST(FsReq, SymlinkAndUnlink) { TEST(FsReq, SymlinkAndUnlink) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"}; const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"};
@ -512,7 +493,6 @@ TEST(FsReq, SymlinkAndUnlink) {
ASSERT_TRUE(checkFsUnlinkEvent); ASSERT_TRUE(checkFsUnlinkEvent);
} }
TEST(FsReq, SymlinkAndUnlinkSync) { TEST(FsReq, SymlinkAndUnlinkSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"}; const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"};
@ -529,7 +509,6 @@ TEST(FsReq, SymlinkAndUnlinkSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Readlink) { TEST(FsReq, Readlink) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"}; const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"};
@ -569,7 +548,6 @@ TEST(FsReq, Readlink) {
ASSERT_TRUE(checkFsReadlinkEvent); ASSERT_TRUE(checkFsReadlinkEvent);
} }
TEST(FsReq, ReadlinkSync) { TEST(FsReq, ReadlinkSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"}; const std::string linkname = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.link"};
@ -590,7 +568,6 @@ TEST(FsReq, ReadlinkSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Realpath) { TEST(FsReq, Realpath) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -625,7 +602,6 @@ TEST(FsReq, Realpath) {
ASSERT_TRUE(checkFsRealpathEvent); ASSERT_TRUE(checkFsRealpathEvent);
} }
TEST(FsReq, RealpathSync) { TEST(FsReq, RealpathSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -644,7 +620,6 @@ TEST(FsReq, RealpathSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Chown) { TEST(FsReq, Chown) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -684,7 +659,6 @@ TEST(FsReq, Chown) {
ASSERT_TRUE(checkFsChownEvent); ASSERT_TRUE(checkFsChownEvent);
} }
TEST(FsReq, ChownSync) { TEST(FsReq, ChownSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -705,7 +679,6 @@ TEST(FsReq, ChownSync) {
loop->run(); loop->run();
} }
TEST(FsReq, Lchown) { TEST(FsReq, Lchown) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -745,7 +718,6 @@ TEST(FsReq, Lchown) {
ASSERT_TRUE(checkFsLChownEvent); ASSERT_TRUE(checkFsLChownEvent);
} }
TEST(FsReq, LchownSync) { TEST(FsReq, LchownSync) {
const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"}; const std::string filename = std::string{TARGET_FS_REQ_DIR} + std::string{"/test.file"};
@ -785,7 +757,7 @@ TEST(FsReq, ReadDir) {
fsReq->on<uvw::FsEvent<uvw::FsReq::Type::READDIR>>([&checkFsReadDirEvent](const auto &event, auto &hndl) { fsReq->on<uvw::FsEvent<uvw::FsReq::Type::READDIR>>([&checkFsReadDirEvent](const auto &event, auto &hndl) {
ASSERT_FALSE(checkFsReadDirEvent); ASSERT_FALSE(checkFsReadDirEvent);
if (!event.eos) { if(!event.eos) {
hndl.readdir(); hndl.readdir();
} else { } else {
checkFsReadDirEvent = true; checkFsReadDirEvent = true;

View File

@ -2,18 +2,19 @@
#include <uvw/async.h> #include <uvw/async.h>
#include <uvw/handle.hpp> #include <uvw/handle.hpp>
struct fake_handle_t {
struct fake_handle_t { void *data; }; void *data;
};
struct FakeHandle: uvw::Handle<FakeHandle, fake_handle_t> { struct FakeHandle: uvw::Handle<FakeHandle, fake_handle_t> {
using Handle::Handle; using Handle::Handle;
template<typename... Args> template<typename... Args>
bool init(Args&&...) { return initialize([](auto...){ return true; }); } bool init(Args &&...) {
return initialize([](auto...) { return true; });
}
}; };
TEST(Handle, Functionalities) { TEST(Handle, Functionalities) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::AsyncHandle>(); auto handle = loop->resource<uvw::AsyncHandle>();
@ -46,7 +47,6 @@ TEST(Handle, Functionalities) {
ASSERT_NO_THROW(handle->fd()); ASSERT_NO_THROW(handle->fd());
} }
TEST(Handle, InitializationFailure) { TEST(Handle, InitializationFailure) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto resource = loop->resource<FakeHandle>(); auto resource = loop->resource<FakeHandle>();

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/idle.h> #include <uvw/idle.h>
TEST(Idle, StartAndStop) { TEST(Idle, StartAndStop) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::IdleHandle>(); auto handle = loop->resource<uvw::IdleHandle>();
@ -28,7 +27,6 @@ TEST(Idle, StartAndStop) {
ASSERT_TRUE(checkIdleEvent); ASSERT_TRUE(checkIdleEvent);
} }
TEST(Idle, Fake) { TEST(Idle, Fake) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::IdleHandle>(); auto handle = loop->resource<uvw::IdleHandle>();

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/lib.h> #include <uvw/lib.h>
TEST(SharedLib, Failure) { TEST(SharedLib, Failure) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto lib = loop->resource<uvw::SharedLib>("foobar.so"); auto lib = loop->resource<uvw::SharedLib>("foobar.so");
@ -14,7 +13,6 @@ TEST(SharedLib, Failure) {
lib.reset(); lib.reset();
} }
TEST(SharedLib, Success) { TEST(SharedLib, Success) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto lib = loop->resource<uvw::SharedLib>(TARGET_LIB_SO); auto lib = loop->resource<uvw::SharedLib>(TARGET_LIB_SO);

View File

@ -1,8 +1,7 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/loop.h>
#include <uvw/prepare.h> #include <uvw/prepare.h>
#include <uvw/work.h> #include <uvw/work.h>
#include <uvw/loop.h>
TEST(Loop, DefaultLoop) { TEST(Loop, DefaultLoop) {
auto def = uvw::Loop::getDefault(); auto def = uvw::Loop::getDefault();
@ -17,11 +16,10 @@ TEST(Loop, DefaultLoop) {
ASSERT_EQ(def, def2); ASSERT_EQ(def, def2);
} }
TEST(Loop, Functionalities) { TEST(Loop, Functionalities) {
auto loop = uvw::Loop::create(); auto loop = uvw::Loop::create();
auto handle = loop->resource<uvw::PrepareHandle>(); auto handle = loop->resource<uvw::PrepareHandle>();
auto req = loop->resource<uvw::WorkReq>([]{}); auto req = loop->resource<uvw::WorkReq>([] {});
loop->on<uvw::ErrorEvent>([](auto &&...) { FAIL(); }); loop->on<uvw::ErrorEvent>([](auto &&...) { FAIL(); });
req->on<uvw::ErrorEvent>([](auto &&...) { FAIL(); }); req->on<uvw::ErrorEvent>([](auto &&...) { FAIL(); });
@ -64,7 +62,6 @@ TEST(Loop, Functionalities) {
ASSERT_FALSE(loop->alive()); ASSERT_FALSE(loop->alive());
} }
TEST(Loop, UserData) { TEST(Loop, UserData) {
auto loop = uvw::Loop::create(); auto loop = uvw::Loop::create();
loop->data(std::make_shared<int>(42)); loop->data(std::make_shared<int>(42));
@ -78,21 +75,18 @@ TEST(Loop, UserData) {
ASSERT_EQ(*loop->data<int>(), 42); ASSERT_EQ(*loop->data<int>(), 42);
} }
TEST(Loop, Configure) { TEST(Loop, Configure) {
auto loop = uvw::Loop::create(); auto loop = uvw::Loop::create();
ASSERT_NO_THROW(loop->configure(uvw::Loop::Configure::BLOCK_SIGNAL, 9)); ASSERT_NO_THROW(loop->configure(uvw::Loop::Configure::BLOCK_SIGNAL, 9));
ASSERT_NO_THROW(loop->run()); ASSERT_NO_THROW(loop->run());
} }
TEST(Loop, IdleTime) { TEST(Loop, IdleTime) {
auto loop = uvw::Loop::create(); auto loop = uvw::Loop::create();
loop->configure(uvw::Loop::Configure::IDLE_TIME); loop->configure(uvw::Loop::Configure::IDLE_TIME);
ASSERT_EQ(loop->idleTime().count(), 0u); ASSERT_EQ(loop->idleTime().count(), 0u);
} }
TEST(Loop, Raw) { TEST(Loop, Raw) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
const auto &cloop = uvw::Loop::getDefault(); const auto &cloop = uvw::Loop::getDefault();

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/pipe.h> #include <uvw/pipe.h>
TEST(Pipe, ReadWrite) { TEST(Pipe, ReadWrite) {
#ifdef _MSC_VER #ifdef _MSC_VER
const std::string sockname{"\\\\.\\pipe\\test.sock"}; const std::string sockname{"\\\\.\\pipe\\test.sock"};
@ -14,8 +13,8 @@ TEST(Pipe, ReadWrite) {
auto client = loop->resource<uvw::PipeHandle>(); auto client = loop->resource<uvw::PipeHandle>();
server->on<uvw::ErrorEvent>([](const auto &, auto &) { FAIL(); }); server->on<uvw::ErrorEvent>([](const auto &, auto &) { FAIL(); });
client->on<uvw::ErrorEvent>([](const auto &, auto &) { client->on<uvw::ErrorEvent>([](const auto &, auto &) {
FAIL(); FAIL();
}); });
server->once<uvw::ListenEvent>([](const uvw::ListenEvent &, uvw::PipeHandle &handle) { server->once<uvw::ListenEvent>([](const uvw::ListenEvent &, uvw::PipeHandle &handle) {
@ -37,7 +36,7 @@ TEST(Pipe, ReadWrite) {
ASSERT_TRUE(handle.writable()); ASSERT_TRUE(handle.writable());
ASSERT_TRUE(handle.readable()); ASSERT_TRUE(handle.readable());
auto dataWrite = std::unique_ptr<char[]>(new char[2]{ 'x', 'y' }); auto dataWrite = std::unique_ptr<char[]>(new char[2]{'x', 'y'});
handle.write(std::move(dataWrite), 2); handle.write(std::move(dataWrite), 2);
}); });
@ -48,11 +47,10 @@ TEST(Pipe, ReadWrite) {
loop->run(); loop->run();
} }
TEST(Pipe, SockPeer) { TEST(Pipe, SockPeer) {
#ifdef _MSC_VER #ifdef _MSC_VER
const std::string sockname{"\\\\.\\pipe\\test.sock"}; const std::string sockname{"\\\\.\\pipe\\test.sock"};
const std::string peername{ "\\\\?\\pipe\\test.sock" }; const std::string peername{"\\\\?\\pipe\\test.sock"};
#else #else
const std::string sockname = std::string{TARGET_PIPE_DIR} + std::string{"/test.sock"}; const std::string sockname = std::string{TARGET_PIPE_DIR} + std::string{"/test.sock"};
const auto peername = sockname; const auto peername = sockname;
@ -91,7 +89,6 @@ TEST(Pipe, SockPeer) {
loop->run(); loop->run();
} }
TEST(Pipe, Shutdown) { TEST(Pipe, Shutdown) {
#ifdef _MSC_VER #ifdef _MSC_VER
const std::string sockname{"\\\\.\\pipe\\test.sock"}; const std::string sockname{"\\\\.\\pipe\\test.sock"};
@ -99,7 +96,7 @@ TEST(Pipe, Shutdown) {
const std::string sockname = std::string{TARGET_PIPE_DIR} + std::string{"/test.sock"}; const std::string sockname = std::string{TARGET_PIPE_DIR} + std::string{"/test.sock"};
#endif #endif
auto data = std::unique_ptr<char[]>(new char[3]{ 'a', 'b', 'c' }); auto data = std::unique_ptr<char[]>(new char[3]{'a', 'b', 'c'});
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto server = loop->resource<uvw::PipeHandle>(); auto server = loop->resource<uvw::PipeHandle>();

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/prepare.h> #include <uvw/prepare.h>
TEST(Prepare, StartAndStop) { TEST(Prepare, StartAndStop) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::PrepareHandle>(); auto handle = loop->resource<uvw::PrepareHandle>();
@ -28,7 +27,6 @@ TEST(Prepare, StartAndStop) {
ASSERT_TRUE(checkPrepareEvent); ASSERT_TRUE(checkPrepareEvent);
} }
TEST(Prepare, Fake) { TEST(Prepare, Fake) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::PrepareHandle>(); auto handle = loop->resource<uvw::PrepareHandle>();

View File

@ -2,7 +2,6 @@
#include <uvw/pipe.h> #include <uvw/pipe.h>
#include <uvw/process.h> #include <uvw/process.h>
TEST(Process, Pid) { TEST(Process, Pid) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::ProcessHandle>(); auto handle = loop->resource<uvw::ProcessHandle>();
@ -12,7 +11,6 @@ TEST(Process, Pid) {
loop->run(); loop->run();
} }
TEST(Process, Cwd) { TEST(Process, Cwd) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::ProcessHandle>(); auto handle = loop->resource<uvw::ProcessHandle>();
@ -22,7 +20,6 @@ TEST(Process, Cwd) {
loop->run(); loop->run();
} }
TEST(Process, StdIO) { TEST(Process, StdIO) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::ProcessHandle>(); auto handle = loop->resource<uvw::ProcessHandle>();

View File

@ -1,11 +1,10 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/work.h>
#include <uvw/request.hpp> #include <uvw/request.hpp>
#include <uvw/work.h>
TEST(Request, Functionalities) { TEST(Request, Functionalities) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto req = loop->resource<uvw::WorkReq>([](){}); auto req = loop->resource<uvw::WorkReq>([]() {});
ASSERT_NE(req->size(), decltype(req->size()){0}); ASSERT_NE(req->size(), decltype(req->size()){0});
ASSERT_FALSE(req->cancel()); ASSERT_FALSE(req->cancel());

View File

@ -4,9 +4,7 @@
#include <uvw/async.h> #include <uvw/async.h>
#include <uvw/request.hpp> #include <uvw/request.hpp>
struct Res: uvw::Resource<Res, int> {};
struct Res: uvw::Resource<Res, int> { };
TEST(Resource, Functionalities) { TEST(Resource, Functionalities) {
ASSERT_FALSE(std::is_copy_constructible<uvw::AsyncHandle>::value); ASSERT_FALSE(std::is_copy_constructible<uvw::AsyncHandle>::value);

View File

@ -2,7 +2,6 @@
#include <uvw/check.h> #include <uvw/check.h>
#include <uvw/signal.h> #include <uvw/signal.h>
TEST(Signal, Start) { TEST(Signal, Start) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::SignalHandle>(); auto handle = loop->resource<uvw::SignalHandle>();

View File

@ -1,13 +1,15 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/stream.h> #include <uvw/stream.h>
struct fake_stream_t {
struct fake_stream_t { void *data; }; void *data;
};
struct FakeStreamHandle: uvw::StreamHandle<FakeStreamHandle, fake_stream_t> { struct FakeStreamHandle: uvw::StreamHandle<FakeStreamHandle, fake_stream_t> {
using StreamHandle::StreamHandle; using StreamHandle::StreamHandle;
template<typename... Args> template<typename... Args>
bool init(Args&&...) { return true; } bool init(Args &&...) {
return true;
}
}; };

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/tcp.h> #include <uvw/tcp.h>
TEST(TCP, Functionalities) { TEST(TCP, Functionalities) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::TCPHandle>(); auto handle = loop->resource<uvw::TCPHandle>();
@ -14,7 +13,6 @@ TEST(TCP, Functionalities) {
loop->run(); loop->run();
} }
TEST(TCP, ReadWrite) { TEST(TCP, ReadWrite) {
const std::string address = std::string{"127.0.0.1"}; const std::string address = std::string{"127.0.0.1"};
const unsigned int port = 4242; const unsigned int port = 4242;
@ -45,9 +43,9 @@ TEST(TCP, ReadWrite) {
ASSERT_TRUE(handle.writable()); ASSERT_TRUE(handle.writable());
ASSERT_TRUE(handle.readable()); ASSERT_TRUE(handle.readable());
auto dataTryWrite = std::unique_ptr<char[]>(new char[1]{ 'a' }); auto dataTryWrite = std::unique_ptr<char[]>(new char[1]{'a'});
handle.tryWrite(std::move(dataTryWrite), 1); handle.tryWrite(std::move(dataTryWrite), 1);
auto dataWrite = std::unique_ptr<char[]>(new char[2]{ 'b', 'c' }); auto dataWrite = std::unique_ptr<char[]>(new char[2]{'b', 'c'});
handle.write(std::move(dataWrite), 2); handle.write(std::move(dataWrite), 2);
}); });
@ -58,7 +56,6 @@ TEST(TCP, ReadWrite) {
loop->run(); loop->run();
} }
TEST(TCP, SockPeer) { TEST(TCP, SockPeer) {
const std::string address = std::string{"127.0.0.1"}; const std::string address = std::string{"127.0.0.1"};
const unsigned int port = 4242; const unsigned int port = 4242;
@ -93,14 +90,13 @@ TEST(TCP, SockPeer) {
handle.close(); handle.close();
}); });
server->bind(uvw::Addr{ address, port }); server->bind(uvw::Addr{address, port});
server->listen(); server->listen();
client->connect(uvw::Addr{ address, port }); client->connect(uvw::Addr{address, port});
loop->run(); loop->run();
} }
TEST(TCP, Shutdown) { TEST(TCP, Shutdown) {
const std::string address = std::string{"127.0.0.1"}; const std::string address = std::string{"127.0.0.1"};
const unsigned int port = 4242; const unsigned int port = 4242;
@ -138,7 +134,6 @@ TEST(TCP, Shutdown) {
loop->run(); loop->run();
} }
TEST(TCP, WriteError) { TEST(TCP, WriteError) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::TCPHandle>(); auto handle = loop->resource<uvw::TCPHandle>();

View File

@ -4,12 +4,13 @@
TEST(Thread, Run) { TEST(Thread, Run) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto has_run = std::make_shared<bool>(); auto has_run = std::make_shared<bool>();
auto cb = [](std::shared_ptr<void> data) {
auto handle = loop->resource<uvw::Thread>([](std::shared_ptr<void> data) {
if(auto has_run = std::static_pointer_cast<bool>(data); has_run) { if(auto has_run = std::static_pointer_cast<bool>(data); has_run) {
*has_run = true; *has_run = true;
} }
}, has_run); };
auto handle = loop->resource<uvw::Thread>(cb, has_run);
ASSERT_TRUE(handle->run()); ASSERT_TRUE(handle->run());
ASSERT_TRUE(handle->join()); ASSERT_TRUE(handle->join());

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/timer.h> #include <uvw/timer.h>
TEST(Timer, StartAndStop) { TEST(Timer, StartAndStop) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handleNoRepeat = loop->resource<uvw::TimerHandle>(); auto handleNoRepeat = loop->resource<uvw::TimerHandle>();
@ -47,7 +46,6 @@ TEST(Timer, StartAndStop) {
ASSERT_TRUE(checkTimerRepeatEvent); ASSERT_TRUE(checkTimerRepeatEvent);
} }
TEST(Timer, Again) { TEST(Timer, Again) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::TimerHandle>(); auto handle = loop->resource<uvw::TimerHandle>();
@ -92,7 +90,6 @@ TEST(Timer, Again) {
ASSERT_TRUE(checkTimerEvent); ASSERT_TRUE(checkTimerEvent);
} }
TEST(Timer, Repeat) { TEST(Timer, Repeat) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::TimerHandle>(); auto handle = loop->resource<uvw::TimerHandle>();
@ -106,7 +103,6 @@ TEST(Timer, Repeat) {
loop->run(); loop->run();
} }
TEST(Timer, Fake) { TEST(Timer, Fake) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::TimerHandle>(); auto handle = loop->resource<uvw::TimerHandle>();
@ -123,16 +119,14 @@ TEST(Timer, Fake) {
loop->run(); loop->run();
} }
TEST(Timer, BaseHandleWalk) { TEST(Timer, BaseHandleWalk) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto timer = loop->resource<uvw::TimerHandle>(); auto timer = loop->resource<uvw::TimerHandle>();
timer->on<uvw::TimerEvent>([](const auto &, uvw::TimerHandle &handle) { timer->on<uvw::TimerEvent>([](const auto &, uvw::TimerHandle &handle) {
handle.loop().walk(uvw::Overloaded{ handle.loop().walk(uvw::Overloaded{
[](uvw::TimerHandle &h){ h.close(); }, [](uvw::TimerHandle &h) { h.close(); },
[](auto &&){} [](auto &&) {}});
});
}); });
timer->start(uvw::TimerHandle::Time{100}, uvw::TimerHandle::Time{100}); timer->start(uvw::TimerHandle::Time{100}, uvw::TimerHandle::Time{100});

View File

@ -2,7 +2,6 @@
#include <uvw/timer.h> #include <uvw/timer.h>
#include <uvw/tty.h> #include <uvw/tty.h>
TEST(TTY, Functionalities) { TEST(TTY, Functionalities) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::TTYHandle>(uvw::StdOUT, false); auto handle = loop->resource<uvw::TTYHandle>(uvw::StdOUT, false);
@ -10,13 +9,13 @@ TEST(TTY, Functionalities) {
bool checkWriteEvent = false; bool checkWriteEvent = false;
handle->on<uvw::WriteEvent>([&checkWriteEvent](const auto &, auto &hndl){ handle->on<uvw::WriteEvent>([&checkWriteEvent](const auto &, auto &hndl) {
ASSERT_FALSE(checkWriteEvent); ASSERT_FALSE(checkWriteEvent);
checkWriteEvent = true; checkWriteEvent = true;
hndl.close(); hndl.close();
}); });
timer->on<uvw::TimerEvent>([handle](const auto &, auto &hndl){ timer->on<uvw::TimerEvent>([handle](const auto &, auto &hndl) {
auto data = std::make_unique<char[]>('*'); auto data = std::make_unique<char[]>('*');
handle->write(std::move(data), 1); handle->write(std::move(data), 1);
hndl.close(); hndl.close();

View File

@ -1,7 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw/udp.h> #include <uvw/udp.h>
TEST(UDP, Functionalities) { TEST(UDP, Functionalities) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::UDPHandle>(); auto handle = loop->resource<uvw::UDPHandle>();
@ -20,7 +19,6 @@ TEST(UDP, Functionalities) {
loop->run(); loop->run();
} }
TEST(UDP, BindRecvStop) { TEST(UDP, BindRecvStop) {
const std::string address = std::string{"127.0.0.1"}; const std::string address = std::string{"127.0.0.1"};
const unsigned int port = 4242; const unsigned int port = 4242;
@ -38,7 +36,6 @@ TEST(UDP, BindRecvStop) {
loop->run(); loop->run();
} }
TEST(UDP, ReadTrySend) { TEST(UDP, ReadTrySend) {
const std::string address = std::string{"127.0.0.1"}; const std::string address = std::string{"127.0.0.1"};
const unsigned int port = 4242; const unsigned int port = 4242;
@ -55,21 +52,20 @@ TEST(UDP, ReadTrySend) {
handle.close(); handle.close();
}); });
server->bind(uvw::Addr{ address, port }); server->bind(uvw::Addr{address, port});
server->recv(); server->recv();
auto dataTrySend = std::unique_ptr<char[]>(new char[1]{ 'a' }); auto dataTrySend = std::unique_ptr<char[]>(new char[1]{'a'});
client->trySend(uvw::Addr{ address, port }, dataTrySend.get(), 1); client->trySend(uvw::Addr{address, port}, dataTrySend.get(), 1);
client->trySend(address, port, nullptr, 0); client->trySend(address, port, nullptr, 0);
client->trySend(uvw::Addr{ address, port }, std::move(dataTrySend), 1); client->trySend(uvw::Addr{address, port}, std::move(dataTrySend), 1);
client->trySend(address, port, std::unique_ptr<char[]>{}, 0); client->trySend(address, port, std::unique_ptr<char[]>{}, 0);
loop->run(); loop->run();
} }
TEST(UDP, ReadSend) { TEST(UDP, ReadSend) {
const std::string address = std::string{"127.0.0.1"}; const std::string address = std::string{"127.0.0.1"};
const unsigned int port = 4242; const unsigned int port = 4242;
@ -92,18 +88,17 @@ TEST(UDP, ReadSend) {
server->bind(address, port); server->bind(address, port);
server->recv(); server->recv();
auto dataSend = std::unique_ptr<char[]>(new char[2]{ 'b', 'c' }); auto dataSend = std::unique_ptr<char[]>(new char[2]{'b', 'c'});
client->send(uvw::Addr{ address , port }, dataSend.get(), 2); client->send(uvw::Addr{address, port}, dataSend.get(), 2);
client->send(address, port, nullptr, 0); client->send(address, port, nullptr, 0);
client->send(uvw::Addr{ address , port }, std::move(dataSend), 2); client->send(uvw::Addr{address, port}, std::move(dataSend), 2);
client->send(address, port, std::unique_ptr<char[]>{}, 0); client->send(address, port, std::unique_ptr<char[]>{}, 0);
loop->run(); loop->run();
} }
TEST(UDP, Sock) { TEST(UDP, Sock) {
const std::string address = std::string{"127.0.0.1"}; const std::string address = std::string{"127.0.0.1"};
const unsigned int port = 4242; const unsigned int port = 4242;

View File

@ -2,7 +2,6 @@
#include <uvw/async.h> #include <uvw/async.h>
#include <uvw/underlying_type.hpp> #include <uvw/underlying_type.hpp>
TEST(UnderlyingType, Functionalities) { TEST(UnderlyingType, Functionalities) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = uvw::AsyncHandle::create(loop); auto handle = uvw::AsyncHandle::create(loop);

View File

@ -1,14 +1,18 @@
#include <memory>
#include <cstdlib> #include <cstdlib>
#include <memory>
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include <uvw.hpp> #include <uvw.hpp>
template<typename T> template<typename T>
struct tag { using type = T; }; struct tag { using type = T; };
TEST(Util, UnscopedFlags) { TEST(Util, UnscopedFlags) {
enum class UnscopedEnum { FOO = 1, BAR = 2, BAZ = 4, QUUX = 8 }; enum class UnscopedEnum {
FOO = 1,
BAR = 2,
BAZ = 4,
QUUX = 8
};
uvw::Flags<UnscopedEnum> flags{}; uvw::Flags<UnscopedEnum> flags{};
@ -38,9 +42,13 @@ TEST(Util, UnscopedFlags) {
ASSERT_TRUE(flags & uvw::Flags<UnscopedEnum>::from<UnscopedEnum::QUUX>()); ASSERT_TRUE(flags & uvw::Flags<UnscopedEnum>::from<UnscopedEnum::QUUX>());
} }
TEST(Util, ScopedFlags) { TEST(Util, ScopedFlags) {
enum class ScopedEnum { FOO = 1, BAR = 2, BAZ = 4, QUUX = 8 }; enum class ScopedEnum {
FOO = 1,
BAR = 2,
BAZ = 4,
QUUX = 8
};
uvw::Flags<ScopedEnum> flags{}; uvw::Flags<ScopedEnum> flags{};
@ -70,7 +78,6 @@ TEST(Util, ScopedFlags) {
ASSERT_TRUE(flags & uvw::Flags<ScopedEnum>::from<ScopedEnum::QUUX>()); ASSERT_TRUE(flags & uvw::Flags<ScopedEnum>::from<ScopedEnum::QUUX>());
} }
TEST(Util, Utilities) { TEST(Util, Utilities) {
ASSERT_EQ(uvw::PidType{}, uvw::PidType{}); ASSERT_EQ(uvw::PidType{}, uvw::PidType{});
@ -141,8 +148,7 @@ TEST(Util, Utilities) {
[](size_t size) { return malloc(size); }, [](size_t size) { return malloc(size); },
[](void *ptr, size_t size) { return realloc(ptr, size); }, [](void *ptr, size_t size) { return realloc(ptr, size); },
[](size_t num, size_t size) { return calloc(num, size); }, [](size_t num, size_t size) { return calloc(num, size); },
[](void *ptr) { return free(ptr); } [](void *ptr) { return free(ptr); }));
));
ASSERT_NO_THROW(uvw::Utilities::loadAverage()); ASSERT_NO_THROW(uvw::Utilities::loadAverage());
ASSERT_NE(uvw::Utilities::totalMemory(), decltype(uvw::Utilities::totalMemory()){0}); ASSERT_NE(uvw::Utilities::totalMemory(), decltype(uvw::Utilities::totalMemory()){0});
@ -153,7 +159,7 @@ TEST(Util, Utilities) {
ASSERT_FALSE(uvw::Utilities::cwd().empty()); ASSERT_FALSE(uvw::Utilities::cwd().empty());
ASSERT_TRUE(uvw::Utilities::chdir(uvw::Utilities::cwd())); ASSERT_TRUE(uvw::Utilities::chdir(uvw::Utilities::cwd()));
std::unique_ptr<char[], void(*)(void *)> fake{new char[1], [](void *ptr) { delete[] static_cast<char *>(ptr); }}; std::unique_ptr<char[], void (*)(void *)> fake{new char[1], [](void *ptr) { delete[] static_cast<char *>(ptr); }};
char *argv = fake.get(); char *argv = fake.get();
argv[0] = '\0'; argv[0] = '\0';

View File

@ -3,7 +3,6 @@
#include <uvw/timer.h> #include <uvw/timer.h>
#include <uvw/work.h> #include <uvw/work.h>
TEST(Work, RunTask) { TEST(Work, RunTask) {
auto loop = uvw::Loop::getDefault(); auto loop = uvw::Loop::getDefault();
auto handle = loop->resource<uvw::CheckHandle>(); auto handle = loop->resource<uvw::CheckHandle>();