SObjectizer: it's all about in-process message dispatching!


Travis CI Build Status

NOTE! The further development of SObjectizer is moved to GitHub.

NOTE! This is an experimental SObjectizer repository mirror.

What is SObjectizer?

SObjectizer is one of a few cross-platform and OpenSource "actor frameworks" for C++. But SObjectizer supports not only Actor Model, but also Publish-Subscribe Model and CSP-like channels. The goal of SObjectizer is significant simplification of development of concurrent and multithreaded applications in C++.

SObjectizer allows the creation of a concurrent app as a set of agent-objects which interact with each other through asynchronous messages. It handles message dispatching and provides a working context for message processing. And allows to tune those things by supplying various ready-to-use dispatchers.

What distinguishes SObjectizer?

Maturity. SObjectizer is based on ideas that have been put forward in 1995-2000. And SObjectizer itself is being developed since 2002. SObjectizer-5 is continuously evolved since 2010.

Stability. From the very beginning SObjectizer was used for business-critical applications, and some of them are still being used in production. Breaking changes in SObjectizer are rare and we approach to them very carefully.

Cross-platform. SObjectizer runs on Windows, Linux, FreeBSD, macOS and Android.

Easy-to-use. SObjectizer provides easy to understand and easy to use API with a lot of examples in the SObjectizer's distributive and a plenty of information in the project's Wiki.

Free. SObjectizer is distributed under BSD-3-CLAUSE license, so it can be used in development of proprietary commercial software for free.

Show me the code!

HelloWorld example

This is a classical example "Hello, World" expressed by using SObjectizer's agents:

#include <so_5/all.hpp>

class hello_actor final : public so_5::agent_t {
   using so_5::agent_t::agent_t;

   void so_evt_start() override {
      std::cout << "Hello, World!" << std::endl;
      // Finish work of example.

int main() {
   // Launch SObjectizer.
   so_5::launch([](so_5::environment_t & env) {
         // Add a hello_actor instance in a new cooperation.
         env.introduce_coop([](so_5::coop_t & coop) {

   return 0;

Ping-Pong example

Let's look at more interesting example with two agents and message exchange between them. It is another famous example for actor frameworks, "Ping-Pong":

#include <so_5/all.hpp>

struct ping {
   int counter_;

struct pong {
   int counter_;

class pinger final : public so_5::agent_t {
   so_5::mbox_t ponger_;

   void on_pong(mhood_t<pong> cmd) {
      if(cmd->counter_ > 0)
         so_5::send<ping>(ponger_, cmd->counter_ - 1);

   pinger(context_t ctx) : so_5::agent_t{std::move(ctx)} {}

   void set_ponger(const so_5::mbox_t mbox) { ponger_ = mbox; }

   void so_define_agent() override {
      so_subscribe_self().event( &pinger::on_pong );

   void so_evt_start() override {
      so_5::send<ping>(ponger_, 1000);

class ponger final : public so_5::agent_t {
   const so_5::mbox_t pinger_;
   int pings_received_{};

   ponger(context_t ctx, so_5::mbox_t pinger)
      :  so_5::agent_t{std::move(ctx)}
      ,  pinger_{std::move(pinger)}

   void so_define_agent() override {
         [this](mhood_t<ping> cmd) {
            so_5::send<pong>(pinger_, cmd->counter_);

   void so_evt_finish() override {
      std::cout << "pings received: " << pings_received_ << std::endl;

int main() {
   so_5::launch([](so_5::environment_t & env) {
         env.introduce_coop([](so_5::coop_t & coop) {
               auto pinger_actor = coop.make_agent<pinger>();
               auto ponger_actor = coop.make_agent<ponger>(


   return 0;

All agents in the code above are working on the same work thread. How to bind them to different work threads?

It is very simple. Just use an appropriate dispatcher:

int main() {
   so_5::launch([](so_5::environment_t & env) {
            [](so_5::coop_t & coop) {
               auto pinger_actor = coop.make_agent<pinger>();
               auto ponger_actor = coop.make_agent<ponger>(


   return 0;

Pub/Sub example

SObjectizer supports Pub/Sub model via multi-producer/multi-consumer message boxes. A message sent to that message box will be received by all subscribers of that message type:

#include <so_5/all.hpp>

using namespace std::literals;

struct acquired_value {
   std::chrono::steady_clock::time_point acquired_at_;
   int value_;

class producer final : public so_5::agent_t {
   const so_5::mbox_t board_;
   so_5::timer_id_t timer_;
   int counter_{};

   struct acquisition_time final : public so_5::signal_t {};

   void on_timer(mhood_t<acquisition_time>) {
      // Publish the next value for all consumers.
            board_, std::chrono::steady_clock::now(), ++counter_);

   producer(context_t ctx, so_5::mbox_t board)
      :  so_5::agent_t{std::move(ctx)}
      ,  board_{std::move(board)}

   void so_define_agent() override {

   void so_evt_start() override {
      // Agent will periodically recive acquisition_time signal
      // without initial delay and with period of 750ms.
      timer_ = so_5::send_periodic<acquisition_time>(*this, 0ms, 750ms);

class consumer final : public so_5::agent_t {
   const so_5::mbox_t board_;
   const std::string name_;

   void on_value(mhood_t<acquired_value> cmd) {
      std::cout << name_ << ": " << cmd->value_ << std::endl;

   consumer(context_t ctx, so_5::mbox_t board, std::string name)
      :  so_5::agent_t{std::move(ctx)}
      ,  board_{std::move(board)}
      ,  name_{std::move(name)}

   void so_define_agent() override {

int main() {
   so_5::launch([](so_5::environment_t & env) {
         auto board = env.create_mbox();
         env.introduce_coop([board](so_5::coop_t & coop) {
               coop.make_agent<consumer>(board, "first"s);
               coop.make_agent<consumer>(board, "second"s);


   return 0;

BlinkingLed example

All agents in SObjectizer are finite-state machines. Almost all functionality of hierarchical finite-states machines (HSM) are supported: child states and handlers inheritance, on_enter/on_exit handlers, state timeouts, deep- and shallow state history, except orthogonal states.

This is a very simple example that demonstrates an agent that is HSM:

#include <so_5/all.hpp>

using namespace std::literals;

class blinking_led final : public so_5::agent_t {
   state_t off{ this }, blinking{ this },
      blink_on{ initial_substate_of{ blinking } },
      blink_off{ substate_of{ blinking } };

public :
   struct turn_on_off : public so_5::signal_t {};

   blinking_led(context_t ctx) : so_5::agent_t{std::move(ctx)} {
      this >>= off;



         .on_enter([]{ std::cout << "ON" << std::endl; })
         .on_exit([]{ std::cout << "off" << std::endl; })
         .time_limit(1250ms, blink_off);

         .time_limit(750ms, blink_on);

int main()
   so_5::launch([](so_5::environment_t & env) {
      so_5::mbox_t m;
      env.introduce_coop([&](so_5::coop_t & coop) {
            auto led = coop.make_agent< blinking_led >();
            m = led->so_direct_mbox();

      const auto pause = [](auto duration) {

      std::cout << "Turn blinking on for 10s" << std::endl;

      std::cout << "Turn blinking off for 5s" << std::endl;

      std::cout << "Turn blinking on for 5s" << std::endl;

      std::cout << "Stopping..." << std::endl;
   } );

   return 0;

CSP-like Ping-Pong example

SObjectizer allows to write concurrent applications even without agents inside. Only plain threads and CSP-like channels can be used.

This is plain-thread implementation of Ping-Pong example (please note that main() is not exception-safe):

#include <so_5/all.hpp>

struct ping {
   int counter_;

struct pong {
   int counter_;

void pinger_proc(so_5::mchain_t self_ch, so_5::mchain_t ping_ch) {
   so_5::send<ping>(ping_ch, 1000);

   // Read all message until channel will be closed.
   so_5::receive( so_5::from(self_ch),
      [&](so_5::mhood_t<pong> cmd) {
         if(cmd->counter_ > 0)
            so_5::send<ping>(ping_ch, cmd->counter_ - 1);
         else {
            // Channels have to be closed to break `receive` calls.

void ponger_proc(so_5::mchain_t self_ch, so_5::mchain_t pong_ch) {
   int pings_received{};

   // Read all message until channel will be closed.
   so_5::receive( so_5::from(self_ch),
      [&](so_5::mhood_t<ping> cmd) {
         so_5::send<pong>(pong_ch, cmd->counter_);

   std::cout << "pings received: " << pings_received << std::endl;

int main() {
   so_5::wrapped_env_t sobj;

   auto pinger_ch = so_5::create_mchain(sobj);
   auto ponger_ch = so_5::create_mchain(sobj);

   std::thread pinger{pinger_proc, pinger_ch, ponger_ch};
   std::thread ponger{ponger_proc, ponger_ch, pinger_ch};


   return 0;

Want to know more?

More information about SObjectizer can be found in the corresponding section of the project's Wiki


SObjectizer is an in-process message dispatching framework. It doesn't support distributed applications just out of box. But external tools and libraries can be used in that case. Please take a look at our mosquitto_transport experiment.

Obtaining and building

SObjectizer can be downloaded from SourceForge or this repository can be cloned.

There are two ways for building SObjectizer. The first one by using Mxx_ru tool. The second one by using CMake.

NOTE. Since v. there is a support of Android platform. Building for Android is possible by CMake only. See the corresponding section below.

SObjectizer can also be installed and used via vcpkg and Conan dependency managers. See the appropriate sections below.

Building via Mxx_ru

NOTE. This is a standard way for building SObjectizer. This way is used in SObjectizer development process.

To build SObjectizer it is necessary to use Ruby language and Mxx_ru tool. Install Ruby and then install Mxx_ru via RubyGems command:

gem install Mxx_ru

If you already have Mxx_ru installed please update to at least version 1.6.11:

gem update Mxx_ru

SObjectizer can be obtained from Subversion repository on SourceForge:

svn export so-5.5.24

Or this repository can be cloned:

git clone so-5.5.24

To build SObjectizer:

cd so-5.5.24/dev
ruby build.rb

Static and shared library for SObjectizer will be built. Libraries will be placed into target/release subdirectory.

If you want to build just shared library:

cd so-5.5.24/dev
ruby so_5/prj.rb

Or if you want to build just static library:

cd so-5.5.24/dev
ruby so_5/prj_s.rb

To build SObjectizer with all tests and samples:

cd so-5.5.24/dev
ruby build_all.rb

Please note that under FreeBSD it could be necessary to define LD_LIBRARY_PATH environment variable. And the actual build command sequence under FreeBSD could be as follows:

cd so-5.5.24/dev
export LD_LIBRARY_PATH=target/release
ruby build_all.rb

To build html-format documentation for SObjectizer the Doxygen tool is necessary. If it is installed then:

cd so-5.5.24/doxygen

Generated html-files will be located in so-5.5.24/dev/doc/html.

NOTE. If you do not specify MXX_RU_CPP_TOOLSET by youself then Mxx_ru will try to detect your C++ toolset automatically. If you want to use C++ compiler which is not default in your system please define MXX_RU_CPP_TOOLSET environment variable manually. It could look like:

export MXX_RU_CPP_TOOLSET="clang_linux compiler_name=clang++-3.5 linker_name=clang++-3.5"

More information about tuning Mxx_ru for your needs you can find in the corresponding documentation.

Building via CMake

NOTE. This way of building is not used by SObjectizer developers. But CMake-related files are in actual state, they maintained by SObjectizer Team and can be used for building SObjectizer, its samples and tests.

NOTE. It is better to have a rather new version of CMake. The oldest CMake version which has been tested is 3.2. The version 3.8 or newer is prefered.

To build SObjectizer via CMake it is necessary to have CMake and some knowledge of how to use it. The following action is just a demonstration. For more detailed info about cmake build system for SObjectizer see dev/cmake/CmakeQuickHowto.txt

To get and build SObjectizer under Linux/FreeBSD in command line run:

svn export so-5.5.24
cd so-5.5.24
mkdir cmake_build
cd cmake_build
cmake --build . --config Release
cmake --build . --config Release --target install

Those commands will create all necessary Makefile, then build SObjectizer. If it necessary to build examples and tests too, use


When 'make install' finished './target' will contain two subfolders './bin' with samples and './lib' with shared

CMake build system currently supports this options:

  • SOBJECTIZER_BUILD_STATIC. Enable building SObjectizer as a static library [default: ON]
  • SOBJECTIZER_BUILD_SHARED. Enable building SObjectizer as a shared library [default: ON]
  • BUILD_ALL. Enable building examples and tests [default: OFF]
  • BUILD_EXAMPLES. Enable building examples [default: OFF]
  • BUILD_TESTS. Enable building tests [default: OFF]


To build SObjectizer under Windows by MS Visual Studio 2013 from command line:

cd so-5.5.24
mkdir cmake_build
cd cmake_build
cmake -DCMAKE_INSTALL_PREFIX=target -DCMAKE_BUILD_TYPE=Release -G "Visual Studio 14 2015" ../dev
cmake --build . --config Release
cmake --build . --config Release --target install

If it necessary to build examples too, use BUILD_ALL in cmake invocation:

cmake -DCMAKE_INSTALL_PREFIX=target -DCMAKE_BUILD_TYPE=Release -DBUILD_ALL=ON -G "Visual Studio 14 2015" ../dev

Since v.5.5.24 SObjectizer provides sobjectizer-config.cmake files. These files are automatically installed into /lib/cmake/sobjectizer subfolder. It allows to use SObjectizer via CMake's find_package command.

Building for Android

Building for Android is possible via a rather fresh Android NDK or CrystaX NDK.

Building with Android NDK

You need Android SDK and Android NDK installed in your system. As well as an appropriate version of CMake. You have also need properly set environment variables ANDROID_HOME, ANDROID_NDK. Then you can issue the following commands:

svn export so-5.5.24
cd so-5.5.24
mkdir cmake_build
cd cmake_build
     -DCMAKE_TOOLCHAIN_FILE=${ANDROID_NDK}/build/cmake/android.toolchain.cmake \
     -G Ninja \
     -DANDROID_ABI=arm64-v8a \
cmake --build . --config=Release
cmake --build . --config=Release --target install

Building with CrystaX NDK

You need CrystaX NDK v.10.4.0 or higher already installed in your system. CMake is used for building SObjectizer:

svn export so-5.5.24
cd so-5.5.24
mkdir cmake_build
cd cmake_build
export NDK=/path/to/the/crystax-ndk
cmake -DBUILD_ALL -DCMAKE_INSTALL_PREFIX=result -DCMAKE_TOOLCHAIN_FILE=$NDK/cmake/toolchain.cmake -DANDROID_ABI=arm64-v8a ../dev
make test
make install

Using C++ Dependency Managers

Using via vcpkg

To use SObjectizer via vcpkg it is necessary to do the following steps.

Install sobjectizer package:

vcpkg install sobjectizer

Add the following lines into your CMakeLists.txt file:

find_package(sobjectizer CONFIG REQUIRED)
target_link_libraries(your_target sobjectizer::SharedLib) # or sobjectizer::StaticLib

Using via Conan

Installing SObjectizer And Adding It To conanfile.txt

To use SObjectizer via Conan it is necessary to do the following steps:

Add the corresponding remote to your conan:

conan remote add stiffstream

Add SObjectizer to conanfile.txt of your project:

sobjectizer/[email protected]/testing

It also may be necessary to specify shared option for SObjectizer. For example, for build SObjectizer as a static library:


Install dependencies for your project:

conan install SOME_PATH --build=missing

Adding SObjectizer To Your CMakeLists.txt

Please note that SObjectizer should be added to your CMakeLists.txt via find_package command:


find_package(sobjectizer CONFIG REQUIRED)
target_link_libraries(your_target sobjectizer::SharedLib) # Or sobjectizer::StaticLib


SObjectizer is distributed under 3-clause BSD license. For license information please see LICENSE file.

  • unix visibility control missing

    unix visibility control missing

    Looking at h/declspec.hpp it seems visibility control is only implemented for Windows. I use this:

    #if FLX_WIN32
      #if defined(FLX_STATIC_LINK)
        #define FLX_EXPORT
        #define FLX_IMPORT
        #define FLX_EXPORT __declspec(dllexport)
        #define FLX_IMPORT __declspec(dllimport)
      // All modules on Unix are compiled with -fvisibility=hidden
      // All API symbols get visibility default
      // whether or not we're static linking or dynamic linking (with -fPIC)
      #define FLX_EXPORT __attribute__((visibility("default"))) 
      #define FLX_IMPORT __attribute__((visibility("default"))) 

    In particular note, you should compile with -fvisibility=hidden, and set the same visibility macros as shown for Unix as above. For you, these are SO_5_TYPE and SO_5_FUNC. You may need to fix your build system to ensure the default visibility is hidden.

    As a comment, hidden visibility is not currently possible with static libraries. However shared libraries should always use two level namespace control. C++ Modules_TS may improve visibility control for static linkage. Its not clear if it will get rid of the need for macros like those above.

    opened by skaller 33
  • Unstable test _unit.test.layer.extra_layer_query

    Unstable test _unit.test.layer.extra_layer_query

    .../Sources/SObjectizer/dev/test/so_5/layer/extra_layer_query/main.cpp(91): unit test error: comparison failed: 'so_env.query_layer_noexcept< test_layer_t< 1 > >() == tl1' where [ so_env.query_layer_noexcept< test_layer_t< 1 > >() is 0, tl1 is 0x9901c0 ] Unit test 'check_1_3_exist' failed

    Я пока еще не пытался углубляться, но срабатывает он не всегда.

    opened by DronMDF 21
  • so Hello World fails to compile with no member named 'in_place' in namespace 'std' error

    so Hello World fails to compile with no member named 'in_place' in namespace 'std' error

    I pulled SO and built it with cmake. I use the following cmake file for my project

    cmake_minimum_required(VERSION 3.13)
    set(DEP_DIR "/home/my_name/il_dependencies/")
    set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -pthread")
    SET (sobjectizer_DIR "${DEP_DIR}lib/cmake/sobjectizer" )
    find_package( sobjectizer REQUIRED )
    target_include_directories( experiment_1 BEFORE PRIVATE "${DEP_DIR}/include" )
    target_link_libraries( experiment_1 PRIVATE  sobjectizer::SharedLib )

    The code in main is very simple, not even launching environment

    #include <iostream>
    #include <so_5/all.hpp>
    int main() {
      std::cout << "Works...\n" ;

    When I try to build I get long list of errors. First error message being:

    In file included from /home/boris/projects/thesis/so5_experiments/experiment-1/m
    In file included from /home/boris/il_dependencies/include/so_5/all.hpp:15:
    In file included from /home/boris/il_dependencies/include/so_5/rt/h/rt.hpp:13:
    In file included from /home/boris/il_dependencies/include/so_5/rt/h/agent.hpp:30
    In file included from /home/boris/il_dependencies/include/so_5/rt/h/agent_contex
    In file included from /home/boris/il_dependencies/include/so_5/rt/h/agent_tuning
    In file included from /home/boris/il_dependencies/include/so_5/rt/h/message_limi
    In file included from /home/boris/il_dependencies/include/so_5/rt/h/enveloped_ms
    In file included from /home/boris/il_dependencies/include/so_5/h/optional.hpp:15
    .hpp:319:12: error:
          no member named 'in_place' in namespace 'std'
    using std::in_place;

    I use clang 6 to compile and it support C++17. So it should support std::in_place but code also fails:

    #include <iostream>
    #include <utility>
    using std::in_place;
    int main() {
      std::cout << "Works...\n" ;

    Might be that there is something wrong with my environment

    opened by atraastrum 18
  • [en] how to integrate extenral loop in SO?

    [en] how to integrate extenral loop in SO?

    I'm not sure that I do the right integration of a loop. Basically I do:

    void my_actor::so_evt_start() {
        timer = so_5::send_periodic<message::wakeup>(*this, 0ms, 10ms);
    void my_actor:::on_wakeup() {
        auto has_events = external_loop->Pending();
        while(has_events) {
            external_loop->DispatchTimeout(10); // can be just non-blocking external_loop->DispatchTimeout(()
            has_events = external_loop->Pending();
        timer = so_5::send_periodic<message::wakeup>(*this, 10ms, 0ms);

    in other words, it blocks SO-dispatcher for 10ms to process events, and then does 10ms pause, and repeats.

    I'm a bit worry, that on idle it still consumes a lot of CPU (14%). If the wake-up event is send every 100ms there is no CPU consumption, but by the price of loosing some interactivity.

    May be there are some other ways? i.e. not guessing the values between 100ms and 10ms ?

    PS. The external loop I'm trying to integrate is wx-widget ( )

    PPS. I'm aware, that it is possible to do that in "wx-widgets" specific way, i.e. launch an dedicated thread, and deliver events in framework-specific way ( i.e. ). But I'd like to use nice sobjectizer as messaging framework.

    opened by basiliscos 7
  • [en] `so_5::message_t` is optional in some places, and mandatory in the others?

    [en] `so_5::message_t` is optional in some places, and mandatory in the others?


    If I define message user-defined struct, i.e.

    struct timeout_initialize {
        actor_t actor;
        so_5::mbox_t mbox;
        timeout_initialize(actor_t actor_, const so_5::mbox_t& mbox_): actor{actor_}, mbox{mbox_}{}

    it is still possible to send it via so_5::send<timeout_initialize>(...). However, when I try to send it via schedule_timer

                    std::make_unique< message::timeout_initialize >(, m.mbox ),

    the compiler errors with :

    ../so_5/rt/h/message.hpp:655:18: error: static assertion failed: expected a type derived from the message_t
       static_assert( is_classical_message< Msg >::value,

    If the timeout_initialize inherits from so_5::message_t, the error message disappears and everything looks fine.

    However, it's a bit weird API-interface: messages, which I don't need send via schedule_timer can be user-defined types, but if they are delivered via schedule_timer, they have to be derived from so_5::message_t .

    opened by basiliscos 4
  • Tabs


    Please stop using tabs in source code. Tabs are hang-over from the 1960s when typists saved keystrokes and improved accuracy by use of the Tab key and tab stops. They were also used by computers to control IBM Selectric typewriters to aid printing forms. This was important because one never knew exactly where the printed form would end up on the paper until it arrived from the printer.

    All modern editors allow programming the tab key to insert spaces, assisting in alignment and assuring all clients get the same layout.

    Tab characters are a disaster in source code. The code becomes unreadable on some devices such as my console. They're also indistinguishable from spaces in my editor. Error diagnostics cannot correctly refer to column numbers since the tab stops are viewing-device dependent.

    I use 2 character indents, which is the best format for books (which have small line widths), however 4 is acceptable. 3 is silly. 8 is way too much. 8 is the default on my console. My editor is fixed to 2. Invariant layout is incompatible with use of tabs.

    opened by skaller 4
  • [en] so_5::deregister_coop_on_exception & exception requirements

    [en] so_5::deregister_coop_on_exception & exception requirements


    It is setup to handle exceptions via coop.set_exception_reaction(so_5::deregister_coop_on_exception);

    When an child agent throws an arbitrary exception, not derived from std::except, it just terminates:

    throw ("boom");
    terminate called after throwing an instance of 'char const*'
    [1]    18965 abort      ./syncspirit --log_level debug --config_file ../syncspirit.conf

    However, when std::exception is thrown:

    throw std::runtime_error("boom");

    Then it is catch and behaves correctly

    SObjectizer event exception caught: boom; cooperation: 'logger'
    [2019-03-09 11:47:51.577 TID:140664060745472] Cooperation 'logger' will be deregistered due to unhandled exception 'boom' (/home/b/development/cpp/sync-spirit/lib/so-5-5/dev/so_5/rt/impl/process_unhandled_exception.cpp:189)

    I think it is too strong assumption, that 3rd-party libraries will always throw something derived from std::except

    PS. It is also terminates on throw new std::runtime_error("boom"). Of course, this is buggy/discouraged to throw new exception, but that's what I met in the others' code.

    opened by basiliscos 3
  • [ru] Приоритеты для сообщений в версии 5.5.5

    [ru] Приоритеты для сообщений в версии 5.5.5

    В чем смысл данного обсуждения?

    Данная тема преследует две цели:

    1. Собрать мнения и/или информацию о том, нужны ли приоритеты, есть ли ситуации, где без приоритетов либо не обойтись вообще, либо же это будет обходиться очень дорого. Или же выяснить, что в озвученных ситуациях есть хорошие решения и без приоритетов.
    2. Если в процессе обсуждения выяснится, что в SO-5 желательно иметь поддержку приоритетов, то определить, каким образом это могло бы выглядеть (хотя бы в первом приближении).

    Нужны ли приоритеты?

    Приоритеты событий поддерживались в SObjectizer-4. Но за все время активного использования SO-4 приоритеты были задействованы всего лишь считанные разы. При этом за поддержку приоритетов приходилось платить более сложной реализацией очередей заявок и невозможностью проведения некоторых оптимизаций при обслуживании очередей.

    Поэтому SObjectizer-5 сразу создавали без поддержки приоритетов. Это серьезно упростило реализацию SO-5, а так же позволило существенно повысить скорость сохранения/извлечения заявок при диспетчеризации сообщений. Так же за время практического использования SO-5 (т.е. где-то с 2011-го года) не было ситуаций, где необходимость поддержки приоритетов была бы критически важна.

    Однако, по мере развития, совершенствования и наполнения SO-5 новыми, полезными для разработчика возможностями, возникает вопрос: “Не пора ли вернуться к теме приоритетов?”

    Примеры ситуаций для приоритетов

    Ниже описаны несколько ситуаций, в которых приоритеты были бы полезны и позволили бы получить более простое решение, нежели без использования оных. Если кто-то может привести пример еще какой-нибудь ситуации (или же вариант решения без приоритетов), то просьба оставить описание этого примера в комментариях.

    Контроль перегрузки агента

    В версии 5.5.4 был добавлен механизм лимитов для сообщений, который позволяет реализовывать простые схемы контроля перегрузки агентов. Но этого механизма недостаточно для того, чтобы делать более сложные и удобные схемы. Например, при заполнении очереди заявок свыше некоторого значения агент должен сменить свое состояние с нормального на перегруженное и перейти к другому режиму обработки сообщений.

    Т.к. только агент может сменить свое состояние, то для воплощения такой схемы контроля за перегрузкой нужно отослать сообщение агенту и дать возможность агенту обработать это сообщение раньше всех остальных сообщений, которые уже стоят у него в очереди. А это ни что иное, как приоритетная обработка сообщений. Но т.к. в SO-5 поддержки приоритетов нет, то такую схему в существующем SObjectizer реализовать не представляется возможным.

    Распределение работы между вокерами

    Простая ситуация: есть агент-менеджер, который получает сообщения-заявки и несколько подчиненных ему агентов-воркеров. Менеджер ведет список свободных воркеров. Когда менеджер получает очередную заявку, он изымает из списка свободного воркера и отдает заявку этому воркеру. Если свободных воркеров нет, то менеджер сразу отказывается от обработки заявки и отсылает отрицательный ответ.

    Агенты-воркеры информируют менеджера о том, что они освободились, простыми сообщениями. Когда менеджер получает сообщение о том, что воркер свободен, он сохраняет воркера в список свободных воркеров.

    Проблема в том, что в такой простой реализации все сообщения к менеджеру будут выстраиваться в простой последовательный список. Например, в какой-то момент времени этот список может выглядеть так:


    Т.е. три новые заявки, за которыми идут два сообщения об освободившихся воркерах.

    Допустим, менеджер обрабатывает сообщения последовательно в ситуации, когда список свободных воркеров пуст. Это означает, что сначала менеджер выбросит три новые заявки, т.к. их некому отдать, а потом поместит описания двух воркеров в список свободных. Т.е. никакой полезной работы проделано не будет.

    Если бы у сообщений free_worker были бы более высокие приоритеты, то очередь заявок к менеджеру имела бы вид:


    Ее последовательная обработка привела бы к тому, что сначала в список свободных воркеров была бы сохранена информация о двух свободных агентах. После чего им были бы переданы две заявки. А отброшена была бы только третья.

    Дополнение. У этой задачи есть решение без использования приоритетов. В агенте-менеджере нужно было бы хранить список отложенных заявок, в который можно помещать заявки, если для них в данный момент нет свободных воркеров. И извлекать заявки из списка при появлении воркера. Но такое решение требует больше работы от программиста: нужно будет не только поддерживать этот список, но так же и следить за временем пребывания заявок в списке отложенных.

    Если приоритеты нужны, то какие?

    per-agent-prio и per-queue-prio

    На самом деле в SO-5 нет такой штуки, как очередь заявок агента. Есть очередь заявок для рабочей нити (в thread_pool/adv_thread_pool-диспетчерах чуть сложнее, но сути это не меняет).

    Если агент работает на рабочей нити один, то очередь заявок нити оказывается очередью заявок агента. Но если агент работает на рабочей нити не один, то заявки всех агентов в этой очереди “перемешиваются”. Что приводит к вопросу: если в очереди заявок размещаются заявки для разных агентов, то как следует поступать с приоритетными заявками, которые попадают в эту очередь?

    Представляется, что есть два подхода:

    • механизм per-agent-prio означает, что приоритеты событий имеют значение только для одного агента. Допустим, что есть агенты A, B и C, разделяющие общую очередь заявок. Эта очередь на данный момент имеет вид (m1(A),m2(B),m3(C),m4(B)). Т.е. сначала сообщение для A, затем для B, затем для C и последнее опять для B. Приходит очередное сообщение m5 для B, приоритет которого выше, чем приоритет сообщений m2 и m4. Очередь заявок должна принять вид (m1(A),m5(B),m3(C),m2(B),m4(B)). Т.е. приоритетное сообщение меняет порядок сообщений только для B;
    • механизм per-queue-prio означает, что приоритеты событий сказываются на всей очереди. Т.е. если в примере (m1(A),m2(B),m3(C),m4(B)) сообщение m5 для B имеет самый высокий приоритет среди всех сообщений m1..m4, то очередь заявок должна принять вид (m5(B),m1(A),m2(B),m3(C),m4(B)).

    Однако, если попробовать спроецировать эти подходы на то, что встречается на практике, то получается, что для механизма per-agent-prio примеры использования придумать можно. Так, два описанных выше сценария использования приоритетов (контроль перегрузки и распределение работы между воркерами), требуют механизма per-agent-prio.

    Поэтому, если у кого-то есть примеры сценариев использования per-queue-prio, то просьба оставить их в комментариях.

    opened by eao197 2
  • Brief performance audit

    Brief performance audit

    1. inline trivial functions & defaulting contructors
    2. TATAS spinlock with pause backoff
    3. cleanup

    preliminary performance numbers described in commit messages

    opened by isilence 1
  • Brief performance audit

    Brief performance audit

    1. inline trivial functions & defaulting contructors
    2. TATAS spinlock with pause backoff
    3. cleanup

    For preliminary performance differences see commit messages.

    opened by isilence 1
  • update masterspline's e-mail (

    update masterspline's e-mail ([email protected])

    Я сменил e-mail (домен .eu дешевле, чем .net). Возможно, в dev/CMakeLists.txt имеет смысл изменить и само сообщение (оно было сделано таким на этапе экспериментального использования cmake сборки, сейчас уже все стабилизировалось).

    opened by ghost 1
  • The history of SObjectizer-5.5 is going to the end

    The history of SObjectizer-5.5 is going to the end

    opened by eao197 0
  • [en/ru] Event-handlers formats for SObjectizer-5.6

    [en/ru] Event-handlers formats for SObjectizer-5.6

    There is a topic in development of SObjectizer-5.6 where some feedback from SObjectizer's users (or just watchers) are required. I described this topic in a post in SObjectizer's Google group: Event-handler formats in SObjectizer-5.6. Please share you option if you have a time/desire. As reply in the Google group or even here.

    При разработке SObjectizer-5.6 возникла тема, по которой хотелось бы получить обратную связь от пользователей SObjectizer-а или просто интересующихся. Тема описана в SObjectizer-овской Google-группе: Форматы обработчиков сообщений в SObjectizer-5.6. Пожалуйста, поделитесь своими соображениями, если у вас найдется время и желание. В виде ответа в Google-группе или прямо здесь.

    help wanted question 
    opened by eao197 8
  • [en] On the road to SObjectizer-5.6

    [en] On the road to SObjectizer-5.6


    Work on 5.5-branch started more than 4.5 years ago. In conditions when it was necessary to take into account compilers without a proper support of C++11, not speaking about C++14. Since then SObjectizer-5.5 is being developed with respect to old C++ compilers and with attempts to provide maximum source-code compatibility between versions inside 5.5-branch. SObjectizer-5.5 also inherited some design decisions from more earlier versions of SObjectizer-5.

    As the result there are some flaws in design and implementation of SObjectizer. These flaws are the consequences of mistakes during designing SObjectizer's API and inabilities to use features from modern C++ standards. There is no way to fix those flaws without breaking compatibility between SObjectizer's versions.

    It seems that there is no sense to continue development of 5.5-branch in 2019.

    The goal of SObjectizer-5.6 development

    The goal of SObjectizer-5.6 development is the creation of next SObjectizer version without a problems detected in 5.5-branch. The next SObjectizer version will keep the basic working principles of SObjectizer-5, but without 100% compatibility with SObjectizer-5.5.

    What are planned for SObjectizer-5.6?

    Remove all deprecated things

    As result of 4+ years evolution of 5.5-branch a plenty of things were marked as deprecated. For example: so_5::rt namespace and send_delayed_to_agent function.

    Those things are still present in SObjectizer-5.5 for the compatibility. But it is a time to cleanup SObjectizer's code base.

    Every mbox will hold a reference to SObjectizer Environment

    There is no way to get a reference to SObjectizer Environment from an mbox. But, in principle, it is possible for MPSC-mboxes. Alse one can get that reference from mchain and mchain can be transformed into mbox, but that mbox doesn't provides access to SObjectizer Environment.

    As a result we have different versions of send_delayed and send_periodic functions in SObjectizer-5.5. In the next version of SObjectizer a reference to Environment can be obtained from any mbox. It allows to make unified versions of send_delayed and send_periodic functions, for examples: send_delayed(mbox, pause, args) and send_delayed(agent, pause, args).

    Reduce count of ways to send a message

    SObjectizer-5.5 has many ways to send a message. For example: several overloads of deliver_message in abstract_message_mbox_t class. It is the result of many years of SObjectizer's evolution.

    It is necessary to remove some of old methods and classes intended for message sending and issuing of service requests. A couple of methods in abstract_message_t and environment_t + template functions send, send_delayed, send_periodic, request_value and request_feature should be enough.

    Reduce count of event-handler's formats

    Only two formats will be allowed in SObjectizer-5.6:

    ret_type event_handler(mhood_t<msg_type>); // for messages and signals.
    ret_type event_handler(const mhood_t<msg_type> &); // for messages and signals.

    Support for ad-hoc agents will be removed

    The experience shows that it is easy to declare an ordinary agent for some simple actions in modern C++. Because of that there is no sense to keep support for ad-hoc agents in SObjectizer.

    Support for tuple_as_message will be removed

    There is no need to support tuple_as_message after introduction of possibility to send messages of arbitrary user type (a type not inherited from so_5::message_t).

    No public dispatchers any more

    There were only public dispatchers in early versions of SObjectizer-5. Private dispatchers were introduced later. But now the private dispatchers are the recommended way to bind agents to some execution context.

    Support for public and private dispatcher makes SObjectizer's API complex and this support is expensive in sense of SObjectizer's maintenance. Because of that only private dispatchers will be supported in SObjectizer-5.6.

    Cleanup of API

    Some duplicated method/functions and potentially dangerous methods/function (like those accept raw pointers) will be removed.

    Where the source code of SObjectizer-5.6 will live?

    Since May 2013 the source code of SObjectizer and related projects lives in Subversion-repository on SourceForge with an experimental mirror on GitHub. We plan to change that for SObjectizer-5.6.

    The first reason is the speed of Svn on last year. Svn on is slow now. And sometimes the repository becomes unavailable during the problems with

    The second reason is a desire to have a simple integration with services like TravisCI (without a complex mirroring procedure).

    The usage of GitHub looks like the main variant (with repository name like But some of SObjectizer's developers (eao197 as an example) don't like git and GitHub and prefer different tools.

    Because of that there is an alternative: Mercurial-repo on BitBucket (with name like With mirror to GitHub (mirror of Hg repo much simpler than mirror of Svn-repo).

    There is no the decision on this question yet.

    Companion projects, like timertt and so_5_extra, will live in separate repos on the same hosting platform. Dependency management will be performed via MxxRu:::externals (like that is done now for so_5_extra).

    Where the documentation for SObjectizer-5.6 will live?

    This is an open question. There are three possible answers.

    1. The documentation for new version will be placed in the Wiki on SourceForge. It means that all SObjectizer's doc will be at the same place. This case simplifies writing of new doc because big fragments from old doc can be reused easily.

    2. The documentation will be placed in the Wiki of new repository. For example if BitBucket will be used for hosting of SObjectizer-5.6 code then the doc will be in Wiki on BitBucket.

    3. The documentation will be placed on like it is done for RESTinio's manual.

    Which C++ standard will be used for 5.6-branch?

    We want to use C++17. With minimal C++ compilers like GCC 7, clang 6 and Visual C++ 15.9.3. Or even GCC 8, clang 7 and VC++ 15.9.3.

    We can reduce the our requirements to C++14 standard. But only if someone tell us why this is important. If nobody asks for C++14 support we will support only C++17 and newer versions of C++.

    We won't support C++11. If you really need C++11 please consider commercial support for SObjectizer.

    What is the timeline?

    We expect two stages of SObjectizer-5.6 development.

    The first stage is the cleanup of SObjectizer's code and forming of the very first SObjectizer-5.6 version. Plus the writing of documentation and manuals for the new version. As the result of this stage the version 5.6.0 should be released. We want to ship 5.6.0 at the end of Feb 2019 (if everything will go as expected).

    The next stage will begin after release of version 5.6.0. This stage is for extension of SObjectizer-5.6 functionality. It means that since v.5.6.0 new features will be added only to SObjectizer-5.6, not to SObjectizer-5.5.

    How long SObjectizer-5.6 will live?

    We expect that SObjectizer-5.6 will be the actual SObjectizer branch till the end of 2019. We have no plans beyond that time point.

    The actual lifetime of 5.6-branch will be dictated by SObjectizer's users. The more people use SObjectizer-5.6 in their projects, the longer lifetime for SObjectizer-5.6.

    What will happen with SObjectizer-5.5?


    We will maintain SObjectizer-5.5, fix defects and publish updates until the release of SObjectizer-5.6.0. After that moment the development and maintenance of SObjectizer-5.5 will be stopped.

    If you want a maintenance for SObjectizer-5.5 then you can ask for commercial support.

    How can you make an influence on SObjectizer's development?

    We always listen to our customers and users. So you can tell us everything you want. For example: what do you want to see in next SObjectizer's version? What do you want to remove from SObjectizer? Do you agree with usage of C++17 or maybe you need C++14? Is it OK to host SObjectizer of BitBucket or maybe you can work with GitHub only?

    Your answers to those questions make our further development of SObjectiver much easier.

    help wanted 
    opened by eao197 3
  • [ru] На пути к SObjectizer-5.6

    [ru] На пути к SObjectizer-5.6


    Работа над веткой 5.5 началась более 4.5 лет назад. В условиях, когда приходилось использовать компиляторы без вменяемой поддержки даже C++11, не говоря уже про C++14. Все это время SObjectizer-5.5 развивался во-первых, с серьезной оглядкой на старые C++ компиляторы и, во-вторых, с максимальным сохранением совместимости между версиями в рамках ветки 5.5. Кроме того, SObjectizer-5.5 унаследовал ряд проектных решений из еще более ранних версий SObjectizer-5.

    В результате в реализации SObjectizer-5.5 накопились "косяки", которые были обусловлены как просчетами при проектировании, так и невозможностью использовать новые версии стандарта C++. Исправить эти косяки без нарушения совместимости между версиями не представляется возможным.

    В условиях 2019-го года продолжать развитие ветки 5.5 с оглядкой как на ограниченное подмножество C++11, так и на совместимость с проектными решениями, принятыми 4.5 года назад не представляется более ни разумным, ни экономически оправданным.

    Цель разработки SObjectizer-5.6

    Целью разработки ветки 5.6 является устранение проблем ветки 5.5 при сохранении основных принципов работы SObjectizer-5, но без стремления обеспечить 100% совместимость с веткой 5.5.

    Планируемые изменения в SObjectizer-5.6

    Изъятие всего того, что в SObjectizer-5.5 было помечено как deprecated.

    За более чем 4 года развития ветки 5.5 множество вещей было помечено как deprecated. Например, пространство имен so_5::rt или функция send_delayed_to_agent. Из-за сохранения совместимости все это еще присутствует в SObjectizer-е и, более того, работает.

    Однако, пришло время избавить кодовую базу SObjectizer-а от этого старого хлама.

    Каждый mbox будет содержать ссылку на SObjectizer Environment

    В SObjectizer-5.5 через mbox нельзя получить ссылку на SObjectizer Environment, хотя это можно было бы сделать для MPSC-mbox-а. Тогда как через mchain ссылку на SObjectizer Environment получить можно. При этом mchain может трансформироваться в mbox, а из mbox доступа к Environment-у нет.

    Если в mbox-е будет хранится ссылка на SObjectizer Environment, то получится сделать send_delayed и send_periodic унифицированными. Т.е. вызов send_delayed(mbox, pause, args) будет выглядеть так же, как и send_delayed(agent, pause, args).

    Сокращение количества способов отослать сообщение

    Сейчас в SObjectizer-5.5 по историческим причинам накопился ряд методов для отсылки сообщений (например, различные варианты deliver_message в классе abstract_message_box_t) и выполнения синхронных запросов. Здесь нужно навести порядок и оставить лишь самый необходимый минимум в классах abstract_message_box_t, environment_t, а также останется только ряд шаблонных функций send, send_delayed, send_periodic, request_value и request_future.

    Сокращение количество разрешенных форматов обработчиков сообщений

    Останется поддержка только двух следующих форматов:

    ret_type event_handler(mhood_t<msg_type>); // for messages and signals.
    ret_type event_handler(const mhood_t<msg_type> &); // for messages and signals.

    Останутся только обычные агенты, ad-hoc агенты будут удалены

    Практика показывает, что определить обычного агента, который выполняет какие-то простые действия, прямо "по месту" в современном C++ совсем не сложно. Поэтому затраты на поддержку ad-hoc агентов в SObjectizer-е не соответствуют той выгоде, которую ad-hoc агенты дают.

    Будет изъята поддержка tuple_as_message

    После того, как в SObjectizer-5.5 появилась возможность отсылки сообщений произвольных пользовательских типов (без необходимости наследования от so_5::message_t), надобность в функциональности tuple_as_message, фактически, отпала.

    Будет устранено деление на публичные и приватные диспетчеры

    Исторически в SObjectizer-е были только публичные диспетчеры. Затем были добавлены приватные диспетчеры, которые и рекомендуются к использованию. Поддержка и публичных, и приватных диспетчеров усложняет API SObjectizer-а и привносит дополнительные расходы на его развитие и сопровождение. Поэтому в SObjectizer-5.6 останутся только приватные диспетчеры.

    Будет проведена чистка API

    Будут удалены методы, которые дублируются и/или имеют потенциально опасный вид, например, принимают "голые" указатели.

    Где будут жить исходники SObjectizer-5.6?

    До сих пор исходники SObjectizer-а жили в Subversion репозитории на SourceForge с экспериментальным зеркалом на GitHub-е. Для SObjectizer-5.6 это уже будет не так.

    Во-первых, скорость работы с Svn на в последнее время стала недостаточно хорошей. И сам Svn-репозиторий на время от времени оказывается недоступным.

    Во-вторых, хотелось бы иметь более простую интеграцию с сервисами, вроде TravisCI, без процедуры зеркалирования куда-то Svn-репозитория.

    В качестве основного варианта пока рассматривается разработка SO-5.6 непосредственно на GitHub-е (с именем вида Но кое-кто из разработчиков SObjectizer-а (например, eao197) не любит ни git, ни GitHub.

    Поэтому есть альтернативный вариант -- Mercurial-репозиторий на BitBucket-е (с именем вида С зеркалом на GitHub. Благо Hg зеркалируется в git гораздо проще.

    Решение по этому вопросу еще не принято.

    Соответственно, сопутствующие проекты, т.к. timertt и so_5_extra, будут жить в отдельных репозиториях на том же самом хостинге, что и SObjectizer-5.6. Управление зависимостями будет построено на базе MxxRu::externals.

    Где будет жить документация по SObjectizer-5.6?

    Открытый пока вопрос. Есть три основных варианта.

    1. Размещение документации по новой версии в Wiki проекта на SourceForge. Чтобы вся документация была собрана в одном месте. Кроме того, в этом варианте проще писать новую документацию, т.к. можно переделывать старую.

    2. Размещение документации в Wiki того репозитория, в котором будут размещаться исходники SObjectizer-5.6.

    3. Размещение документации на сайте, как это сейчас происходит, например, с документаций по RESTinio.

    Какая версия стандарта C++ будет использоваться для разработки версии 5.6?

    Есть большое желание сразу использовать C++17. И, соответственно, в качестве минимальных версий компиляторов рассматривать GCC 7, clang 6 и Visual C++ 15.9.3. Либо даже GCC 8, clang 7 и VC++ 15.9.3.

    Требования к стандарту C++ можно уменьшить до C++14, но только в случае, если кто-то объяснит, почему это важно. Если никто не попросит о поддержке C++14, то ее и не будет.

    С++11 не будет поддерживаться в принципе. Если вам это, действительно нужно, то рассмотрите, пожалуйста, вариант коммерческой поддержки SObjectizer-а.

    Что по срокам?

    Разработка SObjectizer-5.6, как предполагается, будет состоять из двух стадий.

    На первой стадии происходит чистка исходного кода SObjectizer-а и формирование основной кодовой базы SObjectizer-5.6. Плюс адаптация уже написанной документации и учебных материалов к особенностям версии 5.6. Завершается эта стадия выпуском версии 5.6.0. Если все будет идти нормально, без форс-мажоров, то ожидать релиза 5.6.0 можно к концу февраля 2019-го.

    Следующая стадия начнется после релиза версии 5.6.0. Она подразумевает расширение SObjectizer-5.6 новой функциональностью. Т.е. новые фичи будут добавляться не в SO-5.5, а в SO-5.6.

    Какое время жизни планируется у SObjectizer-5.6?

    Предположительно, SObjectizer-5.6 будет актуален до конца 2019-го года. Дальше мы пока не загадываем.

    На развитие SObjectizer-5.6 прямое влияние будет оказывать его востребованность. Чем больше людей будет использовать SO-5.6 и будет высказывать заинтересованность в нем, тем дольше мы будет развивать ветку 5.6 обеспечивая максимально возможную совместимость между версиями внутри ветки, как это происходило с веткой 5.5.

    Что будет дальше с SObjectizer-5.5?


    До момента релиза SObjectizer-5.6.0 мы будет устранять найденные в SObjectizer-5.5 проблемы и выпускать обновления. После релиза версии 5.6.0 какое-либо развитие ветки 5.5 будет остановлено.

    Если вам необходима дальнейшая поддержка SObjectizer-5.5, то вы можете обратиться к нам за коммерческой поддержкой.

    Как вы можете повлиять на развитие SObjectizer-а?

    Мы всегда прислушиваемся к пожеланиям наших пользователей. Поэтому если вы найдете возможность высказать свое мнение о том, каким вы видите SObjectizer-5.6, что вы хотели бы там иметь, чтобы вы из SObjectizer-а выбросили бы, устраивает ли вас использование стандарта C++17, напрягает ли вас хостинг проекта на BitBucket-е и т.д., то вы окажете нам существенную помощь в выборе вектора дальнейшего развития SObjectizer-а.

    help wanted 
    opened by eao197 3
  • multiparameter messages

    multiparameter messages

    It was not bad to have it possible not to write your structure but to transfer a set of parameters in rune-time.

    auto args0 = 0;
    auto args1 = 0.5;
    std::string arg2 = "args2";
    auto msg = make_message(arg0,arg1,arg2);
    opened by kotbegemot 14
Read and write rosbag on a platform without ROS installed, using MQTT for message delivery.

EasyRosBag x86_64: Test on Ubuntu18.04 arm64 : Test on Ubuntu21.04(raspberry Pi4) Introducton ROS(Robot Operation System) is too fat!!! We do not ins

afei 9 May 23, 2022
Yet another tensor library in C++. It allows direct access to its underlying data buffer, and serializes in JSON.

Yet another tensor library in C++. It allows direct access to its underlying data buffer, and serializes in JSON. Built on top of zax json parser, C++ structures having tensor members can also be JSON-serialized and deserialized, allowing one to save and load the state of a highly hierarchical object.

Tamas Levente Kis 2 Dec 15, 2022
An implementation on Fast Ground Segmentation for 3D LiDAR Point Cloud Based on Jump-Convolution-Process.

An implementation on "Shen Z, Liang H, Lin L, Wang Z, Huang W, Yu J. Fast Ground Segmentation for 3D LiDAR Point Cloud Based on Jump-Convolution-Process. Remote Sensing. 2021; 13(16):3239."

Wangxu1996 59 Jan 5, 2023
Fairring (FAIR + Herring) is a plug-in for PyTorch that provides a process group for distributed training that outperforms NCCL at large scales

Fairring (FAIR + Herring): a faster all-reduce TL;DR: Using a variation on Amazon’s "Herring" technique, which leverages reduction servers, we can per

Meta Research 46 Nov 24, 2022
Frog is an integration of memory-based natural language processing (NLP) modules developed for Dutch. All NLP modules are based on Timbl, the Tilburg memory-based learning software package.

Frog - A Tagger-Lemmatizer-Morphological-Analyzer-Dependency-Parser for Dutch Copyright 2006-2020 Ko van der Sloot, Maarten van Gompel, Antal van den

Language Machines 70 Dec 14, 2022
The core engine forked from NVidia's Q2RTX. Heavily modified and extended to allow for a nicer experience all-round.

Nail & Crescent - Development Branch Scratchpad - Things to do or not forget: Items are obviously broken. Physics.cpp needs more work, revising. Proba

PalmliX Studio 21 Dec 22, 2022
A program that receives all the results of the matches of a basketball tournament and calculates the final results as well as which teams go up or down a division.

O enunciado fornecido não é necessariamente completo. O comportamento do programa nas situações não previstas no enunciado deve ser escolhido por cada

António Pedro Correia 1 Dec 21, 2021
Eclipse Deeplearning4J (DL4J) ecosystem is a set of projects intended to support all the needs of a JVM based deep learning application

Suite of tools for deploying and training deep learning models using the JVM. Highlights include model import for keras, tensorflow, and onnx/pytorch, a modular and tiny c++ library for running math code and a java based math library on top of the core c++ library. Also includes samediff: a pytorch/tensorflow like library for running deep learning using automatic differentiation.

Eclipse Foundation 12.7k Dec 29, 2022
C++ library for getting full ROS message definition or MD5 sum given message type as string

rosmsg_cpp C++ library for getting full message definition, MD5 sum and more given just the message type as string. This package provides both C++ lib

Vision for Robotics and Autonomous Systems 3 Jan 5, 2022
Stealthy way to hijack the existing game process handle within the game launcher (currently supports Steam and Achieve external game process read/write with minimum footprint.

Launcher Abuser Stealthy way to hijack the existing game process handle within the game launcher (currently supports Steam and Achieve ex

Ricardo Nacif 80 Nov 25, 2022
Process Ghosting - a PE injection technique, similar to Process Doppelgänging, but using a delete-pending file instead of a transacted file

Process Ghosting This is my implementation of the technique presented by Gabriel Landau:

hasherezade 514 Jan 3, 2023
EarlyBird process hollowing technique (BOF) - Spawns a process in a suspended state, inject shellcode, hijack main thread with APC, and execute shellcode

HOLLOW - Cobalt Strike BOF Authors: Bobby Cooke (@0xBoku) Justin Hamilton (@JTHam0) Octavio Paguaga (@OakTree__) Matt Kingstone (@n00bRage) Beacon Obj

Bobby Cooke 203 Dec 20, 2022
C++11 header-only message digest library

digestpp Experimental C++11 header-only message digest library. Derived from cppcrypto in an attempt to devise a more modern yet flexible and universa

null 150 Dec 24, 2022
Simple Binary Encoding (SBE) - High Performance Message Codec

Simple Binary Encoding (SBE) SBE is an OSI layer 6 presentation for encoding and decoding binary application messages for low-latency financial applic

Real Logic 2.8k Dec 28, 2022
Reliable & unreliable messages over UDP. Robust message fragmentation & reassembly. P2P networking / NAT traversal. Encryption.

GameNetworkingSockets GameNetworkingSockets is a basic transport layer for games. The features are: Connection-oriented API (like TCP) ... but message

Valve Software 6.4k Dec 30, 2022
Embeddable Event-based Asynchronous Message/HTTP Server library for C/C++

libasyncd Embeddable Event-based Asynchronous Message/HTTP Server library for C/C++. What is libasyncd? Libasyncd is an embeddable event-driven asynch

Seungyoung 166 Dec 5, 2022
Ring powered by an adafruit gemma + neopixel that sends a positive affirmation message to me via morse code

Positive Affirmation Morse Code Ring ✨ Ring powered by an adafruit gemma + neopixel that sends a positive affirmation message to me via slowed-down mo

Stephanie 3 Dec 31, 2021
A C++17 message passing library based on MPI

MPL - A message passing library MPL is a message passing library written in C++17 based on the Message Passing Interface (MPI) standard. Since the C++

Heiko Bauke 115 Dec 28, 2022
New generation message broker service

Push1st Push1st is open source multiple protocol PUB/SUB message broker server (Pusher, MQTT, RAW WebSocket). Key features Suitable for distributed on

Naveksoft 16 Dec 14, 2022
Realtime Micro Kernel -- Event-driven Run-to-Completion RTOS with Active Objects, Timed Events, Memory Pools, and Message Queues

Realtime Micro Kernel Features Active Objects Message queues Variable sized, custom messages Periodic and single timed events Memory pools Supported P

null 3 Nov 7, 2022