text:
/// \file
/// Maintainer: Felice Serena
///
///

#include "hog_labeling.h"

#include <opencv2/core/core.hpp>
#include <opencv2/core/eigen.hpp>
#include <opencv2/objdetect/objdetect.hpp>

#include <boost/log/trivial.hpp>

#include <classifier/knn.h>

namespace MouseTrack {

/// Returns a n x 2 matrix of (x,y) pairs of valid corner coordinates for
/// sliding windows of the desired size such that they are within the given
/// image dimensions.
///
std::vector<cv::Point> slidingWindows(int imgWidth, int imgHeight, int stepSize,
                                      int windowWidth, int windowHeight) {
  std::vector<cv::Point> result;
  for (int x = 0; x < imgWidth - windowWidth; x += stepSize) {
    for (int y = 0; y < imgHeight - windowHeight; y += stepSize) {
      result.push_back(cv::Point(x, y));
    }
  }
  return result;
} // namespace MouseTrack

int HogLabeling::slidingWindowWidth() const {
    return _windowWidth;
}

void HogLabeling::slidingWindowWidth(int _new) {
    _windowWidth = _new;
}

int HogLabeling::slidingWindowHeight() const{
    return _windowHeight;
}

void HogLabeling::slidingWindowHeight(int _new){
    _windowHeight = _new;
}

/// Get the number of pixels between two neighboring sliding windows (used along both axis)
int HogLabeling::slidingWindowStride() const {
    return _stepSize;
}

/// Set the number of pixels between two neighboring sliding windows (used along both axis)
void HogLabeling::slidingWindowStride(int _new) {
    _stepSize = _new;
}

std::unique_ptr<Classifier>& HogLabeling::classifier(){
  return _classifier;
}

void HogLabeling::train(const Mat &X_train, const Vec &y_train) {
  if(_classifier.get() == nullptr){
    auto ptr = std::make_unique<KnnClassifier>();
    ptr->k(11);
    _classifier = std::move(ptr);
  }
  _classifier->fit(X_train, y_train);
  _numLabels = y_train.maxCoeff() + 1;
}

FrameWindow HogLabeling::operator()(const FrameWindow &window) const {
  if (window.frames().empty()) {
    return window;
  }
  if (_classifier.get() == nullptr) {
    BOOST_LOG_TRIVIAL(warning)
        << "HOG classifier not trained, no labeling performed.";
    return window;
  }
  FrameWindow result = window;
  // create matrices for labels
  for (Frame &f : result.frames()) {
    f.labels.resize(_numLabels);
    for (auto &l : f.labels) {
      l.setZero(f.referencePicture.rows(), f.referencePicture.cols());
    }
  }

  // hog settings
  cv::Size windowSize(_windowWidth, _windowHeight);
  cv::Size blockSize(_blockWidth, _blockHeight);
  cv::Size blockStride(_blockStrideWidth, _blockStrideHeight);
  cv::Size cellSize(_cellWidth, _cellHeight);

  // create hog descriptor: it is able to tansform images patches to feature
  // vectors
  cv::HOGDescriptor hog(windowSize, blockSize, blockStride, cellSize, _nbins);

  // compute settings
  cv::Size windowStride;
  cv::Size padding;

  // build locations for sliding window
  const auto &first = result.frames()[0];
  std::vector<cv::Point> locations = slidingWindows(
      first.referencePicture.cols(), first.referencePicture.rows(), _stepSize,
      _windowWidth, _windowHeight);

  BOOST_LOG_TRIVIAL(trace) << "Created " << locations.size()
                           << " sliding window locations to check.";

  for (size_t f = 0; f < result.frames().size(); ++f) {
    BOOST_LOG_TRIVIAL(trace) << "Checking frame " << f;
    Frame &frame = result.frames()[f];
    cv::Mat img;
    PictureI eig = (frame.referencePicture * 255.0).cast<PictureI::Scalar>();
    cv::eigen2cv(eig, img);

    // holds `locations.size()` descriptors of size hog.getDescriptorSize()
    std::vector<float> descriptors;
    hog.compute(img, descriptors, windowStride, padding, locations);
    BOOST_LOG_TRIVIAL(trace)
        << "Found " << (descriptors.size() / hog.getDescriptorSize())
        << " HOG descriptors of size " << hog.getDescriptorSize() << " at "
        << locations.size() << " locations in frame " << f;
    Eigen::Map<Eigen::MatrixXf> map(descriptors.data(), hog.getDescriptorSize(),
                                    locations.size());
    Classifier::Mat tmp = map.cast<double>();
    BOOST_LOG_TRIVIAL(trace) << "Classifying...";
    auto labels = _classifier->predictProbabilities(tmp);
    BOOST_LOG_TRIVIAL(trace) << "Assigning...";
    // apply labels of windows to frame.labels
    for (size_t w = 0; w < locations.size(); ++w) {
      // iterate over pixels within window w
      for (int x = locations[w].x; x < locations[w].x + _windowWidth; ++x) {
        for (int y = locations[w].y; y < locations[w].y + _windowHeight; ++y) {
          // distribute labels
          for (int l = 0; l < _numLabels; ++l) {
            frame.labels[l](y, x) += labels(l, w);
          }
        }
      }
    }
    // normalize label weights
    if (_normalizeRange) {
      for (auto &l : frame.labels) {
        auto min = l.minCoeff();
        l = l.array() - min;
        auto max = l.maxCoeff();
        l = l.array() / max;
      }
    }

    // normalize accross labels
    if (_normalizeAccross) {
      PictureD sum;
      sum.setZero(frame.referencePicture.rows(), frame.referencePicture.cols());
      for (int l = 0; l < _numLabels; ++l) {
        sum += frame.labels[l];
      }
      // avoid division by zero
      sum = sum.array() + 0.0000001;
      sum = sum.array().inverse();
      for (int l = 0; l < _numLabels; ++l) {
        frame.labels[l] = frame.labels[l].array() * sum.array();
      }
    }
    BOOST_LOG_TRIVIAL(trace) << "Frame " << f << " finished.";
  }
  return result;
}

} // namespace MouseTrack

ext: cpp

max_stars_repo_name: itko/scanbox

max_issues_repo_name: itko/scanbox

max_forks_repo_name: itko/scanbox


text:
#include "storage/io.hpp"
#include "util/exception.hpp"
#include "util/fingerprint.hpp"
#include "util/typedefs.hpp"
#include "util/version.hpp"

#include <boost/test/test_case_template.hpp>
#include <boost/test/unit_test.hpp>

#include <exception>
#include <numeric>
#include <string>

const static std::string IO_TMP_FILE = "test_io.tmp";
const static std::string IO_NONEXISTENT_FILE = "non_existent_test_io.tmp";
const static std::string IO_TOO_SMALL_FILE = "file_too_small_test_io.tmp";
const static std::string IO_CORRUPT_FINGERPRINT_FILE = "corrupt_fingerprint_file_test_io.tmp";
const static std::string IO_INCOMPATIBLE_FINGERPRINT_FILE =
    "incompatible_fingerprint_file_test_io.tmp";
const static std::string IO_TEXT_FILE = "plain_text_file.tmp";

BOOST_AUTO_TEST_SUITE(osrm_io)

BOOST_AUTO_TEST_CASE(io_data)
{
    std::vector<int> data_in(53), data_out;
    std::iota(begin(data_in), end(data_in), 0);

    {
        osrm::storage::io::FileWriter outfile(IO_TMP_FILE,
                                              osrm::storage::io::FileWriter::GenerateFingerprint);
        outfile.SerializeVector(data_in);
    }

    osrm::storage::io::FileReader infile(IO_TMP_FILE,
                                         osrm::storage::io::FileReader::VerifyFingerprint);
    infile.DeserializeVector(data_out);

    BOOST_REQUIRE_EQUAL(data_in.size(), data_out.size());
    BOOST_CHECK_EQUAL_COLLECTIONS(data_out.begin(), data_out.end(), data_in.begin(), data_in.end());
}

BOOST_AUTO_TEST_CASE(io_nonexistent_file)
{
    try
    {
        osrm::storage::io::FileReader infile(IO_NONEXISTENT_FILE,
                                             osrm::storage::io::FileReader::VerifyFingerprint);
        BOOST_REQUIRE_MESSAGE(false, "Should not get here");
    }
    catch (const osrm::util::exception &e)
    {
        const std::string expected("Error opening non_existent_test_io.tmp");
        const std::string got(e.what());
        BOOST_REQUIRE(std::equal(expected.begin(), expected.end(), got.begin()));
    }
}

BOOST_AUTO_TEST_CASE(file_too_small)
{
    {
        std::vector<int> v(53);
        std::iota(begin(v), end(v), 0);

        {
            osrm::storage::io::FileWriter outfile(
                IO_TOO_SMALL_FILE, osrm::storage::io::FileWriter::GenerateFingerprint);
            outfile.SerializeVector(v);
        }

        std::fstream f(IO_TOO_SMALL_FILE);
        f.seekp(sizeof(osrm::util::FingerPrint), std::ios_base::beg);
        std::uint64_t badcount = 100;
        f.write(reinterpret_cast<char *>(&badcount), sizeof(badcount));
    }

    try
    {
        osrm::storage::io::FileReader infile(IO_TOO_SMALL_FILE,
                                             osrm::storage::io::FileReader::VerifyFingerprint);
        std::vector<int> buffer;
        infile.DeserializeVector(buffer);
        BOOST_REQUIRE_MESSAGE(false, "Should not get here");
    }
    catch (const osrm::util::exception &e)
    {
        const std::string expected(
            "Error reading from file_too_small_test_io.tmp: Unexpected end of file");
        const std::string got(e.what());
        BOOST_REQUIRE(std::equal(expected.begin(), expected.end(), got.begin()));
    }
}

BOOST_AUTO_TEST_CASE(io_corrupt_fingerprint)
{
    {
        std::vector<int> v(153);
        std::iota(begin(v), end(v), 0);

        osrm::storage::io::FileWriter outfile(IO_CORRUPT_FINGERPRINT_FILE,
                                              osrm::storage::io::FileWriter::HasNoFingerprint);

        outfile.WriteOne(0xDEADBEEFCAFEFACE);
        outfile.SerializeVector(v);
    }

    try
    {
        osrm::storage::io::FileReader infile(IO_CORRUPT_FINGERPRINT_FILE,
                                             osrm::storage::io::FileReader::VerifyFingerprint);
        BOOST_REQUIRE_MESSAGE(false, "Should not get here");
    }
    catch (const osrm::util::exception &e)
    {
        const std::string expected("Fingerprint mismatch in corrupt_fingerprint_file_test_io.tmp");
        const std::string got(e.what());
        BOOST_REQUIRE(std::equal(expected.begin(), expected.end(), got.begin()));
    }
}

BOOST_AUTO_TEST_CASE(io_incompatible_fingerprint)
{
    {
        std::vector<int> v(153);
        std::iota(begin(v), end(v), 0);

        {
            osrm::storage::io::FileWriter outfile(IO_INCOMPATIBLE_FINGERPRINT_FILE,
                                                  osrm::storage::io::FileWriter::HasNoFingerprint);

            const auto fingerprint = osrm::util::FingerPrint::GetValid();
            outfile.WriteOne(fingerprint);
            outfile.SerializeVector(v);
        }

        std::fstream f(IO_INCOMPATIBLE_FINGERPRINT_FILE);
        f.seekp(5, std::ios_base::beg); // Seek past `OSRN` and Major version byte
        std::uint8_t incompatibleminor = static_cast<std::uint8_t>(OSRM_VERSION_MAJOR) + 1;
        f.write(reinterpret_cast<char *>(&incompatibleminor), sizeof(incompatibleminor));
    }

    try
    {
        osrm::storage::io::FileReader infile(IO_INCOMPATIBLE_FINGERPRINT_FILE,
                                             osrm::storage::io::FileReader::VerifyFingerprint);
        BOOST_REQUIRE_MESSAGE(false, "Should not get here");
    }
    catch (const osrm::util::exception &e)
    {
        const std::string expected("Fingerprint mismatch in " + IO_INCOMPATIBLE_FINGERPRINT_FILE);
        const std::string got(e.what());
        BOOST_REQUIRE(std::equal(expected.begin(), expected.end(), got.begin()));
    }
}

BOOST_AUTO_TEST_CASE(io_read_lines)
{
    {
        std::ofstream f(IO_TEXT_FILE, std::ios::binary);
        char str[] = "A\nB\nC\nD";
        f.write(str, strlen(str));
    }
    {
        osrm::storage::io::FileReader infile(IO_TEXT_FILE,
                                             osrm::storage::io::FileReader::HasNoFingerprint);
        auto startiter = infile.GetLineIteratorBegin();
        auto enditer = infile.GetLineIteratorEnd();
        std::vector<std::string> resultlines;
        while (startiter != enditer)
        {
            resultlines.push_back(*startiter);
            ++startiter;
        }
        BOOST_REQUIRE_MESSAGE(resultlines.size() == 4, "Expected 4 lines of text");
        BOOST_REQUIRE_MESSAGE(resultlines[0] == "A", "Expected the first line to be A");
        BOOST_REQUIRE_MESSAGE(resultlines[1] == "B", "Expected the first line to be B");
        BOOST_REQUIRE_MESSAGE(resultlines[2] == "C", "Expected the first line to be C");
        BOOST_REQUIRE_MESSAGE(resultlines[3] == "D", "Expected the first line to be D");
    }
}

BOOST_AUTO_TEST_SUITE_END()

max_stars_repo_name: mbeckem/msc

max_issues_repo_name: mbeckem/msc

max_forks_repo_name: mbeckem/msc


text:
#include <memory>
#include <list>
#include <iostream>
#include <exception>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/json_parser.hpp>

#include "config.h"
#include "AntiDebug.h"

#include "DebuggerFugitive.h"
#include "Console.h"
#include "interprocess.h"

bool DebuggerFugitive::ParseConfig(const char *szConfig)
{
	namespace pt = boost::property_tree;

	try
	{
		pt::ptree root;
		ReadConfigFile(szConfig, root);

		for (auto &node : root)
		{
			auto name = node.second.get<std::string>("name");
			auto subgroups = node.second.get_child_optional("subgroups");
			if (!subgroups)
				continue;

			auto group = anti_debug_ptr(new TechniqueGroup(name));
			ParseNode(subgroups.get(), group);
			if (!group->IsEmpty())
				m_lstAntiDebugGroups.push_back(group);
		}
	}
	catch (const pt::ptree_error &e)
	{
		Console::SetYellow();
		std::cout << "ERROR: " << e.what() << std::endl;
		Console::SetDefault();
		return false;
	}
	catch (...)
	{
		HandleException(std::current_exception());
		return false;
	}
	return true;
}

void DebuggerFugitive::Execute()
{
	for (auto &pAntiDebugGroup : m_lstAntiDebugGroups)
		pAntiDebugGroup->Check();
}

void DebuggerFugitive::ParseNode(boost::property_tree::ptree &root, anti_debug_ptr &parent)
{
	for (auto &node : root)
	{
		auto name = node.second.get<std::string>("name");
		auto subgroups = node.second.get_child_optional("subgroups");
		auto tags = GetNodeTags(node);
		if (!CheckTags(tags))
			continue;

		auto new_node = !subgroups
			? GetTechniqueByName(name, parent)
			: anti_debug_ptr(new TechniqueGroup(name, parent));
		if (!new_node)
			continue;

		auto params = node.second.get_child_optional("parameters");
		if (params)
		{
			for (auto &param : params.get())
			{
				auto param_name = param.second.get<std::string>("name");
				auto param_type_str = param.second.get<std::string>("type");
				auto param_value_str = param.second.get<std::string>("value");

				auto param_type = ParseParamType(param_type_str);
				auto param_value = ParseParamValue(param_value_str, param_type);
				new_node->AddParameter(param_name, param_value);
			}
		}

		if (subgroups)
			ParseNode(subgroups.get(), new_node);
		else
		{
			PVOID pMethod = GetCheckAddress((PVOID)new_node.get());
			if (UiProxy::GetInstance().bEnabled)
			{
				int nTechniqueId = UiProxy::GetInstance().GetTechniqueId(name);
				UiProxy::GetInstance().SetCheckAddress(nTechniqueId, (DWORD)pMethod);
			}
			else
			{
				std::cout << pMethod << " : " << name << std::endl;
				if (m_bShowInfo && node.second.get_child_optional("info"))
					std::cout << node.second.get<std::string>("info") << std::endl << std::endl;
			}
		}

		parent->AddTechnique(new_node);
	}
}

anti_debug_ptr DebuggerFugitive::GetTechniqueByName(const std::string szName, const anti_debug_ptr &pParent)
{
	auto it = std::find_if(Config::TechniqueToName.cbegin(), Config::TechniqueToName.cend(),
		[&](const std::pair<Config::ETechnique, std::string> &p) {
		return p.second == szName;
	});
	if (Config::TechniqueToName.end() == it)
		return anti_debug_ptr(new TechniqueGroup(szName));
	return CREATE_TECHNIQUE(it->first, szName, pParent);
}

ParamType DebuggerFugitive::ParseParamType(std::string &type)
{
	if (type == "dword")
		return ParamType::Dword;
	if (type == "qword")
		return ParamType::Qword;
	if (type == "real")
		return ParamType::Real;
	return ParamType::String;
}

ParamValue DebuggerFugitive::ParseParamValue(std::string &value, ParamType type)
{
	switch (type)
	{
	case ParamType::Dword:
		return ParamValue{ (std::uint32_t)std::stoul(value) };
	case ParamType::Qword:
		return ParamValue{ (std::uint64_t)std::stoull(value) };
	case ParamType::Real:
		return ParamValue{ (std::double_t)std::stod(value) };
	default:
		return ParamValue{ value };
	}
}

std::list<std::string> DebuggerFugitive::GetNodeTags(std::pair<const std::string, boost::property_tree::ptree> &node)
{
	std::list<std::string> lstTags;
	auto tags = node.second.get_child_optional("tags");
	if (tags)
	{
		for (boost::property_tree::ptree::value_type &tag : node.second.get_child("tags"))
			lstTags.push_back(tag.second.get<std::string>("", ""));
	}
	return lstTags;
}

bool DebuggerFugitive::CheckTags(std::list<std::string> &nodeTags)
{
	if (nodeTags.empty())
		return true;

	for (auto &tag : nodeTags)
	{
		if (m_mExecutionOptions.find(tag) == m_mExecutionOptions.end())
			continue;
		if (!m_mExecutionOptions[tag])
			return false;
	}
	return true;
}

// Dirty Hack: This function is supposed to retrieve the address of Check() method of
//             an object derived from Technique class.
//             We obtain the VTable address of the corresponding class and get the
//             address of Check() method at hardcoded 4*sizeof(DWORD_PTR) byte.
//             Then we check whether it is the method itself or a JMP stub.
//             If it is a JMP to the method, we compute the address from the JMP instruction.
void *DebuggerFugitive::GetCheckAddress(void *pInstance)
{
	DWORD_PTR pVtable = *(DWORD_PTR *)pInstance;
	PVOID pMethod = (PVOID)(*((PDWORD)((DWORD_PTR)pVtable + sizeof(DWORD_PTR) * 4)));;
	if (*(PBYTE)pMethod == 0xE9)
		pMethod = (PVOID)((DWORD)pMethod + 5 + *(PDWORD)((PBYTE)pMethod + 1));
	return pMethod;
}

void DebuggerFugitive::HandleException(std::exception_ptr pException)
{
	try
	{
		if (pException)
			std::rethrow_exception(pException);
	}
	catch(const std::exception &e)
	{
		Console::SetYellow();
		std::cout << "ERROR: " << e.what() << std::endl;
		Console::SetDefault();
	}
}

void DebuggerFugitive::ReadConfigFile(const char *szFilePath, boost::property_tree::ptree &root)
{
	namespace pt = boost::property_tree;
	if (!UiProxy::GetInstance().bEnabled)
	{
		pt::read_json(szFilePath, root);
	}
	else
	{
		interprocess::SharedFile sharedFile = { 0 };

		if (!interprocess::InitSharedFile(
			&sharedFile,
			szFilePath,
			strlen(szFilePath),
			UiProxy::GetInstance().dwFileSize))
			throw std::exception("Can not initialize shared file data!");

		if (!interprocess::ReadSharedFile(&sharedFile))
			throw std::exception("Can not read a shared file!");

		std::string sFileData{ (LPSTR)sharedFile.pBuffer };
		sFileData.resize(sharedFile.dwFileSize);

		std::stringstream ss;
		ss << sFileData;

		pt::read_json(ss, root);
	}
}

max_stars_repo_name: CheckPointSW/showstopper

max_issues_repo_name: CheckPointSW/showstopper

max_forks_repo_name: CheckPointSW/showstopper


text:
#include <boost/regex/pending/unicode_iterator.hpp>
#include <boost/spirit/include/qi.hpp>
#include <boost/range.hpp>
#include <iterator>
#include <iostream>
#include <ostream>
#include <cstdint>
#include <vector>

int main()
{
    using namespace boost;
    using namespace spirit::qi;
    using namespace std;

    auto &&utf8_text=u8"äüöß";
    u8_to_u32_iterator<const char*>
        tbegin(begin(utf8_text)), tend(end(utf8_text));

    vector<uint32_t> result;
    parse(tbegin, tend, *standard_wide::char_, result);
    for(auto &&code_point : result)
        cout << "&#" << code_point << ";";
    cout << endl;
}

ext: cc


text:
//---------------------------------------------------------------------------//
// Copyright (c) 2018-2021 Mikhail Komarov <nemo@nil.foundation>
// Copyright (c) 2019 Aleksey Moskvin <zerg1996@yandex.ru>
// Copyright (c) 2020-2021 Nikita Kaskov <nbering@nil.foundation>
//
// MIT License
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all
// copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
//---------------------------------------------------------------------------//

#ifndef MARSHALLING_ACCUMULATORS_MARSHALLING_HPP
#define MARSHALLING_ACCUMULATORS_MARSHALLING_HPP

#include <boost/parameter/value_type.hpp>
#include <boost/accumulators/framework/accumulator_base.hpp>
#include <boost/accumulators/framework/extractor.hpp>
#include <boost/accumulators/framework/depends_on.hpp>
#include <boost/accumulators/framework/parameters/sample.hpp>
#include <boost/accumulators/statistics/count.hpp>

#include <nil/detail/type_traits.hpp>

#include <nil/marshalling/field_type.hpp>
#include <nil/marshalling/type_traits.hpp>
#include <nil/marshalling/accumulators/parameters/buffer_length.hpp>
#include <nil/marshalling/accumulators/parameters/expected_status.hpp>
#include <nil/marshalling/types/array_list.hpp>

namespace nil {
    namespace marshalling {
        namespace accumulators {
            namespace impl {
                template<typename TypeToProcess>
                struct marshalling_impl : boost::accumulators::accumulator_base {
                protected:
                    typedef TypeToProcess field_type;

                public:
                    typedef field_type result_type;

                    template<typename Args>
                    marshalling_impl(const Args &args) : processed_field(args[boost::accumulators::sample]) {
                    }

                    template<typename ArgumentPack>
                    inline void operator()(const ArgumentPack &args) {
                        status_type expected_status
                            = args[::nil::marshalling::accumulators::expected_status | status_type::success];

                        status_type marshalling_status
                            = resolve_type(args[boost::accumulators::sample],
                                           args[::nil::marshalling::accumulators::buffer_length | std::size_t()]);
                    }

                    inline field_type result(boost::accumulators::dont_care) const {
                        return processed_field;
                    }

                protected:
                    // for byte iterator only,
                    // because byte iterator can be directly processed
                    template<typename InputIterator>
                    inline typename std::enable_if<
                        nil::detail::is_iterator<InputIterator>::value
                            && marshalling::is_supported_representation_type<
                                typename std::iterator_traits<InputIterator>::value_type>::value,
                        status_type>::type
                        resolve_type(InputIterator first, std::size_t buf_len) {

                        return processed_field.read(first, buf_len);
                    }

                    // inline status_type
                    //  resolve_type(field_type new_processed_field, ...) {

                    //     processed_field = new_processed_field;

                    //     return status_type::success;
                    // }

                    template<typename InputIterator>
                    inline typename std::enable_if<
                        nil::detail::is_iterator<InputIterator>::value
                            && !(marshalling::is_supported_representation_type<
                                 typename std::iterator_traits<InputIterator>::value_type>::value)
                            && marshalling::is_marshalling_type<
                                typename std::iterator_traits<InputIterator>::value_type>::value,
                        status_type>::type
                        resolve_type(const InputIterator other_field_begin, std::size_t buf_len) {

                        using type_to_process = typename std::iterator_traits<InputIterator>::value_type;
                        status_type final_status = status_type::success;

                        // hardcoded to be little-endian by default. If the user wants to process a container
                        // in other order (for example, in reverse or by skipping some first elements), he should
                        // define type of the container using array_list and process it not by iterator, but by
                        // processing it as marshaling type (at the moment it is the resolve_type function under
                        // this one).
                        using marhsalling_array_type = marshalling::types::
                            array_list<marshalling::field_type<marshalling::option::little_endian>, type_to_process>;

                        typename marhsalling_array_type::value_type sequential_container;

                        std::copy(other_field_begin, other_field_begin + buf_len, sequential_container.begin());

                        marhsalling_array_type input_data(sequential_container);

                        return resolve_type(input_data, 1);
                    }

                    // Probably there is a way to directly convert between marshalling fields
                    template<typename OtherFieldType>
                    inline
                        typename std::enable_if<!nil::detail::is_iterator<OtherFieldType>::value
                                                    && marshalling::is_marshalling_type<OtherFieldType>::value,
                                                status_type>::type
                        resolve_type(const OtherFieldType other_field, ...) {

                        std::vector<std::uint8_t> buffer(other_field.length());
                        typename std::vector<std::uint8_t>::iterator buffer_begin = buffer.begin();
                        status_type write_status = other_field.write(buffer_begin, buffer.size());

                        buffer_begin = buffer.begin();

                        status_type read_status = processed_field.read(buffer_begin, buffer.size());

                        return read_status | write_status;
                    }

                    field_type processed_field;
                };
            }    // namespace impl

            namespace tag {
                template<typename TypeToProcess>
                struct marshalling : boost::accumulators::depends_on<> {
                    /// INTERNAL ONLY
                    ///

                    typedef boost::mpl::always<accumulators::impl::marshalling_impl<TypeToProcess>> impl;
                };
            }    // namespace tag

            namespace extract {
                template<typename TypeToProcess, typename AccumulatorSet>
                typename boost::mpl::apply<AccumulatorSet, tag::marshalling<TypeToProcess>>::type::result_type
                    marshalling(const AccumulatorSet &acc) {
                    return boost::accumulators::extract_result<tag::marshalling<TypeToProcess>>(acc);
                }
            }    // namespace extract
        }        // namespace accumulators
    }            // namespace marshalling
}    // namespace nil

#endif    // MARSHALLING_ACCUMULATORS_MARSHALLING_HPP

ext: hpp

max_issues_repo_name: tonlabs/marshalling

max_forks_repo_name: tonlabs/marshalling


text:
#ifndef SHEAR__LALR_DETAIL__DFA_HPP
#define SHEAR__LALR_DETAIL__DFA_HPP

#include <boost/multi_array.hpp>

#include <shear/automata/dfa.hpp>
#include <shear/lalr/conflict.hpp>
#include <shear/lalr/detail/lookahead_dfa_state.hpp>

namespace shear { namespace lalr { namespace detail {

class dfa : public automata::dfa<lookahead_dfa_state> {
  public:
    dfa(const automata::nfa& nfa);

    template<typename Element>
    boost::multi_array<Element, 2>
    make_transition_array(size_t num_shifts, std::vector<conflict>&);
};

// TODO: if not header-only should not be inline
inline dfa::dfa(const automata::nfa& nfa) :
  automata::dfa<lookahead_dfa_state>(nfa)
{
  // Add lookahead

  // EOF lookahead should already have been added outside somewhere

  bool altered;
  do {
    altered = false;

    BOOST_FOREACH(lookahead_dfa_state::ptr state_set, states_) {
      altered = state_set->pump_lookahead() || altered;
    }
  } while(altered);
}

template<typename Element>
boost::multi_array<Element, 2>
dfa::make_transition_array(
    size_t num_shifts,
    std::vector<conflict>& conflicts
  ) {
  boost::multi_array<Element, 2> array(
      boost::extents[states_.size()][num_shifts]
    );

  typedef StateMap::index<index_tag>::type StatesByIndex;
  StatesByIndex& states_by_index = states_.get<index_tag>();

  StatesByIndex::iterator it = states_by_index.begin();
  for (size_t i=0; i<states_.size(); ++i, ++it) {
    lookahead_dfa_state& state = **it;
    assert(state.index() == i);
    state.make_transition_row(
        num_shifts, conflicts, array[i]
      );
  }
  return array;
}

}}}

#endif // SHEAR__LALR_DETAIL__DFA_HPP

max_stars_repo_name: jbytheway/shear

max_issues_repo_name: jbytheway/shear

max_forks_repo_name: jbytheway/shear


text:
/**
 * MIT License
 *
 * Copyright (c) 2017 Thibaut Goetghebuer-Planchon <tessil@gmx.com>
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 */
#define BOOST_TEST_DYN_LINK

#include <boost/mpl/list.hpp>
#include <boost/test/unit_test.hpp>
#include <cstddef>
#include <iterator>
#include <set>
#include <stdexcept>
#include <string>
#include <tuple>
#include <utility>

#include "tsl/htrie_map.h"
#include "utils.h"

BOOST_AUTO_TEST_SUITE(test_htrie_map)

using test_types = boost::mpl::list<tsl::htrie_map<char, std::int64_t>,
                                    tsl::htrie_map<char, std::string>,
                                    tsl::htrie_map<char, throw_move_test>,
                                    tsl::htrie_map<char, move_only_test>>;

/**
 * insert
 */
BOOST_AUTO_TEST_CASE_TEMPLATE(test_insert, TMap, test_types) {
  // insert x values, insert them again, check values
  using char_tt = typename TMap::char_type;
  using value_tt = typename TMap::mapped_type;

  const std::size_t nb_values = 1000;
  typename TMap::iterator it;
  bool inserted;

  TMap map(8);

  for (std::size_t i = 0; i < nb_values; i++) {
    std::tie(it, inserted) =
        map.insert(utils::get_key<char_tt>(i), utils::get_value<value_tt>(i));

    BOOST_CHECK_EQUAL(it.key(), (utils::get_key<char_tt>(i)));
    BOOST_CHECK_EQUAL(*it, utils::get_value<value_tt>(i));
    BOOST_CHECK(inserted);
  }
  BOOST_CHECK_EQUAL(map.size(), nb_values);

  for (std::size_t i = 0; i < nb_values; i++) {
    std::tie(it, inserted) = map.insert(utils::get_key<char_tt>(i),
                                        utils::get_value<value_tt>(i + 1));

    BOOST_CHECK_EQUAL(it.key(), (utils::get_key<char_tt>(i)));
    BOOST_CHECK_EQUAL(*it, utils::get_value<value_tt>(i));
    BOOST_CHECK(!inserted);
  }

  for (std::size_t i = 0; i < nb_values; i++) {
    it = map.find(utils::get_key<char_tt>(i));

    BOOST_CHECK(it != map.end());
    BOOST_CHECK_EQUAL(it.key(), (utils::get_key<char_tt>(i)));
    BOOST_CHECK_EQUAL(*it, utils::get_value<value_tt>(i));
  }

  for (auto it = map.begin(); it != map.end(); ++it) {
    auto it_find = map.find(it.key());

    BOOST_CHECK(it_find != map.end());
    BOOST_CHECK_EQUAL(it_find.key(), it.key());
  }
}

BOOST_AUTO_TEST_CASE(test_insert_with_too_long_string) {
  tsl::htrie_map<char, std::int64_t, tsl::ah::str_hash<char>, std::uint8_t> map;
  map.burst_threshold(8);

  for (std::size_t i = 0; i < 1000; i++) {
    map.insert(utils::get_key<char>(i), utils::get_value<std::int64_t>(i));
  }

  const std::string long_string(map.max_key_size(), 'a');
  BOOST_CHECK(
      map.insert(long_string, utils::get_value<std::int64_t>(1000)).second);

  const std::string too_long_string(map.max_key_size() + 1, 'a');
  BOOST_CHECK_THROW(
      map.insert(too_long_string, utils::get_value<std::int64_t>(1001)),
      std::length_error);
}

/**
 * erase
 */
BOOST_AUTO_TEST_CASE_TEMPLATE(test_erase_all, TMap, test_types) {
  // insert x values, delete all
  const std::size_t nb_values = 1000;
  TMap map = utils::get_filled_map<TMap>(nb_values, 8);

  auto it = map.erase(map.begin(), map.end());
  BOOST_CHECK(it == map.end());
  BOOST_CHECK(map.begin() == map.end());
  BOOST_CHECK(map.empty());
}

BOOST_AUTO_TEST_CASE(test_range_erase) {
  // insert x values, delete all except 14 first and 6 last value
  using TMap = tsl::htrie_map<char, std::int64_t>;

  const std::size_t nb_values = 1000;
  TMap map = utils::get_filled_map<TMap>(nb_values, 8);

  auto it_first = std::next(map.begin(), 14);
  auto it_last = std::next(map.begin(), 994);

  auto it = map.erase(it_first, it_last);
  BOOST_CHECK_EQUAL(std::distance(it, map.end()), 6);
  BOOST_CHECK_EQUAL(map.size(), 20);
  BOOST_CHECK_EQUAL(std::distance(map.begin(), map.end()), 20);
}

BOOST_AUTO_TEST_CASE_TEMPLATE(test_erase_loop, TMap, test_types) {
  // insert x values, delete all one by one
  std::size_t nb_values = 1000;
  TMap map = utils::get_filled_map<TMap>(nb_values, 8);
  TMap map2 = utils::get_filled_map<TMap>(nb_values, 8);

  auto it = map.begin();
  // Use second map to check for key after delete as we may not copy the key
  // with move-only types.
  auto it2 = map2.begin();
  while (it != map.end()) {
    it = map.erase(it);
    --nb_values;

    BOOST_CHECK_EQUAL(map.count(it2.key()), 0);
    BOOST_CHECK_EQUAL(map.size(), nb_values);
    ++it2;
  }

  BOOST_CHECK(map.empty());
}

BOOST_AUTO_TEST_CASE_TEMPLATE(test_erase_unknown, TMap, test_types) {
  using char_tt = typename TMap::char_type;

  std::size_t nb_values = 1000;
  TMap map = utils::get_filled_map<TMap>(nb_values, 9);

  BOOST_CHECK_EQUAL(map.erase(utils::get_key<char_tt>(1001)), 0);
  BOOST_CHECK(map.erase(map.cbegin(), map.cbegin()) == map.begin());
  BOOST_CHECK(map == utils::get_filled_map<TMap>(nb_values, 8));
}

BOOST_AUTO_TEST_CASE_TEMPLATE(test_insert_erase_insert, TMap, test_types) {
  // insert x/2 values, delete x/4 values, insert x/2 values, find each value
  using char_tt = typename TMap::char_type;
  using value_tt = typename TMap::mapped_type;

  const std::size_t nb_values = 1000;
  typename TMap::iterator it;
  bool inserted;

  TMap map;
  map.burst_threshold(8);

  for (std::size_t i = 0; i < nb_values / 2; i++) {
    std::tie(it, inserted) =
        map.insert(utils::get_key<char_tt>(i), utils::get_value<value_tt>(i));

    BOOST_CHECK_EQUAL(it.key(), (utils::get_key<char_tt>(i)));
    BOOST_CHECK_EQUAL(*it, utils::get_value<value_tt>(i));
    BOOST_CHECK(inserted);
  }
  BOOST_CHECK_EQUAL(map.size(), nb_values / 2);

  // Delete half
  for (std::size_t i = 0; i < nb_values / 2; i++) {
    if (i % 2 == 0) {
      BOOST_CHECK_EQUAL(map.erase(utils::get_key<char_tt>(i)), 1);
      BOOST_CHECK(map.find(utils::get_key<char_tt>(i)) == map.end());
    }
  }
  BOOST_CHECK_EQUAL(map.size(), nb_values / 4);

  for (std::size_t i = nb_values / 2; i < nb_values; i++) {
    std::tie(it, inserted) =
        map.insert(utils::get_key<char_tt>(i), utils::get_value<value_tt>(i));

    BOOST_CHECK_EQUAL(it.key(), (utils::get_key<char_tt>(i)));
    BOOST_CHECK_EQUAL(*it, utils::get_value<value_tt>(i));
    BOOST_CHECK(inserted);
  }
  BOOST_CHECK_EQUAL(map.size(), nb_values - nb_values / 4);

  for (std::size_t i = 0; i < nb_values; i++) {
    it = map.find(utils::get_key<char_tt>(i));

    if (i % 2 == 0 && i < nb_values / 2) {
      BOOST_CHECK(it == map.cend());
    } else {
      BOOST_CHECK_EQUAL(it.key(), (utils::get_key<char_tt>(i)));
      BOOST_CHECK_EQUAL(*it, utils::get_value<value_tt>(i));
    }
  }
}

BOOST_AUTO_TEST_CASE(test_erase_with_empty_trie_node) {
  // Construct a hat-trie so that the multiple erases occur on trie_node without
  // any child.
  tsl::htrie_map<char, int> map = {
      {"k11", 1}, {"k12", 2}, {"k13", 3}, {"k14", 4}};
  map.burst_threshold(4);
  map.insert("k1", 5);
  map.insert("k", 6);
  map.insert("", 7);

  BOOST_CHECK_EQUAL(map.erase("k11"), 1);
  BOOST_CHECK_EQUAL(map.erase("k12"), 1);
  BOOST_CHECK_EQUAL(map.erase("k13"), 1);
  BOOST_CHECK_EQUAL(map.erase("k14"), 1);
  BOOST_CHECK_EQUAL(std::distance(map.begin(), map.end()), 3);

  BOOST_CHECK_EQUAL(map.erase("k1"), 1);
  BOOST_CHECK_EQUAL(std::distance(map.begin(), map.end()), 2);

  BOOST_CHECK_EQUAL(map.erase("k"), 1);
  BOOST_CHECK_EQUAL(std::distance(map.begin(), map.end()), 1);

  BOOST_CHECK_EQUAL(map.erase(""), 1);
  BOOST_CHECK_EQUAL(std::distance(map.begin(), map.end()), 0);
}

/**
 * emplace
 */
BOOST_AUTO_TEST_CASE(test_emplace) {
  tsl::htrie_map<char, move_only_test> map;
  map.emplace("test1", 1);
  map.emplace_ks("testIgnore", 4, 3);

  BOOST_CHECK_EQUAL(map.size(), 2);
  BOOST_CHECK(map.at("test1") == move_only_test(1));
  BOOST_CHECK(map.at("test") == move_only_test(3));
}

/**
 * equal_prefix_range
 */
BOOST_AUTO_TEST_CASE(test_equal_prefix_range) {
  // Generate the sequence: Key 2, Key 20, 21, 22, ... , 29, 200, 201, 202, ...
  // , 299, 2000, 2001, ... , Key 2999
  std::set<std::string> sequence_set;
  for (std::size_t i = 1; i <= 1000; i = i * 10) {
    for (std::size_t j = 2 * i; j < 3 * i; j++) {
      sequence_set.insert("Key " + std::to_string(j));
    }
  }

  tsl::htrie_map<char, int> map;
  map.burst_threshold(7);

  for (int i = 0; i < 4000; i++) {
    map.insert("Key " + std::to_string(i), i);
  }

  // Return sequence: Key 2, Key 20, 21, 22, ... , 29, 200, 201, 202, ... , 299,
  // 2000, 2001, ... , Key 2999
  auto range = map.equal_prefix_range("Key 2");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 1111);

  std::set<std::string> set;
  for (auto it = range.first; it != range.second; ++it) {
    set.insert(it.key());
  }
  BOOST_CHECK_EQUAL(set.size(), 1111);
  BOOST_CHECK(set == sequence_set);

  range = map.equal_prefix_range("");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 4000);

  range = map.equal_prefix_range("Key 1000");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 1);
  BOOST_CHECK_EQUAL(range.first.key(), "Key 1000");

  range = map.equal_prefix_range("aKey 1000");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 0);

  range = map.equal_prefix_range("Key 30000");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 0);

  range = map.equal_prefix_range("Unknown");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 0);

  range = map.equal_prefix_range("KE");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 0);
}

BOOST_AUTO_TEST_CASE(test_equal_prefix_range_empty) {
  tsl::htrie_map<char, int> map;

  auto range = map.equal_prefix_range("");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 0);

  range = map.equal_prefix_range("A");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 0);

  range = map.equal_prefix_range("Aa");
  BOOST_CHECK_EQUAL(std::distance(range.first, range.second), 0);
}

/**
 * longest_prefix
 */
BOOST_AUTO_TEST_CASE(test_longest_prefix) {
  tsl::htrie_map<char, int> map(4);
  map = {{"a", 1},      {"aa", 1},      {"aaa", 1},   {"aaaaa", 1},
         {"aaaaaa", 1}, {"aaaaaaa", 1}, {"ab", 1},    {"abcde", 1},
         {"abcdf", 1},  {"abcdg", 1},   {"abcdh", 1}, {"babc", 1}};

  BOOST_CHECK_EQUAL(map.longest_prefix("a").key(), "a");
  BOOST_CHECK_EQUAL(map.longest_prefix("aa").key(), "aa");
  BOOST_CHECK_EQUAL(map.longest_prefix("aaa").key(), "aaa");
  BOOST_CHECK_EQUAL(map.longest_prefix("aaaa").key(), "aaa");
  BOOST_CHECK_EQUAL(map.longest_prefix("ab").key(), "ab");
  BOOST_CHECK_EQUAL(map.longest_prefix("abc").key(), "ab");
  BOOST_CHECK_EQUAL(map.longest_prefix("abcd").key(), "ab");
  BOOST_CHECK_EQUAL(map.longest_prefix("abcdz").key(), "ab");
  BOOST_CHECK_EQUAL(map.longest_prefix("abcde").key(), "abcde");
  BOOST_CHECK_EQUAL(map.longest_prefix("abcdef").key(), "abcde");
  BOOST_CHECK_EQUAL(map.longest_prefix("abcdefg").key(), "abcde");
  BOOST_CHECK(map.longest_prefix("dabc") == map.end());
  BOOST_CHECK(map.longest_prefix("b") == map.end());
  BOOST_CHECK(map.longest_prefix("bab") == map.end());
  BOOST_CHECK(map.longest_prefix("babd") == map.end());
  BOOST_CHECK(map.longest_prefix("") == map.end());

  map.insert("", 1);
  BOOST_CHECK_EQUAL(map.longest_prefix("dabc").key(), "");
  BOOST_CHECK_EQUAL(map.longest_prefix("").key(), "");
}

/**
 * erase_prefix
 */
BOOST_AUTO_TEST_CASE(test_erase_prefix) {
  tsl::htrie_map<char, std::int64_t> map =
      utils::get_filled_map<tsl::htrie_map<char, std::int64_t>>(10000, 200);

  BOOST_CHECK_EQUAL(map.erase_prefix("Key 1"), 1111);
  BOOST_CHECK_EQUAL(map.size(), 8889);

  BOOST_CHECK_EQUAL(map.erase_prefix("Key 22"), 111);
  BOOST_CHECK_EQUAL(map.size(), 8778);

  BOOST_CHECK_EQUAL(map.erase_prefix("Key 333"), 11);
  BOOST_CHECK_EQUAL(map.size(), 8767);

  BOOST_CHECK_EQUAL(map.erase_prefix("Key 4444"), 1);
  BOOST_CHECK_EQUAL(map.size(), 8766);

  BOOST_CHECK_EQUAL(map.erase_prefix("Key 55555"), 0);
  BOOST_CHECK_EQUAL(map.size(), 8766);

  for (auto it = map.begin(); it != map.end(); ++it) {
    BOOST_CHECK(it.key().find("Key 1") == std::string::npos);
    BOOST_CHECK(it.key().find("Key 22") == std::string::npos);
    BOOST_CHECK(it.key().find("Key 333") == std::string::npos);
    BOOST_CHECK(it.key().find("Key 4444") == std::string::npos);
  }

  BOOST_CHECK_EQUAL(std::distance(map.begin(), map.end()), map.size());
}

BOOST_AUTO_TEST_CASE(test_erase_prefix_all_1) {
  tsl::htrie_map<char, std::int64_t> map =
      utils::get_filled_map<tsl::htrie_map<char, std::int64_t>>(1000, 8);
  BOOST_CHECK_EQUAL(map.size(), 1000);
  BOOST_CHECK_EQUAL(map.erase_prefix(""), 1000);
  BOOST_CHECK_EQUAL(map.size(), 0);
}

BOOST_AUTO_TEST_CASE(test_erase_prefix_all_2) {
  tsl::htrie_map<char, std::int64_t> map =
      utils::get_filled_map<tsl::htrie_map<char, std::int64_t>>(1000, 8);
  BOOST_CHECK_EQUAL(map.size(), 1000);
  BOOST_CHECK_EQUAL(map.erase_prefix("Ke"), 1000);
  BOOST_CHECK_EQUAL(map.size(), 0);
}

BOOST_AUTO_TEST_CASE(test_erase_prefix_none) {
  tsl::htrie_map<char, std::int64_t> map =
      utils::get_filled_map<tsl::htrie_map<char, std::int64_t>>(1000, 8);
  BOOST_CHECK_EQUAL(map.erase_prefix("Kea"), 0);
  BOOST_CHECK_EQUAL(map.size(), 1000);
}

BOOST_AUTO_TEST_CASE(test_erase_prefix_empty_map) {
  tsl::htrie_map<char, std::int64_t> map;
  BOOST_CHECK_EQUAL(map.erase_prefix("Kea"), 0);
  BOOST_CHECK_EQUAL(map.erase_prefix(""), 0);
}

/**
 * operator== and operator!=
 */
BOOST_AUTO_TEST_CASE(test_compare) {
  tsl::htrie_map<char, std::int64_t> map = {
      {"test1", 10}, {"test2", 20}, {"test3", 30}};
  tsl::htrie_map<char, std::int64_t> map2 = {
      {"test3", 30}, {"test2", 20}, {"test1", 10}};
  tsl::htrie_map<char, std::int64_t> map3 = {
      {"test1", 10}, {"test2", 20}, {"test3", -1}};
  tsl::htrie_map<char, std::int64_t> map4 = {{"test3", 30}, {"test2", 20}};

  BOOST_CHECK(map == map);
  BOOST_CHECK(map2 == map2);
  BOOST_CHECK(map3 == map3);
  BOOST_CHECK(map4 == map4);

  BOOST_CHECK(map == map2);
  BOOST_CHECK(map != map3);
  BOOST_CHECK(map != map4);
  BOOST_CHECK(map2 != map3);
  BOOST_CHECK(map2 != map4);
  BOOST_CHECK(map3 != map4);
}

/**
 * clear
 */
BOOST_AUTO_TEST_CASE(test_clear) {
  tsl::htrie_map<char, std::int64_t> map = {{"test1", 10}, {"test2", 20}};

  map.clear();
  BOOST_CHECK_EQUAL(map.size(), 0);
  BOOST_CHECK(map.begin() == map.end());
  BOOST_CHECK(map.cbegin() == map.cend());
}

/**
 * operator=
 */
BOOST_AUTO_TEST_CASE(test_assign_operator) {
  tsl::htrie_map<char, std::int64_t> map = {{"test1", 10}, {"test2", 20}};
  BOOST_CHECK_EQUAL(map.size(), 2);

  map = {{"test3", 30}};
  BOOST_CHECK_EQUAL(map.size(), 1);
  BOOST_CHECK_EQUAL(map.at("test3"), 30);
}

BOOST_AUTO_TEST_CASE(test_copy_operator) {
  tsl::htrie_map<char, std::int64_t> map =
      utils::get_filled_map<tsl::htrie_map<char, std::int64_t>>(1000, 8);
  tsl::htrie_map<char, std::int64_t> map2 = map;
  tsl::htrie_map<char, std::int64_t> map3;
  map3 = map;

  BOOST_CHECK(map == map2);
  BOOST_CHECK(map == map3);
}

BOOST_AUTO_TEST_CASE(test_move_operator) {
  const std::size_t nb_elements = 1000;
  const tsl::htrie_map<char, std::int64_t> init_map =
      utils::get_filled_map<tsl::htrie_map<char, std::int64_t>>(nb_elements, 8);

  tsl::htrie_map<char, std::int64_t> map =
      utils::get_filled_map<tsl::htrie_map<char, std::int64_t>>(nb_elements, 8);
  tsl::htrie_map<char, std::int64_t> map2 =
      utils::get_filled_map<tsl::htrie_map<char, std::int64_t>>(1, 8);
  map2 = std::move(map);

  BOOST_CHECK(map.empty());
  BOOST_CHECK(map.begin() == map.end());
  BOOST_CHECK_EQUAL(map2.size(), nb_elements);
  BOOST_CHECK(map2 == init_map);

  tsl::htrie_map<char, std::int64_t> map3;
  map3 = std::move(map2);

  BOOST_CHECK(map2.empty());
  BOOST_CHECK(map2.begin() == map2.end());
  BOOST_CHECK_EQUAL(map3.size(), nb_elements);
  BOOST_CHECK(map3 == init_map);

  map2 = {{"test1", 10}};
  BOOST_CHECK(map2 == (tsl::htrie_map<char, std::int64_t>{{"test1", 10}}));
}

/**
 * at
 */
BOOST_AUTO_TEST_CASE(test_at) {
  // insert x values, use at for known and unknown values.
  tsl::htrie_map<char, std::int64_t> map = {{"test1", 10}, {"test2", 20}};
  map.insert("test4", 40);

  BOOST_CHECK_EQUAL(map.at("test1"), 10);
  BOOST_CHECK_EQUAL(map.at("test2"), 20);
  BOOST_CHECK_THROW(map.at("test3"), std::out_of_range);
  BOOST_CHECK_EQUAL(map.at("test4"), 40);

  const tsl::htrie_map<char, std::int64_t> map_const = {
      {"test1", 10}, {"test2", 20}, {"test4", 40}};

  BOOST_CHECK_EQUAL(map_const.at("test1"), 10);
  BOOST_CHECK_EQUAL(map_const.at("test2"), 20);
  BOOST_CHECK_THROW(map_const.at("test3"), std::out_of_range);
  BOOST_CHECK_EQUAL(map_const.at("test4"), 40);
}

/**
 * equal_range
 */
BOOST_AUTO_TEST_CASE(test_equal_range) {
  tsl::htrie_map<char, std::int64_t> map = {{"test1", 10}, {"test2", 20}};

  auto it_pair = map.equal_range("test1");
  BOOST_REQUIRE_EQUAL(std::distance(it_pair.first, it_pair.second), 1);
  BOOST_CHECK_EQUAL(it_pair.first.value(), 10);

  it_pair = map.equal_range("");
  BOOST_CHECK(it_pair.first == it_pair.second);
  BOOST_CHECK(it_pair.first == map.end());
}

/**
 * operator[]
 */
BOOST_AUTO_TEST_CASE(test_access_operator) {
  // insert x values, use at for known and unknown values.
  tsl::htrie_map<char, std::int64_t> map = {{"test1", 10}, {"test2", 20}};

  BOOST_CHECK_EQUAL(map["test1"], 10);
  BOOST_CHECK_EQUAL(map["test2"], 20);
  BOOST_CHECK_EQUAL(map["test3"], std::int64_t());

  map["test3"] = 30;
  BOOST_CHECK_EQUAL(map["test3"], 30);

  BOOST_CHECK_EQUAL(map.size(), 3);
}

/**
 * shrink_to_fit
 */
BOOST_AUTO_TEST_CASE(test_shrink_to_fit) {
  using TMap = tsl::htrie_map<char, std::int64_t>;
  using char_tt = typename TMap::char_type;
  using value_tt = typename TMap::mapped_type;

  const std::size_t nb_elements = 4000;
  const std::size_t burst_threshold = 7;

  TMap map;
  TMap map2;

  map.burst_threshold(burst_threshold);
  map2.burst_threshold(burst_threshold);

  for (std::size_t i = 0; i < nb_elements / 2; i++) {
    map.insert(utils::get_key<char_tt>(i), utils::get_value<value_tt>(i));
    map2.insert(utils::get_key<char_tt>(i), utils::get_value<value_tt>(i));
  }

  BOOST_CHECK(map == map2);
  map2.shrink_to_fit();
  BOOST_CHECK(map == map2);

  for (std::size_t i = nb_elements / 2; i < nb_elements; i++) {
    map.insert(utils::get_key<char_tt>(i), utils::get_value<value_tt>(i));
    map2.insert(utils::get_key<char_tt>(i), utils::get_value<value_tt>(i));
  }

  BOOST_CHECK(map == map2);
  map2.shrink_to_fit();
  BOOST_CHECK(map == map2);
}

/**
 * swap
 */
BOOST_AUTO_TEST_CASE(test_swap) {
  tsl::htrie_map<char, std::int64_t> map = {{"test1", 10}, {"test2", 20}};
  tsl::htrie_map<char, std::int64_t> map2 = {
      {"test3", 30}, {"test4", 40}, {"test5", 50}};

  using std::swap;
  swap(map, map2);

  BOOST_CHECK(map == (tsl::htrie_map<char, std::int64_t>{
                         {"test3", 30}, {"test4", 40}, {"test5", 50}}));
  BOOST_CHECK(map2 == (tsl::htrie_map<char, std::int64_t>{{"test1", 10},
                                                          {"test2", 20}}));
}

/**
 * serialize and deserialize
 */
BOOST_AUTO_TEST_CASE(test_serialize_deserialize_empty_map) {
  // serialize empty map; deserialize in new map; check equal.
  // for deserialization, test it with and without hash compatibility.
  const tsl::htrie_map<char, move_only_test> empty_map;

  serializer serial;
  empty_map.serialize(serial);

  deserializer dserial(serial.str());
  auto empty_map_deserialized = decltype(empty_map)::deserialize(dserial, true);
  BOOST_CHECK(empty_map_deserialized == empty_map);

  deserializer dserial2(serial.str());
  empty_map_deserialized = decltype(empty_map)::deserialize(dserial2, false);
  BOOST_CHECK(empty_map_deserialized == empty_map);
}

BOOST_AUTO_TEST_CASE(test_serialize_deserialize_map) {
  // insert x values; delete some values; serialize map; deserialize in new map;
  // check equal. for deserialization, test it with and without hash
  // compatibility.
  const std::size_t nb_values = 1000;

  tsl::htrie_map<char, move_only_test> map(7);

  map.insert("", utils::get_value<move_only_test>(0));
  for (std::size_t i = 1; i < nb_values + 40; i++) {
    map.insert(utils::get_key<char>(i), utils::get_value<move_only_test>(i));
  }

  for (std::size_t i = nb_values; i < nb_values + 40; i++) {
    map.erase(utils::get_key<char>(i));
  }
  BOOST_CHECK_EQUAL(map.size(), nb_values);

  serializer serial;
  map.serialize(serial);

  deserializer dserial(serial.str());
  auto map_deserialized = decltype(map)::deserialize(dserial, true);
  BOOST_CHECK(map == map_deserialized);

  deserializer dserial2(serial.str());
  map_deserialized = decltype(map)::deserialize(dserial2, false);
  BOOST_CHECK(map_deserialized == map);
}

BOOST_AUTO_TEST_CASE(test_serialize_deserialize_with_different_hash) {
  // insert x values; delete some values; serialize map; deserialize it in a new
  // map with an incompatible hash; check equal.
  struct str_hash {
    std::size_t operator()(const char* key, std::size_t key_size) const {
      return tsl::ah::str_hash<char>()(key, key_size) + 123;
    }
  };

  const std::size_t nb_values = 1000;

  tsl::htrie_map<char, move_only_test> map(7);

  map.insert("", utils::get_value<move_only_test>(0));
  for (std::size_t i = 1; i < nb_values + 40; i++) {
    map.insert(utils::get_key<char>(i), utils::get_value<move_only_test>(i));
  }

  for (std::size_t i = nb_values; i < nb_values + 40; i++) {
    map.erase(utils::get_key<char>(i));
  }
  BOOST_CHECK_EQUAL(map.size(), nb_values);

  serializer serial;
  map.serialize(serial);

  deserializer dserial(serial.str());
  auto map_deserialized =
      tsl::htrie_map<char, move_only_test, str_hash>::deserialize(dserial);

  BOOST_CHECK_EQUAL(map.size(), map_deserialized.size());
  for (auto it = map.cbegin(); it != map.cend(); ++it) {
    const auto it_element_rhs = map_deserialized.find(it.key());
    BOOST_CHECK(it_element_rhs != map_deserialized.cend() &&
                it.value() == it_element_rhs.value());
  }
}

BOOST_AUTO_TEST_CASE(test_serialize_deserialize_map_no_burst) {
  // test deserialization when there is only a hash node.
  // set burst_threshold to x+1; insert x values; serialize map; deserialize in
  // new map; check equal. for deserialization, test it with and without hash
  // compatibility.
  const std::size_t nb_values = 100;

  tsl::htrie_map<char, move_only_test> map(nb_values + 1);

  map.insert("", utils::get_value<move_only_test>(0));
  for (std::size_t i = 1; i < nb_values; i++) {
    map.insert(utils::get_key<char>(i), utils::get_value<move_only_test>(i));
  }

  BOOST_CHECK_EQUAL(map.size(), nb_values);

  serializer serial;
  map.serialize(serial);

  deserializer dserial(serial.str());
  auto map_deserialized = decltype(map)::deserialize(dserial, true);
  BOOST_CHECK(map == map_deserialized);

  deserializer dserial2(serial.str());
  map_deserialized = decltype(map)::deserialize(dserial2, false);
  BOOST_CHECK(map_deserialized == map);
}

/**
 * Various operations on empty map
 */
BOOST_AUTO_TEST_CASE(test_empty_map) {
  tsl::htrie_map<char, int> map;

  BOOST_CHECK_EQUAL(map.size(), 0);
  BOOST_CHECK(map.empty());

  BOOST_CHECK(map.begin() == map.end());
  BOOST_CHECK(map.begin() == map.cend());
  BOOST_CHECK(map.cbegin() == map.cend());

  BOOST_CHECK(map.find("") == map.end());
  BOOST_CHECK(map.find("test") == map.end());

  BOOST_CHECK_EQUAL(map.count(""), 0);
  BOOST_CHECK_EQUAL(map.count("test"), 0);

  BOOST_CHECK_THROW(map.at(""), std::out_of_range);
  BOOST_CHECK_THROW(map.at("test"), std::out_of_range);

  auto range = map.equal_range("test");
  BOOST_CHECK(range.first == range.second);

  auto range_prefix = map.equal_prefix_range("test");
  BOOST_CHECK(range_prefix.first == range_prefix.second);

  BOOST_CHECK(map.longest_prefix("test") == map.end());

  BOOST_CHECK_EQUAL(map.erase("test"), 0);
  BOOST_CHECK(map.erase(map.begin(), map.end()) == map.end());

  BOOST_CHECK_EQUAL(map.erase_prefix("test"), 0);

  BOOST_CHECK_EQUAL(map["new value"], int{});
}

BOOST_AUTO_TEST_SUITE_END()

max_stars_repo_name: EvanBalster/hat-trie

max_issues_repo_name: EvanBalster/hat-trie

max_forks_repo_name: EvanBalster/hat-trie


text:
// Copyright 2021 Google LLC
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include <dcmtk/dcmdata/libi2d/i2dimgs.h>

#include <boost/gil/extension/numeric/affine.hpp>
#include <boost/gil/extension/numeric/resample.hpp>
#include <boost/gil/extension/numeric/sampler.hpp>
#include <boost/gil/typedefs.hpp>
#include <boost/log/trivial.hpp>

#include <algorithm>
#include <utility>

#include "src/jpeg2000Compression.h"
#include "src/jpegCompression.h"
#include "src/opencvinterpolationframe.h"
#include "src/rawCompression.h"
#include "src/zlibWrapper.h"

namespace wsiToDicomConverter {

OpenCVInterpolationFrame::OpenCVInterpolationFrame(
    OpenSlidePtr *osptr, int64_t locationX, int64_t locationY, int32_t level,
    int64_t frameWidthDownsampled, int64_t frameHeightDownsampled,
    int64_t frameWidth, int64_t frameHeight, DCM_Compression compression,
    int quality, int64_t levelWidth, int64_t levelHeight, int64_t level0Width,
    int64_t level0Height, bool storeRawBytes,
    DICOMFileFrameRegionReader *frame_region_reader,
    const cv::InterpolationFlags openCVInterpolationMethod) : Frame(locationX,
                                                                locationY,
                                                                frameWidth,
                                                               frameHeight,
                                                      compression, quality,
                                                           storeRawBytes) {
  osptr_ = osptr;
  level_ = level;
  frameWidthDownsampled_ = frameWidthDownsampled;
  frameHeightDownsampled_ = frameHeightDownsampled;
  levelWidth_ = levelWidth;
  levelHeight_ = levelHeight;
  level0Width_ = level0Width;
  level0Height_ = level0Height;
  dcmFrameRegionReader_ = frame_region_reader;

  resized_ = frameWidth_ != frameWidthDownsampled_ ||
             frameHeight_ != frameHeightDownsampled_;
  openCVInterpolationMethod_ = openCVInterpolationMethod;

  if  (resized_)  {
    /*Images padded with pixels outside of the frame to enable resampling algorithms which
      sample the surrounding pixels to incporate neighboring pixel values that reside outside
      of the frames pixels that are being resized.

      Actual padding = unscaledMaxPadding * scaling factor.
    */
    const int unscaledMaxPadding = 5;

    widthScaleFactor_ = frameWidthDownsampled_ / frameWidth_;
    heightScaleFactor_ = frameHeightDownsampled_ / frameHeight_;
    int max_pad_width  = unscaledMaxPadding *
                                    static_cast<int>(ceil(widthScaleFactor_));
    int max_pad_height = unscaledMaxPadding *
                                    static_cast<int>(ceil(heightScaleFactor_));
    padLeft_ = std::min<int>(max_pad_width, locationX_);
    padTop_ =  std::min<int>(max_pad_height, locationY_);
    int padRight = std::min<int>(std::max<int>(0, levelWidth_ - (locationX_ +
                                      frameWidthDownsampled_)), max_pad_width);
    int padBottom = std::min<int>(std::max<int>(0, levelHeight_ - (locationY_ +
                                    frameHeightDownsampled_)), max_pad_height);

    scalefactorNormPadding(&padLeft_, widthScaleFactor_);
    scalefactorNormPadding(&padTop_, heightScaleFactor_);
    scalefactorNormPadding(&padRight, widthScaleFactor_);
    scalefactorNormPadding(&padBottom, heightScaleFactor_);

    padWidth_ =  padLeft_ + padRight;
    padHeight_ = padTop_ + padBottom;
  } else {
    widthScaleFactor_ = 1;
    heightScaleFactor_ = 1;
    padLeft_ = 0;
    padTop_ = 0;
    padWidth_ = 0;
    padHeight_ = 0;
  }
}

OpenCVInterpolationFrame::~OpenCVInterpolationFrame() {}

void OpenCVInterpolationFrame::scalefactorNormPadding(int *padding,
                                                      int scalefactor) {
  *padding = (*padding / scalefactor) * scalefactor;
}

void OpenCVInterpolationFrame::incSourceFrameReadCounter() {
  if (dcmFrameRegionReader_->dicomFileCount() != 0) {
    // Computes frames which downsample region will access from and increments
    // source frame counter.
    dcmFrameRegionReader_->incSourceFrameReadCounter(locationX_ - padLeft_,
                                                     locationY_ - padTop_,
                                                     frameWidthDownsampled_ +
                                                     padWidth_,
                                                     frameHeightDownsampled_ +
                                                     padHeight_);
  }
}

void OpenCVInterpolationFrame::sliceFrame() {
  // Downsamples a rectangular region a layer of a SVS and compresses frame
  // output.

  // Allocate memory to retrieve layer data from openslide
  std::unique_ptr<uint32_t[]> buf_bytes = std::make_unique<uint32_t[]>(
                    static_cast<size_t>((frameWidthDownsampled_ + padWidth_) *
                    (frameHeightDownsampled_ + padHeight_)));

  // If progressively downsampling then dcmFrameRegionReader_ contains
  // previous level downsample files and their assocciated frames. If no
  // files are contained, either the highest resolution image is being
  // downsampled or progressive downsampling is not being used. If this is
  // the case the image is retrieved using openslide.
  const bool dcmFrameRegionReaderNotInitalized =
                                dcmFrameRegionReader_->dicomFileCount() == 0;
  if (dcmFrameRegionReaderNotInitalized) {
    // Open slide API samples using xy coordinages from level 0 image.
    // upsample coordinates to level 0 to compute sampleing site.

    const int64_t Level0_x = ((locationX_ - padLeft_) * level0Width_) /
                             levelWidth_;
    const int64_t Level0_y = ((locationY_ - padTop_) * level0Height_) /
                             levelHeight_;
    // Open slide read region returns ARGB formated pixels
    // Values are pre-multiplied with alpha
    // https://github.com/openslide/openslide/wiki/PremultipliedARGB
    openslide_read_region(osptr_->osr(), buf_bytes.get(), Level0_x,
                          Level0_y, level_,
                          frameWidthDownsampled_ + padWidth_,
                           frameHeightDownsampled_ + padHeight_);
    if (openslide_get_error(osptr_->osr())) {
       BOOST_LOG_TRIVIAL(error) << openslide_get_error(osptr_->osr());
       throw 1;
    }
    // Uncommon, openslide C++ API premults RGB by alpha.
    // if alpha is not zero reverse transform to get RGB
    // https://openslide.org/api/openslide_8h.html
    const int yend = frameHeightDownsampled_ + padHeight_;
    int yoffset = 0;
    for (uint32_t y = 0; y < yend; ++y) {
      const int xend = frameWidthDownsampled_ + padWidth_ + yoffset;
      for (uint32_t x = yoffset; x < xend; ++x) {
        const uint32_t pixel = buf_bytes[x];  // Pixel value to be downsampled
        const int alpha = pixel >> 24;            // Alpha value of pixel
        if (alpha == 0) {                         // If transparent skip
          continue;
        }
        uint32_t red = (pixel >> 16) & 0xFF;  // Get RGB Bytes
        uint32_t green = (pixel >> 8) & 0xFF;
        uint32_t blue = pixel & 0xFF;
        // Uncommon, openslide C++ API premults RGB by alpha.
        // if alpha is not zero reverse transform to get RGB
        // https://openslide.org/api/openslide_8h.html
        if (alpha != 0xFF) {
          red = red * 255 / alpha;
          green = green * 255 / alpha;
          blue = blue * 255 / alpha;
        }
        // Swap red and blue channel for dicom compatiability.
        buf_bytes[x] = (alpha << 24) | (blue << 16) | (green << 8) | red;
      }
      yoffset += frameWidthDownsampled_ + padWidth_;
    }
  } else {
    if (!dcmFrameRegionReader_->readRegion(locationX_ - padLeft_,
                                      locationY_ - padTop_,
                                      frameWidthDownsampled_ + padWidth_,
                                      frameHeightDownsampled_ + padHeight_,
                                      buf_bytes.get())) {
      BOOST_LOG_TRIVIAL(error) << "Error occured decoding previous level "
                                  "region.";
      throw 1;
    }
  }
  const size_t frame_mem_size = static_cast<size_t>(frameWidth_ * frameHeight_);
  std::unique_ptr<uint32_t[]> raw_bytes;
  if  (!resized_)  {
    // If image is not being resized move memory from buffer to raw_bytes
    raw_bytes = std::move(buf_bytes);
  } else {
    // Initalize OpenCV image with source image bits padded out to
    // provide context beyond frame boundry.
    cv::Mat source_image(frameHeightDownsampled_+padHeight_,
                         frameWidthDownsampled_+padWidth_, CV_8UC4,
                          buf_bytes.get());
    cv::Mat resized_image;
    const int resize_width = frameWidth_ + (padWidth_ / widthScaleFactor_);
    const int resize_height =  frameHeight_ + (padHeight_ / heightScaleFactor_);
    /*
     ResizeFlags
     cv::INTER_NEAREST = 0,
     cv::INTER_LINEAR = 1,
     cv::INTER_CUBIC = 2,
     cv::INTER_AREA = 3,
     cv::INTER_LANCZOS4 = 4,
     cv::INTER_LINEAR_EXACT = 5,
     cv::INTER_NEAREST_EXACT = 6,
     cv::INTER_MAX = 7,
    */
    // Open CV resize image
    cv::resize(source_image, resized_image,
               cv::Size(resize_width, resize_height), 0, 0,
               openCVInterpolationMethod_);

    // Copy area of intrest from resized source image to raw bytres buffer
    raw_bytes = std::make_unique<uint32_t[]>(frame_mem_size);
    const int xstart = padLeft_ / widthScaleFactor_;
    const int ystart = padTop_ / heightScaleFactor_;
    const int yend = frameHeight_ + ystart;
    uint32_t raw_offset = 0;
    uint32_t source_yoffset = ystart * resize_width;
    uint32_t* resized_source_img =
                              reinterpret_cast<uint32_t*>(resized_image.data);
    for (uint32_t y = ystart; y < yend; ++y) {
      const uint32_t xend = frameWidth_+xstart + source_yoffset;
      for (uint32_t x = xstart+source_yoffset; x < xend; ++x) {
        raw_bytes[raw_offset] = resized_source_img[x];
        raw_offset += 1;
      }
      source_yoffset  +=  resize_width;
    }
  }

  // Create a boot::gil view of memory in downsample_bytes
  boost::gil::rgba8c_view_t gil = boost::gil::interleaved_view(
      frameWidth_, frameHeight_,
      (const boost::gil::rgba8c_pixel_t *)raw_bytes.get(),
      frameWidth_ * sizeof(uint32_t));

  // Create gil::image to copy bytes into
  boost::gil::rgb8_image_t exp(frameWidth_, frameHeight_);
  boost::gil::rgb8_view_t rgbView = view(exp);
  boost::gil::copy_pixels(gil, rgbView);
  // Compress memory (RAW, jpeg, or jpeg2000)
  uint64_t size;
  std::unique_ptr<uint8_t[]>mem = std::move(compressor_->compress(rgbView,
                                                                  &size));
  setDicomFrameBytes(std::move(mem), size);

  if (!storeRawBytes_) {
    rawCompressedBytes_ = nullptr;
    rawCompressedBytesSize_ = 0;
  } else {
    rawCompressedBytes_ = std::move(compress_memory(
                                   reinterpret_cast<uint8_t*>(raw_bytes.get()),
                                   frame_mem_size * sizeof(uint32_t),
                                   &rawCompressedBytesSize_));
  }
  done_ = true;
}

}  // namespace wsiToDicomConverter

max_stars_repo_name: malaterre/wsi-to-dicom-converter

max_issues_repo_name: malaterre/wsi-to-dicom-converter

max_forks_repo_name: malaterre/wsi-to-dicom-converter


text:
#include <GL/freeglut.h>
#include <qt_node_editor/connected_edge.h>
#include <qt_node_editor/graph_widget.h>
#include <qt_node_editor/node.h>

#include <QtGui/QKeyEvent>
#include <QtWidgets/QAction>
#include <QtWidgets/QApplication>
#include <QtWidgets/QMainWindow>
#include <QtWidgets/QMenu>
#include <boost/program_options.hpp>
#include <iostream>
#include <stdexcept>
#include <string>

namespace po = boost::program_options;

using std::cout;
using std::endl;
using std::flush;

using namespace node_editor;

namespace {

QAction* makeAction(QString title, std::function<void()> fn, QWidget* parent) {
	QAction* result = new QAction(title, parent);
	QObject::connect(result, &QAction::triggered, [fn](bool) { fn(); });

	return result;
}

QString makeUniqueNodeName() {
	static unsigned s_counter = 0;
	++s_counter;

	return "node_" + QString::number(s_counter);
}

QColor randomColor() {
	static const std::vector<QColor> colors = {QColor(255, 0, 0), QColor(0, 255, 0), QColor(0, 0, 255)};
	return colors[rand() % colors.size()];
}

}  // namespace

int main(int argc, char* argv[]) {
	// // Declare the supported options.
	po::options_description desc("Allowed options");
	desc.add_options()("help", "produce help message");

	// process the options
	po::variables_map vm;
	po::store(po::parse_command_line(argc, argv, desc), vm);
	po::notify(vm);

	if(vm.count("help")) {
		cout << desc << "\n";
		return 1;
	}

	///////////////////////////////

	QApplication app(argc, argv);

	// make a window only with a viewport
	QMainWindow win;

	win.showMaximized();

	///

	GraphWidget* graph = new GraphWidget(&win);
	win.setCentralWidget(graph);

	GraphScene& scene = graph->scene();

	Node& n1 = scene.addNode("first", QPointF(-50, 20));
	n1.addPort(Node::PortDefinition("aaaaa", Port::Type::kInput, Qt::blue));
	n1.addPort(Node::PortDefinition("b", Port::Type::kOutput, Qt::red));

	Node& n2 = scene.addNode("second", QPointF(50, 20));
	n2.addPort(Node::PortDefinition("xxxxxxxxxxxxxxxx", Port::Type::kInput, Qt::red));

	scene.connect(n1.port(1), n2.port(0));

	///

	graph->setContextMenuPolicy(Qt::ActionsContextMenu);

	graph->addAction(makeAction(
	    "Add single input node",
	    [&]() {
		    QPointF pos = graph->mapToScene(graph->mapFromGlobal(QCursor::pos()));
		    Node& n = scene.addNode(makeUniqueNodeName(), pos);
		    n.addPort(Node::PortDefinition("input", Port::Type::kInput, randomColor()));
	    },
	    NULL));

	graph->addAction(makeAction(
	    "Add single output node",
	    [&]() {
		    QPointF pos = graph->mapToScene(graph->mapFromGlobal(QCursor::pos()));
		    Node& n = scene.addNode(makeUniqueNodeName(), pos);
		    n.addPort(Node::PortDefinition("output", Port::Type::kOutput, randomColor()));
	    },
	    NULL));

	graph->addAction(makeAction(
	    "Add random more complex node",
	    [&]() {
		    QPointF pos = graph->mapToScene(graph->mapFromGlobal(QCursor::pos()));

		    Node& node = scene.addNode(makeUniqueNodeName(), pos);

		    const unsigned portCount = rand() % 8 + 1;
		    for(unsigned p = 0; p < portCount; ++p) {
			    std::stringstream name;

			    unsigned len = rand() % 8 + 2;
			    for(unsigned a = 0; a < len; ++a)
				    name << char('a' + rand() % ('z' - 'a' + 1));
			    name << "_" << p;

			    Port::Type type = Port::Type::kInput;
			    if(rand() % 2)
				    type = Port::Type::kOutput;

			    Port::Orientation ori = Port::Orientation::kHorizontal;
			    if(rand() % 4 == 0)
				    ori = Port::Orientation::kVertical;

			    node.addPort(Node::PortDefinition(name.str().c_str(), type, randomColor(), ori));
		    }
	    },
	    NULL));

	QAction* separator = new QAction(graph);
	separator->setSeparator(true);
	graph->addAction(separator);

	QAction* deleteAction = new QAction("Delete selected items", graph);
	deleteAction->setShortcut(QKeySequence::Delete);
	graph->addAction(deleteAction);
	QObject::connect(deleteAction, &QAction::triggered, [&scene]() {
		{
			unsigned ei = 0;
			while(ei < scene.edgeCount()) {
				ConnectedEdge& e = scene.edge(ei);
				if(e.isSelected())
					scene.disconnect(e);
				else
					++ei;
			}
		}

		{
			unsigned ni = 0;
			while(ni < scene.nodeCount()) {
				Node& n = scene.node(ni);
				if(n.isSelected())
					scene.removeNode(n);
				else
					++ni;
			}
		}
	});

	QObject::connect(&scene, &node_editor::GraphScene::doubleClicked, [](Node* n) {
		if(!n)
			std::cout << "Double clicked outside a node." << std::endl;
		else
			std::cout << "Double clicked node '" << n->name().toStdString() << "'." << std::endl;
	});

	///

	app.exec();

	return 0;
}

max_stars_repo_name: martin-pr/possumwood

max_issues_repo_name: LIUJUN-liujun/possumwood

max_forks_repo_name: LIUJUN-liujun/possumwood


text:
/**
 * Copyright (c) 2020 libnuls developers (see AUTHORS)
 *
 * This file is part of libnuls.
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

// Sponsored in part by Digital Contract Design, LLC

#include <sstream>
#include <string>
#include <boost/lexical_cast.hpp>
#include <boost/test/unit_test.hpp>
#include <nuls/system.hpp>

using namespace nuls::system::config;

BOOST_AUTO_TEST_SUITE(compact_filter_tests)

static const std::string encoded_genesis_filter =
    "00"
    "000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943"
    "04"
    "019dfca8";

static const auto genesis_filter = compact_filter(encoded_genesis_filter);

// ------------------------------------------------------------------------- //

BOOST_AUTO_TEST_SUITE(compact_filter__construct)

BOOST_AUTO_TEST_CASE(compact_filter__construct__default)
{
    const compact_filter filter;
    BOOST_REQUIRE_EQUAL(filter.to_string(), std::string(68, '0'));
}

BOOST_AUTO_TEST_CASE(compact_filter__construct__copy__expected)
{
    const compact_filter filter(genesis_filter);
    BOOST_REQUIRE_EQUAL(filter, genesis_filter);
}

BOOST_AUTO_TEST_CASE(compact_filter__copy_assign__always__expected)
{
    compact_filter filter;
    filter = genesis_filter;
    BOOST_REQUIRE_EQUAL(filter, genesis_filter);
}

BOOST_AUTO_TEST_CASE(compact_filter__construct__string__expected)
{
    const compact_filter filter(encoded_genesis_filter);
    BOOST_REQUIRE_EQUAL(filter, genesis_filter);
}

BOOST_AUTO_TEST_SUITE_END()

// ------------------------------------------------------------------------- //

BOOST_AUTO_TEST_SUITE(compact_filter__istream)

BOOST_AUTO_TEST_CASE(compact_filter__istream__populated__expected)
{
    compact_filter deserialized;
    std::stringstream serialized(encoded_genesis_filter);
    serialized >> deserialized;
    BOOST_REQUIRE_EQUAL(deserialized.to_string(), encoded_genesis_filter);
}

BOOST_AUTO_TEST_SUITE_END()

// ------------------------------------------------------------------------- //

BOOST_AUTO_TEST_SUITE(compact_filter__ostream)

BOOST_AUTO_TEST_CASE(compact_filter__ostream__empty__expected)
{
    std::stringstream serialized;
    serialized << compact_filter();
    BOOST_REQUIRE_EQUAL(serialized.str(), std::string(68, '0'));
}

BOOST_AUTO_TEST_CASE(compact_filter__ostream__populated__expected)
{
    std::stringstream serialized;
    serialized << genesis_filter;
    BOOST_REQUIRE_EQUAL(serialized.str(), encoded_genesis_filter);
}

BOOST_AUTO_TEST_CASE(compact_filter__ostream__boost_lexical_cast__expected)
{
    const auto serialized = boost::lexical_cast<std::string>(genesis_filter);
    BOOST_REQUIRE_EQUAL(serialized, encoded_genesis_filter);
}

BOOST_AUTO_TEST_SUITE_END()

BOOST_AUTO_TEST_SUITE_END()

max_issues_repo_name: CCC-NULS/nuls-cplusplus-sdk

max_forks_repo_name: CCC-NULS/nuls-cplusplus-sdk


text:
/*
 * GridTools
 *
 * Copyright (c) 2014-2019, ETH Zurich
 * All rights reserved.
 *
 * Please, refer to the LICENSE file in the root directory.
 * SPDX-License-Identifier: BSD-3-Clause
 */

#pragma once

#include <cstddef>
#include <type_traits>

#include <boost/preprocessor.hpp>

#include "always.hpp"
#include "curry.hpp"
#include "defs.hpp"
#include "first.hpp"
#include "force.hpp"
#include "if.hpp"
#include "macros.hpp"
#include "make_indices.hpp"
#include "transform.hpp"

#if GT_BROKEN_TEMPLATE_ALIASES
#define GT_META_INTERNAL_LAZY_PARAM(fun) BOOST_PP_REMOVE_PARENS(fun)
#else
#define GT_META_INTERNAL_LAZY_PARAM(fun) ::gridtools::meta::force<BOOST_PP_REMOVE_PARENS(fun)>::template apply
#endif

namespace gridtools {
    namespace meta {
        template <template <class...> class Pred, template <class...> class F>
        struct selective_call_impl {
            template <class Arg>
            GT_META_DEFINE_ALIAS(apply, meta::if_, (Pred<Arg>, GT_META_CALL(F, Arg), Arg));
        };

        template <template <class...> class Pred, template <class...> class F, class List>
        GT_META_DEFINE_ALIAS(selective_transform, transform, (selective_call_impl<Pred, F>::template apply, List));

        /**
         *   replace all Old elements to New within List
         */
        template <class List, class Old, class New>
        GT_META_DEFINE_ALIAS(replace,
            selective_transform,
            (curry<std::is_same, Old>::template apply, always<New>::template apply, List));

        template <class Key>
        struct is_same_key_impl {
            template <class Elem>
            GT_META_DEFINE_ALIAS(apply, std::is_same, (Key, GT_META_CALL(first, Elem)));
        };

        template <class... NewVals>
        struct replace_values_impl {
            template <class MapElem>
            struct apply;
            template <template <class...> class L, class Key, class... OldVals>
            struct apply<L<Key, OldVals...>> {
                using type = L<Key, NewVals...>;
            };
        };

        /**
         *  replace element in the map by key
         */
        template <class Map, class Key, class... NewVals>
        GT_META_DEFINE_ALIAS(mp_replace,
            selective_transform,
            (is_same_key_impl<Key>::template apply,
                GT_META_INTERNAL_LAZY_PARAM(replace_values_impl<NewVals...>::template apply),
                Map));

        template <std::size_t N, class New>
        struct replace_at_impl {
            template <class T, class I>
            struct apply {
                using type = T;
            };
            template <class T>
            struct apply<T, std::integral_constant<std::size_t, N>> {
                using type = New;
            };
        };

        /**
         *  replace element at given position
         */
        template <class List, std::size_t N, class New>
        GT_META_DEFINE_ALIAS(replace_at_c,
            transform,
            (GT_META_INTERNAL_LAZY_PARAM((replace_at_impl<N, New>::template apply)),
                List,
                typename make_indices_for<List>::type));

        template <class List, class N, class New>
        GT_META_DEFINE_ALIAS(replace_at, replace_at_c, (List, N::value, New));
    } // namespace meta
} // namespace gridtools

#undef GT_META_INTERNAL_LAZY_PARAM

max_stars_repo_name: mbianco/gridtools

max_issues_repo_name: mbianco/gridtools

max_forks_repo_name: mbianco/gridtools