~siborgium/prelockdpp

368e662caca71e4fa37890620607c1cc1c65dcd0 — Sergey Smirnykh 2 years ago c8eed12
Use plain set_base_hook<>, no need for tags
1 files changed, 33 insertions(+), 33 deletions(-)

M main.cpp
M main.cpp => main.cpp +33 -33
@@ 158,7 158,7 @@ using uniq_alive_hook =
using uniq_temp_hook =
    intr::set_base_hook<intr::optimize_size<true>, intr::tag<tags::dead>>;

struct uniq_id: public uniq_alive_hook, public uniq_temp_hook {
struct uniq_id: public uniq_alive_hook {
    timespec start_time;
    int      pid;



@@ 212,7 212,7 @@ using uniq_temp_set = intr::set<
namespace std {
    template<>
    struct hash<uniq_id> {
        size_t operator()(const uniq_id &id) const {
        size_t operator()(const uniq_id& id) const {
            constexpr size_t prime = 257;

            size_t h1{ hash<decltype(id.start_time.tv_sec)>{}(id.start_time.tv_sec) };


@@ 274,7 274,7 @@ struct context {

    // storage for ids
    plf::colony<uniq_id> ids;
    uniq_alive_set       alive_ids;
    uniq_alive_set       current_uniqs_set;

    // FIXME: I could use Boost.Intrusive & build something decent
    //        instead of endless maps & sets


@@ 464,7 464,9 @@ struct context {

        // this set will contain ids (see later)
        // that are alive at this iteration
        uniq_temp_set current_ids;
        // FIXME: we could use a list, actually
        //        any_hooks are pain though
        uniq_alive_set new_ids;

        auto m0 = get_clock_time(CLOCK_MONOTONIC);
        auto p0 = get_clock_time(CLOCK_PROCESS_CPUTIME_ID);


@@ 494,18 496,25 @@ struct context {
            fmt_proc_pid_file(stat_path);

            with_uniq_id(path_buf, [&](auto start_time) {

                // if uniq_id is already exists
                // (e.g. process was alive on the prev iteration)
                // we migrate it to the `current_ids` set
                uniq_id id{ start_time, pid };
                if (auto iter = alive_ids.find(id); iter != alive_ids.end()) {
                    current_ids.insert(*iter);
                    alive_ids.erase(iter);
                } else {
                    auto colony_iter = ids.emplace(id);
                    set_self_iter(*colony_iter, colony_iter);
                    current_ids.insert(*colony_iter);
                {
                    // if uniq_id is already exists
                    // (e.g. process was alive on the prev iteration)
                    // we migrate it to the `current_ids` set
                    // NOTE: we create `source` & use it to lookup the set
                    //       but all further actions are made on the actual
                    //       value in the set, not `source`
                    uniq_id source{ start_time, pid };
                    auto iter = current_uniqs_set.find(source);
                    if (iter != current_uniqs_set.end()) {
                        // the id is still alive from the previous iteration
                        // just move it to new_ids
                        new_ids.insert(*iter);
                        current_uniqs_set.erase(iter);
                    } else {
                        auto colony_iter = ids.emplace(source);
                        set_self_iter(*colony_iter, colony_iter);
                        new_ids.insert(*colony_iter);
                    }
                }

#if 0


@@ 524,28 533,19 @@ struct context {
            throw errno_exception("readdir(proc) failed", errno);
        }

        // all alive ids are in `current_ids`
        // and alive_ids only store dead ones
        // lets clear alive_ids and re-populate it with actually alive ids
        // FIXME: figure out how to store iterators
        //        and enjoy cheap removal
        // all alive ids are in `new_ids`
        // and `current_uniqs_set` only stores dead ones
        // lets clear dead ids and re-populate it with actually alive ids
        {
            auto dead = alive_ids.begin();
            while (dead != alive_ids.end()) {
                auto copy = dead;
                ++dead;

                auto orig = get_self_iter(*copy);
                alive_ids.erase(copy);
            while (!current_uniqs_set.empty()) {
                auto* dead = current_uniqs_set.unlink_leftmost_without_rebalance();
                auto orig = get_self_iter(*dead);
                ids.erase(orig);
            }

        }
        for (auto&& id: current_ids) {
            alive_ids.insert(id);
            current_uniqs_set = std::move(new_ids);
        }

        for (auto && id: alive_ids) {
        for (auto && id: current_uniqs_set) {
            std::cout << id.start_time.tv_sec << '.' << id.start_time.tv_nsec << ' ' << id.pid << '\n';
        }