text:
/* vim:set ts=3 sw=3 sts=3 et: */
/**
 * Copyright © 2008-2013 Last.fm Limited
 *
 * This file is part of libmoost.
 *
 * 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 MOOST_CONTAINER_MEMORY_MAPPED_DATASET_DATASET_HPP__
#define MOOST_CONTAINER_MEMORY_MAPPED_DATASET_DATASET_HPP__

#include <string>
#include <stdexcept>
#include <fstream>
#include <sstream>
#include <algorithm>
#include <cstring>

#include <boost/archive/text_iarchive.hpp>
#include <boost/archive/text_oarchive.hpp>
#include <boost/serialization/string.hpp>
#include <boost/serialization/map.hpp>
#include <boost/iostreams/device/mapped_file.hpp>
#include <boost/type_traits/is_pod.hpp>
#include <boost/lexical_cast.hpp>
#include <boost/noncopyable.hpp>
#include <boost/cstdint.hpp>

#include "config.hpp"

namespace moost { namespace container {

/**
 * Representation of a memory-mapped dataset
 *
 * Each instance of this class represents a memory-mapped dataset.
 * Sections within the dataset can be accessed using accessor classes,
 * e.g. mmd_vector, mmd_hash_multimap or mmd_archive.
 *
 * The dataset class as well as the accessor classes contain writer
 * classes than be used to easily implement methods for writing a
 * dataset to disk.
 */
class memory_mapped_dataset : public boost::noncopyable
{
private:
   static const boost::uint32_t MMD_MAGIC = 0x7473614C;    ///< helps us to identify the file and verify byte order
   static const boost::uint32_t MMD_VERSION = 1;           ///< increment in case of incompatible format changes

   static const size_t MAP_PAGE_SIZE = 4096;               ///< page size used for "warming" the mapping cache

   /**
    * The dataset file header
    *
    * Contains the magic and version as well as the offset and length of
    * the index archive. The index as well as the sections can be placed
    * at an arbitrary position within the dataset, though usually the
    * index will be the last part of the dataset. (As in a good book!)
    */
   struct mmd_header // must be POD
   {
      boost::uint32_t mmd_magic;              ///< magic number, must be set to MMD_MAGIC
      boost::uint32_t mmd_version;            ///< current format version, must be MMD_VERSION
      boost::uint64_t index_offset;           ///< offset of the index archive
      boost::uint64_t index_length;           ///< length of the index archive
   };

public:
   /**
    * Section information
    *
    * This class is used to store and access information about a single
    * section in the dataset, such as the offset at which the section is
    * located, the type of the section and attributes associated with
    * this section.
    *
    * Instances of this class can be serialised and deserialised using
    * boost::archive.
    *
    * This class is usually only used by section accessor classes.
    */
   class section_info
   {
   private:
      typedef std::map<std::string, std::string> attribute_map_type;

   public:
      section_info()
         : m_offset(0)
         , m_alignment(0)
      {
      }

      section_info(const std::string& type, size_t alignment)
         : m_type(type)
         , m_offset(0)
         , m_alignment(alignment)
      {
      }

      boost::uint64_t offset() const
      {
         return m_offset;
      }

      size_t alignment() const
      {
         return m_alignment;
      }

      void set_offset(boost::uint64_t offset)
      {
         m_offset = offset;
      }

      template <typename T>
      void setattr(const std::string& name, const T& value)
      {
         m_attributes[name] = boost::lexical_cast<std::string>(value);
      }

      template <typename T>
      const T getattr(const std::string& name) const
      {
         attribute_map_type::const_iterator it = m_attributes.find(name);

         if (it == m_attributes.end())
         {
            throw std::runtime_error("no such attribute " + name);
         }

         return boost::lexical_cast<T>(it->second);
      }

      const std::string& type() const
      {
         return m_type;
      }

   private:
      friend class boost::serialization::access;

      template <class Archive>
      void serialize(Archive & ar, const unsigned int /* version */)
      {
         ar & m_type & m_offset & m_attributes;
      }

      std::string m_type;
      boost::uint64_t m_offset;
      const size_t m_alignment;
      attribute_map_type m_attributes;
   };

   typedef std::map<std::string, section_info> section_map_type;

   /**
    * Dataset writer
    *
    * This class is used to aid dataset creation. It handles all writing
    * of data to the dataset file and keeps track of all its sections.
    * It also takes care of aligning sections properly and writing the
    * section index.
    *
    * Most of its methods are supposed to be called only by section
    * creating accessors.
    */
   class writer
   {
   public:
      /**
       * Dataset writer constructor
       *
       * Used to open a dataset file for writing.
       *
       * \param map_file_name       name of the file to write
       * \param dataset_name        name of the dataset, used for validation
       *                            when reading the file
       * \param format_version      dataset format version, used for validation
       *                            when reading the file
       */
      writer(const std::string& map_file_name, const std::string& dataset_name, boost::uint32_t format_version)
         : m_ofs(map_file_name.c_str(), std::ios::binary | std::ios::trunc)
         , m_dataset_name(dataset_name)
         , m_format_version(format_version)
      {
         if (!m_ofs)
         {
            throw std::runtime_error("failed to open file " + map_file_name);
         }

         if (dataset_name.empty())
         {
            throw std::runtime_error("empty dataset name");
         }

         m_header.mmd_magic = MMD_MAGIC;
         m_header.mmd_version = MMD_VERSION;
         m_header.index_offset = 0;
         m_header.index_length = 0;

         write(m_header);
      }

      ~writer()
      {
         try
         {
            close();
         }
         catch (...)
         {
         }
      }

      /**
       * Close the dataset file
       *
       * This method should always be called explicitly in order to avoid
       * hidden exceptions when it is called by the destructor.
       */
      void close()
      {
         if (m_ofs.is_open())
         {
            m_header.index_offset = m_ofs.tellp();
            boost::archive::text_oarchive oa(m_ofs);
            oa << m_dataset_name << m_format_version << m_section_map;
            m_header.index_length = static_cast<boost::uint64_t>(m_ofs.tellp()) - m_header.index_offset;
            m_ofs.seekp(0);
            write(m_header);
            m_ofs.close();
         }
      }

      void create_section(const std::string& name, const std::string& type, size_t alignment)
      {
         if (name.empty())
         {
            throw std::runtime_error("invalid empty section name");
         }

         if (type.empty())
         {
            throw std::runtime_error("invalid empty section type");
         }

         if (alignment == 0 || (alignment & (alignment - 1)) != 0)
         {
            throw std::runtime_error("alignment must be a power of 2");
         }

         std::pair<section_map_type::iterator, bool> rv = m_section_map.insert(std::make_pair(name, section_info(type, alignment)));

         if (!rv.second)
         {
            throw std::runtime_error("attempt to create duplicate section " + name);
         }
      }

      void uncreate_section(const std::string& name)
      {
         if (name.empty())
         {
            throw std::runtime_error("invalid empty section name");
         }

         section_map_type::iterator it = m_section_map.find(name);

         if (it == m_section_map.end())
         {
            throw std::runtime_error("attempt to uncreate non-existent section " + name);
         }

         if (it->second.offset())
         {
            throw std::runtime_error("cannot uncreate section " + name + " that has already been written to");
         }

         m_section_map.erase(it);
      }

      void write(const std::string& section, const char *data, size_t size)
      {
         set_active_section(section);
         m_ofs.write(data, size);
      }

      void commit_section(const std::string& section)
      {
         set_active_section(section);
      }

      template <typename T>
      void setattr(const std::string& section, const std::string& attr, const T& value)
      {
         find(section).setattr(attr, value);
      }

   private:
      section_info& find(const std::string& section)
      {
         section_map_type::iterator it = m_section_map.find(section);

         if (it == m_section_map.end())
         {
            throw std::runtime_error("no such section " + section);
         }

         return it->second;
      }

      template <typename T>
      void write(const T& data)
      {
         m_ofs.write(reinterpret_cast<const char *>(&data), sizeof(data));
      }

      void set_active_section(const std::string& section)
      {
         // Yeah, this is slightly inefficient, but it's only being used at
         // dataset creation time.
         if (section != m_active_section)
         {
            section_info& sec = find(section);

            // We have to ensure that only one section is written at a time.
            if (sec.offset() > 0)
            {
               throw std::runtime_error("interleaved write access to section " + section);
            }

            align_stream(sec.alignment());
            sec.set_offset(m_ofs.tellp());
            m_active_section = section;
         }
      }

      void align_stream(size_t alignment)
      {
         while (m_ofs.tellp() % alignment)
         {
            m_ofs.put(0);
         }
      }

      section_map_type m_section_map;
      std::string m_active_section;
      std::ofstream m_ofs;
      const std::string m_dataset_name;
      const boost::uint32_t m_format_version;
      mmd_header m_header;
   };

   /**
    * Memory-mapped dataset constructor
    *
    * Used to map an existing on-disk dataset into memory. Performs a whole
    * variety of checks to ensure the dataset is consistent and matches the
    * specification given by dataset_name and format_version.
    *
    * \param map_file_name       name of the dataset file to map into memory
    * \param dataset_name        name of the dataset, used for validation
    * \param format_version      dataset format version, used for validation
    */
   memory_mapped_dataset(const std::string& map_file_name,
                         const std::string& dataset_name,
                         boost::uint32_t format_version)
      : m_file(map_file_name)
      , m_format(dataset_name)
   {
      try
      {
         m_map.open(m_file, boost::iostreams::mapped_file::readonly);
      }
      catch (const BOOST_IOSTREAMS_FAILURE& fail)
      {
         // otherwise it's a real pain to figure out which file it's actually complaining about
         throw BOOST_IOSTREAMS_FAILURE(m_file + ": " + fail.what());
      }

      const mmd_header *hdr = data<mmd_header>();

      if (hdr->mmd_magic != MMD_MAGIC)
      {
         throw std::runtime_error(m_file + ": invalid magic");
      }

      if (hdr->mmd_version != MMD_VERSION)
      {
         throw std::runtime_error(m_file + ": unsupported version");
      }

      if (hdr->index_offset == 0 || hdr->index_length == 0)
      {
         throw std::runtime_error(m_file + ": corrupted file");
      }

      std::string indexstr(data<char>(hdr->index_offset, hdr->index_length), hdr->index_length);
      std::istringstream iss(indexstr);

      std::string dset_name;
      boost::uint32_t fmt_version;

      boost::archive::text_iarchive ia(iss);
      ia >> dset_name >> fmt_version >> m_section_map;

      if (dset_name != dataset_name)
      {
         throw std::runtime_error(m_file + ": unexpected format name: " + dset_name + " (expected " + dataset_name + ")");
      }

      if (fmt_version != format_version)
      {
         std::ostringstream oss;
         oss << m_file << ": unsupported format version: " << fmt_version << " (expected " << format_version << ")";
         throw std::runtime_error(oss.str());
      }
   }

   std::string description() const
   {
      return m_format + " (" + m_file + ")";
   }

   /**
    * Find a section in the dataset's index
    *
    * Will throw an exception if the section cannot be found or is corrupt.
    *
    * \param section        section name
    * \param type           section type
    *
    * \returns reference to a section_info object describing the section
    */
   const section_info& find(const std::string& section, const std::string& type) const
   {
      section_map_type::const_iterator it = m_section_map.find(section);

      if (it == m_section_map.end())
      {
         throw std::runtime_error(m_file + ": no such section " + section);
      }

      if (it->second.offset() == 0)
      {
         throw std::runtime_error(m_file + ": corrupt section " + section);
      }

      if (it->second.type() != type)
      {
         throw std::runtime_error(m_file + ": invalid section type " + it->second.type() + " (expected " + type + ")");
      }

      return it->second;
   }

   /**
    * Access mapped data
    *
    * \tparam T            type to access
    *
    * \param offset        offset relative to start of mapped file
    * \param count         number of items of type T to access
    *
    * \returns a pointer to the requested type at a certain offset relative to
    *          the start of the mapped file.
    */
   template <typename T>
   const T *data(size_t offset = 0, size_t count = 1) const
   {
      BOOST_STATIC_ASSERT_MSG(boost::is_pod<T>::value, "data<>() called on non-POD type");

      if (offset + count*sizeof(T) > m_map.size())
      {
         throw std::runtime_error(m_file + ": potential attempt to access data beyond end of mapping");
      }

      return reinterpret_cast<const T *>(m_map.const_data() + offset);
   }

   /**
    * Return name of mapped file
    */
   const std::string& filename() const
   {
      return m_file;
   }

   /**
    * Warm the cache for a particular data structure
    *
    * This is intended to be called by the individual data structure's
    * cache warming method. Cache warming is useful _only_ if there's a
    * chance for the particular data structure to fit into memory and
    * it's most effective when the data structure in question is randomly
    * accessed very frequently (i.e. several thousand times per second).
    */
   static void warm_cache(const void *beg, const void *end)
   {
      const char *b = reinterpret_cast<const char *>(beg);
      const char *e = reinterpret_cast<const char *>(end);
      char buf[MAP_PAGE_SIZE];
      size_t page_off = static_cast<size_t>(b - static_cast<const char *>(0))%sizeof(buf);

      if (page_off)
      {
         size_t len = std::min(sizeof(buf) - page_off, static_cast<size_t>(e - b));
         std::memcpy(buf, beg, len);
         b += len;
      }

      while (b < e)
      {
         size_t len = std::min(sizeof(buf), static_cast<size_t>(e - b));
         std::memcpy(buf, b, len);
         b += len;
      }
   }

private:
   const std::string m_file;
   const std::string m_format;
   boost::iostreams::mapped_file m_map;
   section_map_type m_section_map;
};

}}

#endif

max_stars_repo_name: lastfm/libmoost

max_issues_repo_name: lastfm/libmoost

max_forks_repo_name: lastfm/libmoost


text:
//               Copyright Marek Dalewski 2017
// Distributed under the Boost Software License, Version 1.0.
//        (See accompanying file LICENSE.md or copy at
//           http://www.boost.org/LICENSE_1_0.txt)

#include <commander/algorithm.hpp>

#include <boost/test/unit_test.hpp>

#include <type_traits>

// template <typename ResChar, typename FirstChar>
// ResChar make_char(FirstChar c0)
// {
//     static_assert(sizeof(FirstChar) == 1);

//     return ResChar(c0);
// }

// template <typename ResChar, typename FirstChar, typename SecondChar, typename... Chars>
// ResChar make_char(FirstChar c0, SecondChar c1, Chars... cs)
// {
//     static_assert(sizeof(FirstChar)  == 1);
//     static_assert(sizeof(SecondChar) == 1);

//     ResChar res = c0;

//     res <<= (sizeof...(cs) + 1) * 8;
//     res |= make_char<ResChar>(c1, cs...);

//     return res;
// }

template <typename ResChar, typename C1, typename C2, typename C3, typename C4>
ResChar make_char(C1 c1, C2 c2, C3 c3, C4 c4)
{
    uint8_t b1 = static_cast<uint8_t>(c1 & 0xff);
    uint8_t b2 = static_cast<uint8_t>(c2 & 0xff);
    uint8_t b3 = static_cast<uint8_t>(c3 & 0xff);
    uint8_t b4 = static_cast<uint8_t>(c4 & 0xff);

    ResChar res = 0ull;

    res <<= 8;
    res |= b1;
    if (sizeof(res) == 1)
        return res;

    res <<= 8;
    res |= b2;
    if (sizeof(res) == 2)
        return res;

    res <<= 8;
    res |= b3;
    if (sizeof(res) == 3)
        return res;

    res <<= 8;
    res |= b4;
    if (sizeof(res) == 4)
        return res;

    return res;
}

BOOST_AUTO_TEST_CASE( compare_characters )
{
    namespace com = commander;

    // c -> *
    {
        // c -> c
        {
            BOOST_CHECK(com::compare_characters('a', 'a') == true);
            BOOST_CHECK(com::compare_characters('a', 'b') == false);

            BOOST_CHECK(com::compare_characters('\0', make_char<char>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters('\0', make_char<char>(0x80, 0, 0, 0)) == false);

            BOOST_CHECK(com::compare_characters(make_char<char>(0, 0, 0, 0),    '\0') == true);
            BOOST_CHECK(com::compare_characters(make_char<char>(0x80, 0, 0, 0), '\0') == false);
        }

        // c -> L
        {
            BOOST_CHECK(com::compare_characters('a', L'a') == true);
            BOOST_CHECK(com::compare_characters('a', L'b') == false);

            BOOST_CHECK(com::compare_characters('\0', make_char<wchar_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters('\0', make_char<wchar_t>(0x80, 0, 0, 0)) == false);
        }

        // c -> u8
        {
            BOOST_CHECK(com::compare_characters('a', u8'a') == true);
            BOOST_CHECK(com::compare_characters('a', u8'b') == false);
        }

        // c -> u
        {
            BOOST_CHECK(com::compare_characters('a', u'a') == true);
            BOOST_CHECK(com::compare_characters('a', u'b') == false);

            BOOST_CHECK(com::compare_characters('\0', make_char<char16_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters('\0', make_char<char16_t>(0x80, 0, 0, 0)) == false);
        }

        // c -> U
        {
            BOOST_CHECK(com::compare_characters('a', U'a') == true);
            BOOST_CHECK(com::compare_characters('a', U'b') == false);
            BOOST_CHECK(com::compare_characters(U'b', 'a') == false);

            BOOST_CHECK(com::compare_characters('\0', make_char<char16_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters('\0', make_char<char16_t>(0x80, 0, 0, 0)) == false);
        }
    }

    // L -> *
    {
        // L -> c
        {
            BOOST_CHECK(com::compare_characters(L'a', 'a') == true);
            BOOST_CHECK(com::compare_characters(L'a', 'b') == false);

            BOOST_CHECK(com::compare_characters(L'\0', make_char<char>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(L'\0', make_char<char>(0x80, 0, 0, 0)) == false);

        }

        // L -> L
        {
            BOOST_CHECK(com::compare_characters(L'a', L'a') == true);
            BOOST_CHECK(com::compare_characters(L'a', L'b') == false);

            BOOST_CHECK(com::compare_characters(L'\0', make_char<wchar_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(L'\0', make_char<wchar_t>(0x80, 0, 0, 0)) == false);

            BOOST_CHECK(com::compare_characters(make_char<wchar_t>(0, 0, 0, 0),    L'\0') == true);
            BOOST_CHECK(com::compare_characters(make_char<wchar_t>(0x80, 0, 0, 0), L'\0') == false);
        }

        // L -> u8
        {
            BOOST_CHECK(com::compare_characters(L'a', u8'a') == true);
            BOOST_CHECK(com::compare_characters(L'a', u8'b') == false);
        }

        // L -> u
        {
            BOOST_CHECK(com::compare_characters(L'a', u'a') == true);
            BOOST_CHECK(com::compare_characters(L'a', u'b') == false);

            BOOST_CHECK(com::compare_characters(L'\0', make_char<char16_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(L'\0', make_char<char16_t>(0x80, 0, 0, 0)) == false);
        }

        // L -> U
        {
            BOOST_CHECK(com::compare_characters(L'a', U'a') == true);
            BOOST_CHECK(com::compare_characters(L'a', U'b') == false);

            BOOST_CHECK(com::compare_characters(L'\0', make_char<char32_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(L'\0', make_char<char32_t>(0x80, 0, 0, 0)) == false);
        }
    }

    // u8 -> *
    {
        // u8 -> c
        {
            BOOST_CHECK(com::compare_characters(u8'a', 'a') == true);
            BOOST_CHECK(com::compare_characters(u8'a', 'b') == false);

            BOOST_CHECK(com::compare_characters(u8'\0', make_char<char>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u8'\0', make_char<char>(0x80, 0, 0, 0)) == false);
        }

        // u8 -> L
        {
            BOOST_CHECK(com::compare_characters(u8'a', L'a') == true);
            BOOST_CHECK(com::compare_characters(u8'a', L'b') == false);

            BOOST_CHECK(com::compare_characters(u8'\0', make_char<wchar_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u8'\0', make_char<wchar_t>(0x80, 0, 0, 0)) == false);
        }

        // u8 -> u8
        {
            BOOST_CHECK(com::compare_characters(u8'a', u8'a') == true);
            BOOST_CHECK(com::compare_characters(u8'a', u8'b') == false);

            BOOST_CHECK(com::compare_characters(u8'\0', make_char<char>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u8'\0', make_char<char>(0x80, 0, 0, 0)) == false);

            BOOST_CHECK(com::compare_characters(make_char<char>(0, 0, 0, 0),    u8'\0') == true);
            BOOST_CHECK(com::compare_characters(make_char<char>(0x80, 0, 0, 0), u8'\0') == false);
        }

        // u8 -> u
        {
            BOOST_CHECK(com::compare_characters(u8'a', u'a') == true);
            BOOST_CHECK(com::compare_characters(u8'a', u'b') == false);

            BOOST_CHECK(com::compare_characters(u8'\0', make_char<char16_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u8'\0', make_char<char16_t>(0x80, 0, 0, 0)) == false);
        }

        // u8 -> U
        {
            BOOST_CHECK(com::compare_characters(u8'a', U'a') == true);
            BOOST_CHECK(com::compare_characters(u8'a', U'b') == false);

            BOOST_CHECK(com::compare_characters(u8'\0', make_char<char32_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u8'\0', make_char<char32_t>(0x80, 0, 0, 0)) == false);
        }
    }

    // u -> *
    {
        // u -> c
        {
            BOOST_CHECK(com::compare_characters(u'a', 'a') == true);
            BOOST_CHECK(com::compare_characters(u'a', 'b') == false);

            BOOST_CHECK(com::compare_characters(u'\0', make_char<char>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u'\0', make_char<char>(0x80, 0, 0, 0)) == false);
        }

        // u -> L
        {
            BOOST_CHECK(com::compare_characters(u'a', L'a') == true);
            BOOST_CHECK(com::compare_characters(u'a', L'b') == false);

            BOOST_CHECK(com::compare_characters(u'\0', make_char<wchar_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u'\0', make_char<wchar_t>(0x80, 0, 0, 0)) == false);
        }

        // u -> u8
        {
            BOOST_CHECK(com::compare_characters(u'a', u8'a') == true);
            BOOST_CHECK(com::compare_characters(u'a', u8'b') == false);
        }

        // u -> u
        {
            BOOST_CHECK(com::compare_characters(u'a', u'a') == true);
            BOOST_CHECK(com::compare_characters(u'a', u'b') == false);

            BOOST_CHECK(com::compare_characters(u'\0', make_char<char16_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u'\0', make_char<char16_t>(0x80, 0, 0, 0)) == false);

            BOOST_CHECK(com::compare_characters(make_char<char16_t>(0, 0, 0, 0),    u'\0') == true);
            BOOST_CHECK(com::compare_characters(make_char<char16_t>(0x80, 0, 0, 0), u'\0') == false);
        }

        // u -> U
        {
            BOOST_CHECK(com::compare_characters(u'a', U'a') == true);
            BOOST_CHECK(com::compare_characters(u'a', U'b') == false);

            BOOST_CHECK(com::compare_characters(u'\0', make_char<char32_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(u'\0', make_char<char32_t>(0x80, 0, 0, 0)) == false);
        }
    }

    // U -> *
    {
        // U -> c
        {
            BOOST_CHECK(com::compare_characters(U'a', 'a') == true);
            BOOST_CHECK(com::compare_characters(U'a', 'b') == false);

            BOOST_CHECK(com::compare_characters(U'\0', make_char<char>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(U'\0', make_char<char>(0x80, 0, 0, 0)) == false);
        }

        // U -> L
        {
            BOOST_CHECK(com::compare_characters(U'a', L'a') == true);
            BOOST_CHECK(com::compare_characters(U'a', L'b') == false);

            BOOST_CHECK(com::compare_characters(U'\0', make_char<wchar_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(U'\0', make_char<wchar_t>(0x80, 0, 0, 0)) == false);
        }

        // U -> u8
        {
            BOOST_CHECK(com::compare_characters(U'a', u8'a') == true);
            BOOST_CHECK(com::compare_characters(U'a', u8'b') == false);
        }

        // U -> u
        {
            BOOST_CHECK(com::compare_characters(U'a', u'a') == true);
            BOOST_CHECK(com::compare_characters(U'a', u'b') == false);

            BOOST_CHECK(com::compare_characters(U'\0', make_char<char16_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(U'\0', make_char<char16_t>(0x80, 0, 0, 0)) == false);
        }

        // U -> U
        {
            BOOST_CHECK(com::compare_characters(U'a', U'a') == true);
            BOOST_CHECK(com::compare_characters(U'a', U'b') == false);

            BOOST_CHECK(com::compare_characters(U'\0', make_char<char32_t>(0, 0, 0, 0))    == true);
            BOOST_CHECK(com::compare_characters(U'\0', make_char<char32_t>(0x80, 0, 0, 0)) == false);

            BOOST_CHECK(com::compare_characters(make_char<char32_t>(0, 0, 0, 0),    U'\0') == true);
            BOOST_CHECK(com::compare_characters(make_char<char32_t>(0x80, 0, 0, 0), U'\0') == false);
        }
    }
}

ext: cpp

max_stars_repo_name: daishe/commander

max_issues_repo_name: daishe/commander

max_forks_repo_name: daishe/commander


text:
/*
 * Software License Agreement (BSD License)
 *
 *  Copyright (c) 2010, AASS Research Center, Orebro University.
 *  All rights reserved.
 *
 *  Redistribution and use in source and binary forms, with or without
 *  modification, are permitted provided that the following conditions
 *  are met:
 *
 *   * Redistributions of source code must retain the above copyright
 *     notice, this list of conditions and the following disclaimer.
 *   * Redistributions in binary form must reproduce the above
 *     copyright notice, this list of conditions and the following
 *     disclaimer in the documentation and/or other materials provided
 *     with the distribution.
 *   * Neither the name of Willow Garage, Inc. nor the names of its
 *     contributors may be used to endorse or promote products derived
 *     from this software without specific prior written permission.
 *
 *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
 *  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
 *  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
 *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
 *  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 *  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
 *  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
 *  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
 *  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 *  POSSIBILITY OF SUCH DAMAGE.
 *
 */
#ifndef CEVENT_COUNTER_DATA_H
#define CEVENT_COUNTER_DATA_H
#include<cmath>
#include <iostream>
#include <cstdio>
#include <Eigen/Dense>
#include <inttypes.h>
#include <boost/archive/text_oarchive.hpp>
#include <boost/archive/text_iarchive.hpp>
///Defines for presets
#define EVENTMAP_OCCU  255
#define EVENTMAP_UNKNOWN  127
#define EVENTMAP_FREE  0
#define EVENTMAP_NUMBER_OF_EVENTS_STORED 128

///Recency filtering stuff
#define EVENTMAP_USE_RECENCY_FILTERING
#define EVENTMAP_OBSERVATION_LIMIT 30000.0
#define Wforget (5000.0/5001.0)

/**
* Structure in the map
**/
struct TEventData
{
  uint8_t 	occval; 			///<Occupancy value
  float 		a_exit_event; ///Number of exit events ( OCC 2 EMP)
  float  		b_exit_event; ///Number of times the cell is perceived as occupied

  float 		a_entry_event;
  float  		b_entry_event; ///Number of times the cell is perceived as empty
  uint64_t  events;        /// A storage for the last 64 events (as bits)

  TEventData():
    occval(127),
    a_exit_event(1.0),
    b_exit_event(1.0),
    a_entry_event(1.0),
    b_entry_event(1.0),
    events(0)
  {
  };

  ~TEventData()
  {
  }

  const TEventData &operator =(const TEventData &copy)
  {
    occval = copy.occval;
    a_exit_event = copy.a_exit_event;
    b_exit_event = copy.b_exit_event;
    a_entry_event = copy.a_entry_event;
    b_entry_event = copy.b_entry_event;
    events = copy.events;

    return *this;
  }

  TEventData(const TEventData& copy):
    occval(copy.occval),
    a_exit_event(copy.a_exit_event),
    b_exit_event(copy.b_exit_event),
    a_entry_event(copy.a_entry_event),
    b_entry_event(copy.b_entry_event),
    events( copy.events)
  {
  }

  void Reset()
  {
    occval = 127;
    a_exit_event = 1;
    b_exit_event = 1;
    a_entry_event = 1;
    b_entry_event = 1;
  }

  bool getBit(int ind)
  {
    if((events & (1<<ind))>0) return true;
    return false;
  }

  float computeShortTermOccupancy()
  {
    static float OCC_LOG_PROP = log(0.6/0.4);
    static float EMP_LOG_PROP = log(0.3/0.7);
    uint bs=0;

    if( (b_entry_event+b_exit_event-2) > 63) bs=64;
    else bs = b_entry_event+b_exit_event-2;
    uint cnt=0;
    float log_ogg_prob  = 0 ;
    for(uint i = 0; i<bs; i++)
    {
      if(getBit(i))
      {
        log_ogg_prob += OCC_LOG_PROP;
        cnt++;
      }
      else
      {
        log_ogg_prob += EMP_LOG_PROP;
      }
    }
    return (1.0- 1.0/(1.0+exp(log_ogg_prob)));
  }

  int getObservations()
  {
    return (b_entry_event+b_exit_event);
  }

  /**
    * Updates a new measurement
    */
  void updateSimple(uint8_t meas)
  {
    events = events<<1;
    if(meas > EVENTMAP_UNKNOWN)  ///OCC
    {
      events |= 1;
    }
    if(occval > EVENTMAP_UNKNOWN)  ///cell is considered Occupied
    {
      updateExitEvent(meas, 1.0);
    }
    else if(occval < EVENTMAP_UNKNOWN)
    {
      updateEntryEvent(meas,1.0);
    }
    else
    {
      occval = meas; ///Just update
    }
  }

  /**
    * Updates a new measurement
    */
  void updateSimple(uint8_t meas, float w)
  {
    events = events<<1;
    if(meas > EVENTMAP_UNKNOWN)  ///OCC
    {
      events |= 1;
    }
    if(occval > EVENTMAP_UNKNOWN)  ///cell is considered Occupied
    {
      updateExitEvent(meas, w);
    }
    else if(occval < EVENTMAP_UNKNOWN)
    {
      updateEntryEvent(meas,w);
    }
    else
    {
      occval = meas; ///Just update
    }
#ifdef EVENTMAP_USE_RECENCY_FILTERING
    performRecencyFiltering();
#endif
  }

  void performRecencyFiltering()
  {
    if(occval > EVENTMAP_UNKNOWN)  ///We are in Exit state
    {
      if(b_exit_event>EVENTMAP_OBSERVATION_LIMIT)
      {
        float w = EVENTMAP_OBSERVATION_LIMIT / b_exit_event;
        b_exit_event *= w;
        a_exit_event *= w;
      }
      a_entry_event = 1.0 + (a_entry_event-1.0) * Wforget;
      b_entry_event = 1.0 + (b_entry_event-1.0) * Wforget;
    }
    else
    {
      if(b_entry_event>EVENTMAP_OBSERVATION_LIMIT)
      {
        float w = EVENTMAP_OBSERVATION_LIMIT / b_entry_event;
        b_entry_event *= w;
        a_entry_event *= w;
      }
      a_exit_event = 1.0 + (a_exit_event-1.0) * Wforget;
      b_exit_event = 1.0 + (b_exit_event-1.0) * Wforget;
    }
  }

  /**
    * Update Exit event (cell is OCC)
    */
  void updateExitEvent(uint8_t meas, float w)
  {
    if(meas>EVENTMAP_UNKNOWN)  ///OCC
    {
      b_exit_event+=1.0;
    }
    else
    {
      if(w>1.0) fprintf(stderr,"EXIT W larger that one = %f\n ",w);
      a_exit_event+=w;
      b_exit_event+=1.0;
      occval = EVENTMAP_FREE;
    }
  }
  /**
    * Update Entry event (Cell is Free)
    */
  void updateEntryEvent(uint8_t meas, float w)
  {
    if(meas>EVENTMAP_UNKNOWN)  ///OCC
    {
      b_entry_event+=1.0;
      if(w>1.0) fprintf(stderr,"W larger that one = %f\n ",w);
      a_entry_event+=w;
      occval = EVENTMAP_OCCU;
    }
    else
    {
      b_entry_event+=1.0;
    }
  }

  ///Expected number of observations/event
  int getEntryN()
  {
    return (int)((float)b_entry_event/(float)a_entry_event +0.5);
  }
  ///Expected number of observations/event
  int getExitN()
  {
    return (int)((float)b_exit_event/(float)a_exit_event +0.5);
  }

  double entryL()
  {
    if(b_entry_event == 0) fprintf(stderr,"B Zero, which is not possible!!\n");
    return ((double)a_entry_event/(double)b_entry_event );
  }
  double exitL()
  {
    if(b_exit_event == 0) fprintf(stderr,"B Zero, which is not possible!!\n");
    return ((double)a_exit_event/(double)b_exit_event);
  }
  double L()
  {
    if(b_exit_event == 0) fprintf(stderr,"B Zero, which is not possible!!\n");
    return ((double)(a_exit_event+a_entry_event)/(double)(b_exit_event+b_entry_event));
  }

  double fac(int n)
  {
    double t=1;
    for (int i=n; i>1; i--)
      t*=i;
    return t;
  }

  double Bin(int n,double p,int r)
  {
    return fac(n)/(fac(n-r)*fac(r))*pow(p,r)*pow(1-p,n-r);
  }

  float binaryBayesUpdate(float Pold, float P)
  {
    return (( Pold*P) / ( Pold*P + (1.0f-Pold)*(1.0f-P))); 	///< Updated probability
  }

  /**
    * To prevent numerical difficulties
    */
  void normalizeProb(float &p)
  {
    if(p>0.999) p = 0.999;
    if(p<0.001) p = 0.001;

  }
  /////////////////////////////////////////////////////////////////////////////////////////////77
  /// Compute different probabilities for the cell
  /////////////////////////////////////////////////////////////////////////////////////////////77
  /////////////////////////////////////////////////////////////////////////////////////////////77
  /**
    * Compute the probability of this cell being Static occupied.
    */
  float getOccStaticLikelihood()
  {
    if( (b_entry_event + b_exit_event)<20.0 )
    {
      return 0.5f;
    }
    Eigen::Matrix2f P;
    Eigen::Vector2f u1(0.5, 0.5);
    Eigen::Vector2f P0;
    float Lex = exitL();
    float Len = entryL();
    P(0,0) = (1.0-Len);
    P(0,1) =  Len;
    P(1,0)	 = Lex;
    P(1,1) = (1-Lex);

    P0 = u1.transpose() * P;
    return (P0(1));
  }

  /**
    * Returns the probability of static empty
    */
  float getFreeStaticLikelihood()
  {
    if( (b_entry_event + b_exit_event)<20.0 )
    {
      return 0.5f;
    }
    Eigen::Matrix2f P;
    Eigen::Vector2f P0;
    Eigen::Vector2f u1(0.5, 0.5);
    float Lex = exitL();
    float Len = entryL();
    P(0,0) = (1.0-Len);
    P(0,1) =  Len;
    P(1,0)	 = Lex;
    P(1,1) = (1-Lex);

    P0 = u1.transpose() * P;
    return (P0(0));
  }

  /**
    * Returns the probability of the cell having dynamics after 2^N
    * Observations. The larger the N, and higher the value, the more "Semi-static"
    * is the cell. Note that the filter returns
    * 0.5 >= P <=1.0 and P = 0.0 only if there is not enough evidence about the
    * Behaviour
    */
  float computeSemiStaticLikelihood(int N)
  {
    if( (b_entry_event + b_exit_event)<20.0 )
    {
      return 0.0f;
    }

    Eigen::Matrix2f P;
    Eigen::Vector2f u2(0, 1.0);
    Eigen::Vector2f u3(1.0, 0);
    float Lex = exitL();
    float Len = entryL();
    Eigen::Vector2f P2,P3;
    P(0,0) = (1.0-Len);
    P(0,1) =  Len;
    P(1,0)	 = Lex;
    P(1,1) = (1-Lex);
    for(int i=0; i<N; i++) P = P*P;
    P2 = u2.transpose() * P;
    P3 = u3.transpose() * P;

    float Po = P2(1);
    float Pu = binaryBayesUpdate(Po, P3(0));
    normalizeProb(Pu);

    return Pu;
  }

  float getOccupancyNow()
  {
    if( (b_entry_event + b_exit_event)<50.0)
    {
      return 0.5f;
    }
    float Po = 0;

    Po = computeShortTermOccupancy();
    float Lex = exitL();
    float Len = entryL();
    Eigen::Matrix2f P;
    P(0,0) = (1.0-Len);
    P(0,1) =  Len;
    P(1,0)	 = Lex;
    P(1,1) = (1-Lex);
    Eigen::Vector2f u1(1.0-Po, Po);
    Eigen::Vector2f u = u1.transpose() *P;
    return u(1);
  }

  /////////////////////////////////////////////////////////////////////////////////////////////77
  /////////////////////////////////////////////////////////////////////////////////////////////77
  ///Predict
  /////////////////////////////////////////////////////////////////////////////////////////////77
  /////////////////////////////////////////////////////////////////////////////////////////////77

  float predictOccupancy(int N)
  {
    if( (b_entry_event + b_exit_event)<20.0)
    {
      return 0.5f;
    }
    ///Testing
    float ps = getOccStaticLikelihood();
    if(ps>0.6) return 0.9;
    ///end testing

    float Po = computeShortTermOccupancy();
    float Lex = exitL();
    float Len = entryL();
    Eigen::Matrix2f P;
    P(0,0) = (1.0-Len);
    P(0,1) =  Len;
    P(1,0)	 = Lex;
    P(1,1) = (1-Lex);
    Eigen::Vector2f u1(1.0-Po, Po);
    for(int i=0; i<N; i++) P = P*P;
    Eigen::Vector2f u = u1.transpose() *P;

    return u(1);
  }

};
namespace boost {
namespace serialization {

template<class Archive>
void serialize(Archive & ar, TEventData & g, const unsigned int version)
{
  ar & 	g.occval; 			///<Occupancy value
  ar &  g.a_exit_event; ///Number of exit events ( OCC 2 EMP)
  ar &  g.b_exit_event; ///Number of times the cell is perceived as occupied
  ar & 	g.a_entry_event;
  ar & 	g.b_entry_event; ///Number of times the cell is perceived as empty
  ar &  g.events;
}

} // namespace serialization
} // namespace boost
#endif

ext: hpp

max_stars_repo_name: lllray/ndt-loam

max_issues_repo_name: lllray/ndt-loam

max_forks_repo_name: lllray/ndt-loam


text:
#include <iostream>
#include <cmath>
#include <algorithm>
#include <vector>
#include <boost/lexical_cast.hpp>
using namespace std;
void solve(vector<long long int> &v, string s, int m, int cnt, int a, int b, int c) {
    if (cnt < m) solve(v, s + '3', m, cnt + 1, a + 1, b, c), solve(v, s + '5', m, cnt + 1, a, b + 1, c), solve(v, s + '7', m, cnt + 1, a, b, c + 1);
    if (cnt >= 3 && a >= 1 && b >= 1 && c >= 1) v.push_back(boost::lexical_cast<int>(s));
}
int main() {
    long long int n; cin >> n;
    vector<long long int> v;
    int c = boost::lexical_cast<string>(n).length(), ans = 0;
    solve(v, "", c, 0, 0, 0, 0);
    for (auto x : v) if (x <= n) ans++;
    cout << ans << endl;
}


text:
/**
 * Copyright 2021 Scott Brauer
 *
 * 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  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.
 */

/**
 * @file   ProgramOptionsGroup.hpp
 * @author Scott Brauer
 * @date   04-04-2019
 */

#ifndef OFFCENTER_COMMON_PROGRAMOPTIONS_PROGRAMOPTIONSGROUP_HPP_
#define OFFCENTER_COMMON_PROGRAMOPTIONS_PROGRAMOPTIONSGROUP_HPP_

#include <boost/program_options.hpp>
namespace po = boost::program_options;

#include "IProgramOptionsGroup.hpp"

namespace offcenter {
namespace common {
namespace program_options {

/**
 * A group of command line/config file options for an application.
 *
 * @tparam OptionConfig The related configuration options that will be filled
 *		   with the parsed values from the command line/config file.
 */
template<typename OptionConfig>
class ProgramOptionsGroup: public IProgramOptionsGroup
{
public:
	using ConfigPtr = std::shared_ptr<OptionConfig>;

public:
	/**
	 * Create a \c ProgramOptionsGroup
	 *
	 * The \c ProgramOptionsGroup is a set of options that can be set via the command line
	 * and/or a configuration file.
	 *
	 * @param groupName				A name describing this group. Displayed in help.
	 * @param isCommandLineOption	Are the elements of this group command line options? Default = true
	 * @param isConfigFileOption	Are the elements of this group config file options? Default = true
	 * @param isVisibleInHelpOption	Should the group be displayed in the help? Default = true
	 */
	ProgramOptionsGroup(
			std::string groupName,
			bool isCommandLineOption = true,
			bool isConfigFileOption = true,
			bool isVisibleInHelpOption = true):
		m_optionsDescription(groupName),
		m_positionalOptionsDescription(),
		m_isCommandLineOption(isCommandLineOption),
		m_isConfigFileOption(isConfigFileOption),
		m_isVisibleInHelpOption(isVisibleInHelpOption),
		m_optionConfig(),
		m_optionConfigPtr(std::make_shared<OptionConfig>())
		{}

	virtual ~ProgramOptionsGroup() = default;

	/// @copydoc IProgramOptionsGroup::processOptions(po::variables_map& vm)
	virtual void processOptions(po::variables_map& vm) {}
	/// @copydoc IProgramOptionsGroup::validateOptions(po::variables_map& vm)
	virtual void validateOptions(po::variables_map& vm) {}

	/// @copydoc IProgramOptionsGroup::isCommandLineOption()
	bool isCommandLineOption() override { return m_isCommandLineOption; }
	/// @copydoc IProgramOptionsGroup::isConfigFileOption()
	bool isConfigFileOption() override { return m_isConfigFileOption; }
	/// @copydoc IProgramOptionsGroup::isVisibleInHelpOption()
	bool isVisibleInHelpOption() override { return m_isVisibleInHelpOption; }

	/// @copydoc IProgramOptionsGroup::hasConfigFileName()
	bool hasConfigFileName() override { return false; }
	/// @copydoc IProgramOptionsGroup::getConfigFileName()
	std::string getConfigFileName() override { return ""; }
	/// @copydoc IProgramOptionsGroup::updateSharedData()
	void updateSharedData() { *m_optionConfigPtr = m_optionConfig; }

	/// @copydoc IProgramOptionsGroup::optionsDescription()
	po::options_description& optionsDescription() override { return m_optionsDescription; }
	/// @copydoc IProgramOptionsGroup::positionalOptionsDescription()
	po::positional_options_description& positionalOptionsDescription() override { return m_positionalOptionsDescription; }

	ConfigPtr optionConfigPtr() { return m_optionConfigPtr; }

private:
	po::options_description m_optionsDescription;
	po::positional_options_description m_positionalOptionsDescription;

	bool m_isCommandLineOption;
	bool m_isConfigFileOption;
	bool m_isVisibleInHelpOption;
	OptionConfig m_optionConfig;

protected:
	ConfigPtr m_optionConfigPtr;
	OptionConfig& optionConfig() { return m_optionConfig; }
	OptionConfig* optionConfigPointer() { return &m_optionConfig; }
};

} /* namespace program_options */
} /* namespace common */
} /* namespace offcenter */

#endif /* OFFCENTER_COMMON_PROGRAMOPTIONS_PROGRAMOPTIONSGROUP_HPP_ */


text:
#ifndef __MODULE_OPTIONS__
#define __MODULE_OPTIONS__

#include <complex.hpp>
#include <string>
#include <boost/program_options.hpp>

class options
 {
  public:

      enum class aspect_ratio { square, hdtv };

      // generic commands
      bool help;
      bool version;
      bool verbose;

      // resolution
      int resolution;
      aspect_ratio aspect;

      // point of interest
      complex center;
      float scale;

      int max_iterations;

      // files
      std::string output_filename;

  public:

      static void show_help();
      static void show_version();

  options()
   : help(false),
     version(false),
     verbose(false),
     resolution(1000),
     aspect(aspect_ratio::square),
     center(0),
     scale(2),
     max_iterations(1000),
     output_filename("output.ppm")
  {}

  options(int,const char * const []);

  ~options()=default;
 };

#endif
    // __MODULE_OPTIONS__


text:
// Copyright Louis Dionne 2013-2016
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt)

#include <boost/hana/experimental/view.hpp>

#include <laws/base.hpp>
#include <support/seq.hpp>
namespace hana = boost::hana;
using hana::test::ct_eq;

struct undefined { };

int main() {
    // Make sure we do not evaluate the function unless required
    auto storage = ::seq(ct_eq<0>{}, ct_eq<1>{}, ct_eq<2>{});
    auto transformed = hana::experimental::transformed(storage, undefined{});
    (void)transformed;
}

max_stars_repo_name: nxplatform/nx-mobile

max_issues_repo_name: nxplatform/nx-mobile

max_forks_repo_name: nxplatform/nx-mobile


text:
//==================================================================================================
/*!
  @file

  @copyright 2016 NumScale SAS

  Distributed under the Boost Software License, Version 1.0.
  (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt)

**/
//==================================================================================================
#ifndef BOOST_SIMD_RANGE_ALIGNED_OUTPUT_RANGE_HPP_INCLUDED
#define BOOST_SIMD_RANGE_ALIGNED_OUTPUT_RANGE_HPP_INCLUDED

#include <boost/simd/range/detail/aligned_output_iterator.hpp>
#include <boost/range/iterator_range.hpp>
#include <boost/simd/detail/is_aligned.hpp>
#include <boost/assert.hpp>
#include <iterator>

namespace boost { namespace simd
{
  /*!
    @ingroup group-std
    Builds an Output ContiguousRange that iterates over the original <tt>[begin, end[</tt>
    ContiguousRange by returning boost::simd::pack at every iteration step.

    @pre @c std::distance(begin,end) is an exact multiple of @c N
    @pre @c std::addressof(*begin) is aligned on @c pack<Iterator::value_type,N>::alignment
    @tparam C Cardinal of the pack to be iterated. By default, @c N is equal to the native cardinal
            on current architecture.
    @param begin Starting iterator of the ContiguousRange to adapt
    @param end   End iterator of the ContiguousRange to adapt
    @return An Output ContiguousRange returning boost::simd::pack
  **/
  template<std::size_t C, class Iterator> inline
  boost::iterator_range< detail::aligned_output_iterator<Iterator, C> >
  aligned_output_range( Iterator begin, Iterator end )
  {
    BOOST_ASSERT_MSG
    ( boost::simd::detail::is_aligned(std::distance(begin,end), C)
    , "Range being adapted holds a non integral number of SIMD pack."
    );

    return boost::make_iterator_range ( detail::aligned_output_begin<C>(begin)
                                      , detail::aligned_output_end<C>(end)
                                      );
  }

  /// @overload
  template<class Iterator> inline
  boost::iterator_range< detail::aligned_output_iterator<Iterator> >
  aligned_output_range( Iterator begin, Iterator end )
  {
    BOOST_ASSERT_MSG
    ( boost::simd::detail::is_aligned( std::distance(begin,end)
                , detail::aligned_output_iterator<Iterator>::cardinal
                )
    , "Range being adapted holds a non integral number of SIMD pack."
    );

    return boost::make_iterator_range ( detail::aligned_output_begin(begin)
                                      , detail::aligned_output_end(end)
                                      );
  }

  /*!
    @ingroup group-std
    Builds an Output ContiguousRange that iterates over the original ContiguousRange by
    returning boost::simd::pack at every iteration step.

    @pre @c std::distance(begin,end) is an exact multiple of @c N
    @pre @c &(*std::begin(r)) is aligned on @c pack<ContiguousRange::value_type,N>::alignment
    @tparam N Cardinal of the pack to be iterated. By default, @c N is equal to
              the native cardinal of current architecture.
    @param r Input ContiguousRange to adapt
    @return An Output ContiguousRange returning boost::simd::pack of cardinal @c N
  **/
  template<std::size_t C, class Range> inline
  boost::iterator_range<detail::aligned_output_iterator<typename range_iterator<Range>::type,C> >
  aligned_output_range( Range& r )
  {
    return aligned_output_range<C>( boost::begin(r), boost::end(r) );
  }

  /// @overload
  template<class Range> inline
  boost::iterator_range<detail::aligned_output_iterator<typename range_iterator<Range>::type> >
  aligned_output_range( Range& r )
  {
    return aligned_output_range( boost::begin(r), boost::end(r) );
  }
} }

#endif

max_stars_repo_name: nickporubsky/boost-simd-clone

max_issues_repo_name: nickporubsky/boost-simd-clone

max_forks_repo_name: nickporubsky/boost-simd-clone


text:
/* gc_test.cc
   Jeremy Barnes, 23 February 2010
   Copyright (c) 2010 Datacratic.  All rights reserved.

   Test of the garbage collector locking.
*/

#define BOOST_TEST_MAIN
#define BOOST_TEST_DYN_LINK

#include "soa/gc/gc_lock.h"
#include "soa/gc/rcu_lock.h"
#include "jml/utils/string_functions.h"
#include "jml/utils/exc_assert.h"
#include "jml/utils/guard.h"
#include "jml/arch/atomic_ops.h"
#include "jml/arch/thread_specific.h"
#include "jml/arch/rwlock.h"
#include "jml/arch/spinlock.h"
#include "jml/arch/tick_counter.h"
#include <boost/test/unit_test.hpp>
#include <boost/bind.hpp>
#include <iostream>

#include <boost/thread.hpp>
#include <boost/thread/barrier.hpp>

using namespace ML;
using namespace Datacratic;
using namespace std;

// Defined in gc_lock.cc
namespace Datacratic {
extern int32_t gcLockStartingEpoch;
};

struct doInit {
    doInit()
    {
        rcu_init();
    }
} init;

#if 1

BOOST_AUTO_TEST_CASE ( test_gc )
{
    GcLock gc;
    gc.lockShared();

    BOOST_CHECK(gc.isLockedShared());

    bool deferred = false;

    cerr << endl << "before defer" << endl;
    gc.dump();

    gc.defer([&] () { deferred = true; memory_barrier(); });

    cerr << endl << "after defer" << endl;
    gc.dump();

    gc.unlockShared();

    cerr << endl << "after unlock shared" << endl;
    gc.dump();

    BOOST_CHECK(!gc.isLockedShared());
    BOOST_CHECK(deferred);
}

BOOST_AUTO_TEST_CASE(test_mutual_exclusion)
{
    cerr << "testing mutual exclusion" << endl;

    GcLock lock;
    volatile bool finished = false;
    volatile int numExclusive = 0;
    volatile int numShared = 0;
    int errors = 0;
    int multiShared = 0;
    uint64_t sharedIterations = 0;
    uint64_t exclusiveIterations = 0;

    auto sharedThread = [&] ()
        {
            while (!finished) {
                GcLock::SharedGuard guard(lock);
                ML::atomic_inc(numShared);

                if (numExclusive > 0) {
                    cerr << "exclusive and shared" << endl;
                    ML::atomic_inc(errors);
                }
                if (numShared > 1) {
                    ML::atomic_inc(multiShared);
                }

                ML::atomic_dec(numShared);
                ML::atomic_inc(sharedIterations);
                ML::memory_barrier();
            }
        };

    auto exclusiveThread = [&] ()
        {
            while (!finished) {
                GcLock::ExclusiveGuard guard(lock);
                ML::atomic_inc(numExclusive);

                if (numExclusive > 1) {
                    cerr << "more than one exclusive" << endl;
                    ML::atomic_inc(errors);
                }
                if (numShared > 0) {
                    cerr << "exclusive and shared" << endl;
                    ML::atomic_inc(multiShared);
                }

                ML::atomic_dec(numExclusive);
                ML::atomic_inc(exclusiveIterations);
                ML::memory_barrier();
            }
        };

    lock.getEntry();

    int nthreads = 4;

    {
        cerr << "single shared" << endl;
        sharedIterations = exclusiveIterations = multiShared = finished = 0;
        boost::thread_group tg;
        tg.create_thread(sharedThread);
        sleep(1);
        finished = true;
        tg.join_all();
        BOOST_CHECK_EQUAL(errors, 0);
        cerr << "iterations: shared " << sharedIterations
             << " exclusive " << exclusiveIterations << endl;
        cerr << "multiShared = " << multiShared << endl;
    }

    {
        cerr << "multi shared" << endl;
        sharedIterations = exclusiveIterations = multiShared = finished = 0;
        boost::thread_group tg;
        for (unsigned i = 0;  i < nthreads;  ++i)
            tg.create_thread(sharedThread);
        sleep(1);
        finished = true;
        tg.join_all();
        BOOST_CHECK_EQUAL(errors, 0);
        if (nthreads > 1)
            BOOST_CHECK_GE(multiShared, 0);
        cerr << "iterations: shared " << sharedIterations
             << " exclusive " << exclusiveIterations << endl;
        cerr << "multiShared = " << multiShared << endl;
    }

    {
        cerr << "single exclusive" << endl;
        sharedIterations = exclusiveIterations = multiShared = finished = 0;
        boost::thread_group tg;
        tg.create_thread(exclusiveThread);
        sleep(1);
        finished = true;
        tg.join_all();
        BOOST_CHECK_EQUAL(errors, 0);
        cerr << "iterations: shared " << sharedIterations
             << " exclusive " << exclusiveIterations << endl;
        cerr << "multiShared = " << multiShared << endl;
    }

    {
        cerr << "multi exclusive" << endl;
        sharedIterations = exclusiveIterations = multiShared = finished = 0;
        boost::thread_group tg;
        for (unsigned i = 0;  i < nthreads;  ++i)
            tg.create_thread(exclusiveThread);
        sleep(1);
        finished = true;
        tg.join_all();
        BOOST_CHECK_EQUAL(errors, 0);
        cerr << "iterations: shared " << sharedIterations
             << " exclusive " << exclusiveIterations << endl;
        cerr << "multiShared = " << multiShared << endl;
    }

    {
        cerr << "mixed shared and exclusive" << endl;
        sharedIterations = exclusiveIterations = multiShared = finished = 0;
        boost::thread_group tg;
        for (unsigned i = 0;  i < nthreads;  ++i)
            tg.create_thread(sharedThread);
        for (unsigned i = 0;  i < nthreads;  ++i)
            tg.create_thread(exclusiveThread);
        sleep(1);
        finished = true;
        tg.join_all();
        BOOST_CHECK_EQUAL(errors, 0);
        if (nthreads > 1)
            BOOST_CHECK_GE(multiShared, 0);
        cerr << "iterations: shared " << sharedIterations
             << " exclusive " << exclusiveIterations << endl;
        cerr << "multiShared = " << multiShared << endl;
    }

    {
        cerr << "overflow" << endl;
        gcLockStartingEpoch = 0xFFFFFFF0;
        sharedIterations = exclusiveIterations = multiShared = finished = 0;
        boost::thread_group tg;
        tg.create_thread(sharedThread);
        sleep(1);
        finished = true;
        tg.join_all();
        BOOST_CHECK_EQUAL(errors, 0);
        cerr << "iterations: shared " << sharedIterations
             << " exclusive " << exclusiveIterations << endl;
        cerr << "multiShared = " << multiShared << endl;
    }

    {
        cerr << "INT_MIN to INT_MAX" << endl;
        gcLockStartingEpoch = 0x7FFFFFF0;
        sharedIterations = exclusiveIterations = multiShared = finished = 0;
        boost::thread_group tg;
        tg.create_thread(sharedThread);
        sleep(1);
        finished = true;
        tg.join_all();
        BOOST_CHECK_EQUAL(errors, 0);
        cerr << "iterations: shared " << sharedIterations
             << " exclusive " << exclusiveIterations << endl;
        cerr << "multiShared = " << multiShared << endl;
    }

    {
        cerr << "benign overflow" << endl;
        gcLockStartingEpoch = 0xBFFFFFF0;
        sharedIterations = exclusiveIterations = multiShared = finished = 0;
        boost::thread_group tg;
        tg.create_thread(sharedThread);
        sleep(1);
        finished = true;
        tg.join_all();
        BOOST_CHECK_EQUAL(errors, 0);
        cerr << "iterations: shared " << sharedIterations
             << " exclusive " << exclusiveIterations << endl;
        cerr << "multiShared = " << multiShared << endl;
    }

}

#endif

#define USE_MALLOC 1

template<typename T>
struct Allocator {
    Allocator(int nblocks, T def = T())
        : def(def)
    {
        init(nblocks);
        highestAlloc = nallocs = ndeallocs = 0;
    }

    ~Allocator()
    {
#if ( ! USE_MALLOC )
        delete[] blocks;
        delete[] free;
#endif
    }

    T def;
    T * blocks;
    int * free;
    int nfree;
    int highestAlloc;
    int nallocs;
    int ndeallocs;
    ML::Spinlock lock;

    void init(int nblocks)
    {
#if ( ! USE_MALLOC )
        blocks = new T[nblocks];
        free = new int[nblocks];

        std::fill(blocks, blocks + nblocks, def);

        nfree = 0;
        for (int i = nblocks - 1;  i >= 0;  --i)
            free[nfree++] = i;
#endif
    }

    T * alloc()
    {
#if USE_MALLOC
        ML::atomic_inc(nallocs);
        ML::atomic_max(highestAlloc, nallocs - ndeallocs);
        return new T(def);
#else
        boost::lock_guard<ML::Spinlock> guard(lock);
        if (nfree == 0)
            throw ML::Exception("none free");
        int i = free[nfree - 1];
        highestAlloc = std::max(highestAlloc, i);
        T * result = blocks + i;
        --nfree;
        ++nallocs;
        return result;
#endif
    }

    void dealloc(T * value)
    {
        if (!value) return;
        *value = def;
#if USE_MALLOC
        delete value;
        ML::atomic_inc(ndeallocs);
        return;
#else
        boost::lock_guard<ML::Spinlock> guard(lock);
        int i = value - blocks;
        free[nfree++] = i;
        ++ndeallocs;
#endif
    }

    static void doDealloc(void * thisptr, void * blockPtr_, void * blockVar_)
    {
        int * & blockVar = *reinterpret_cast<int **>(blockVar_);
        int * blockPtr = reinterpret_cast<int *>(blockPtr_);
        ExcAssertNotEqual(blockVar, blockPtr);
        //blockVar = 0;
        //ML::memory_barrier();
        //cerr << "blockPtr = " << blockPtr << endl;
        //int * blockPtr = reinterpret_cast<int *>(block);
        reinterpret_cast<Allocator *>(thisptr)->dealloc(blockPtr);
    }

    static void doDeallocAll(void * thisptr, void * blocksPtr_, void * numBlocks_)
    {
        size_t numBlocks = reinterpret_cast<size_t>(numBlocks_);
        int ** blocksPtr = reinterpret_cast<int **>(blocksPtr_);
        Allocator * alloc = reinterpret_cast<Allocator *>(thisptr);

        for (unsigned i = 0;  i != numBlocks;  ++i) {
            if (blocksPtr[i])
                alloc->dealloc(blocksPtr[i]);
        }

        delete[] blocksPtr;
    }
};

template<typename Lock>
struct TestBase {
    TestBase(int nthreads, int nblocks, int nSpinThreads = 0)
        : finished(false),
          nthreads(nthreads),
          nblocks(nblocks),
          nSpinThreads(nSpinThreads),
          allocator(1024 * 1024, -1),
          nerrors(0),
          allBlocks(nthreads)
    {
        for (unsigned i = 0;  i < nthreads;  ++i) {
            allBlocks[i] = new int *[nblocks];
            std::fill(allBlocks[i], allBlocks[i] + nblocks, (int *)0);
        }
    }

    ~TestBase()
    {
        for (unsigned i = 0;  i < nthreads;  ++i)
            delete[] allBlocks[i];
    }

    volatile bool finished;
    int nthreads;
    int nblocks;
    int nSpinThreads;
    Allocator<int> allocator;
    Lock gc;
    uint64_t nerrors;

    /* All of the blocks are published here.  Any pointer which is read from
       here by another thread should always refer to exactly the same
       value.
    */
    vector<int **> allBlocks;

    void checkVisible(int threadNum, unsigned long long start)
    {
        // We're reading from someone else's pointers, so we need to lock here
        gc.enterCS();
        //gc.lockShared();

        for (unsigned i = 0;  i < nthreads;  ++i) {
            for (unsigned j = 0;  j < nblocks;  ++j) {
                //int * val = allBlocks[i][j];
                int * val = (int *)(rcu_dereference_sym(allBlocks[i][j]));
                if (val) {
                    int atVal = *val;
                    if (atVal != i) {
                        cerr << ML::format("%.6f thread %d: invalid value read "
                                "from thread %d block %d: %d\n",
                                (ticks() - start) / ticks_per_second, threadNum,
                                i, j, atVal);
                        ML::atomic_inc(nerrors);
                        //abort();
                    }
                }
            }
        }

        gc.exitCS();
        //gc.unlockShared();
    }

    void doReadThread(int threadNum)
    {
        gc.getEntry();
        unsigned long long start = ticks();
        while (!finished) {
            checkVisible(threadNum, start);
        }
    }

    void doSpinThread()
    {
        while (!finished) {
        }
    }

    void allocThreadDefer(int threadNum)
    {
        gc.getEntry();
        try {
            uint64_t nErrors = 0;

            int ** blocks = allBlocks[threadNum];

            while (!finished) {

                int ** oldBlocks = new int * [nblocks];

                //gc.enterCS();

                for (unsigned i = 0;  i < nblocks;  ++i) {
                    int * block = allocator.alloc();
                    if (*block != -1) {
                        cerr << "old block was allocated" << endl;
                        ++nErrors;
                    }
                    *block = threadNum;
                    ML::memory_barrier();
                    //rcu_set_pointer_sym((void **)&blocks[i], block);
                    int * oldBlock = blocks[i];
                    blocks[i] = block;
                    ML::memory_barrier();
                    oldBlocks[i] = oldBlock;
                }

                gc.defer(Allocator<int>::doDeallocAll, &allocator, oldBlocks,
                         (void *)(size_t)nblocks);

                //gc.exitCS();
            }

            int * oldBlocks[nblocks];

            for (unsigned i = 0;  i < nblocks;  ++i) {
                oldBlocks[i] = blocks[i];
                blocks[i] = 0;
            }

            gc.visibleBarrier();

            //cerr << "at end" << endl;

            for (unsigned i = 0;  i < nblocks;  ++i)
                allocator.dealloc(oldBlocks[i]);

            //cerr << "nErrors = " << nErrors << endl;
        } catch (...) {
            static ML::Spinlock lock;
            lock.acquire();
            //cerr << "threadnum " << threadNum << " inEpoch "
            //     << gc.getEntry().inEpoch << endl;
            gc.dump();
            abort();
        }
    }

    void allocThreadSync(int threadNum)
    {
        gc.getEntry();
        try {
            uint64_t nErrors = 0;

            int ** blocks = allBlocks[threadNum];
            int * oldBlocks[nblocks];

            while (!finished) {

                for (unsigned i = 0;  i < nblocks;  ++i) {
                    int * block = allocator.alloc();
                    if (*block != -1) {
                        cerr << "old block was allocated" << endl;
                        ++nErrors;
                    }
                    *block = threadNum;
                    int * oldBlock = blocks[i];
                    blocks[i] = block;
                    oldBlocks[i] = oldBlock;
                }

                ML::memory_barrier();
                gc.visibleBarrier();

                for (unsigned i = 0;  i < nblocks;  ++i)
                    if (oldBlocks[i]) *oldBlocks[i] = 1234;

                for (unsigned i = 0;  i < nblocks;  ++i)
                    if (oldBlocks[i]) allocator.dealloc(oldBlocks[i]);
            }

            for (unsigned i = 0;  i < nblocks;  ++i) {
                oldBlocks[i] = blocks[i];
                blocks[i] = 0;
            }

            gc.visibleBarrier();

            for (unsigned i = 0;  i < nblocks;  ++i)
                allocator.dealloc(oldBlocks[i]);

            //cerr << "nErrors = " << nErrors << endl;
        } catch (...) {
            static ML::Spinlock lock;
            lock.acquire();
            //cerr << "threadnum " << threadNum << " inEpoch "
            //     << gc.getEntry().inEpoch << endl;
            gc.dump();
            abort();
        }
    }

    void run(boost::function<void (int)> allocFn,
             int runTime = 1)
    {
        gc.getEntry();
        boost::thread_group tg;

        for (unsigned i = 0;  i < nthreads;  ++i)
            tg.create_thread(boost::bind<void>(&TestBase::doReadThread, this, i));

        for (unsigned i = 0;  i < nthreads;  ++i)
            tg.create_thread(boost::bind<void>(allocFn, i));

        for (unsigned i = 0;  i < nSpinThreads;  ++i)
            tg.create_thread(boost::bind<void>(&TestBase::doSpinThread, this));

        sleep(runTime);

        finished = true;

        tg.join_all();

        gc.deferBarrier();

        gc.dump();

        BOOST_CHECK_EQUAL(allocator.nallocs, allocator.ndeallocs);
        BOOST_CHECK_EQUAL(nerrors, 0);

        cerr << "allocs " << allocator.nallocs
             << " deallocs " << allocator.ndeallocs << endl;
        cerr << "highest " << allocator.highestAlloc << endl;

        cerr << "gc.currentEpoch() = " << gc.currentEpoch() << endl;
    }
};

#if 1
BOOST_AUTO_TEST_CASE ( test_gc_sync_many_threads_contention )
{
    cerr << "testing contention synchronized GcLock with many threads" << endl;

    int nthreads = 8;
    int nSpinThreads = 16;
    int nblocks = 2;

    TestBase<GcLock> test(nthreads, nblocks, nSpinThreads);
    test.run(boost::bind(&TestBase<GcLock>::allocThreadSync, &test, _1));
}
#endif

BOOST_AUTO_TEST_CASE ( test_gc_deferred_contention )
{
    cerr << "testing contended deferred GcLock" << endl;

    int nthreads = 8;
    int nSpinThreads = 0;//16;
    int nblocks = 2;

    TestBase<GcLock> test(nthreads, nblocks, nSpinThreads);
    test.run(boost::bind(&TestBase<GcLock>::allocThreadDefer, &test, _1));
}

#if 1

BOOST_AUTO_TEST_CASE ( test_gc_sync )
{
    cerr << "testing synchronized GcLock" << endl;

    int nthreads = 2;
    int nblocks = 2;

    TestBase<GcLock> test(nthreads, nblocks);
    test.run(boost::bind(&TestBase<GcLock>::allocThreadSync, &test, _1));
}

BOOST_AUTO_TEST_CASE ( test_gc_sync_many_threads )
{
    cerr << "testing synchronized GcLock with many threads" << endl;

    int nthreads = 8;
    int nblocks = 2;

    TestBase<GcLock> test(nthreads, nblocks);
    test.run(boost::bind(&TestBase<GcLock>::allocThreadSync, &test, _1));
}

BOOST_AUTO_TEST_CASE ( test_rcu_sync )
{
    cerr << "testing synchronized RCU" << endl;

    int nthreads = 2;
    int nblocks = 2;

    TestBase<RcuLock> test(nthreads, nblocks);
    test.run(boost::bind(&TestBase<RcuLock>::allocThreadSync, &test, _1));
}

BOOST_AUTO_TEST_CASE ( test_gc_deferred )
{
    cerr << "testing deferred GcLock" << endl;

    int nthreads = 2;
    int nblocks = 2;

    TestBase<GcLock> test(nthreads, nblocks);
    test.run(boost::bind(&TestBase<GcLock>::allocThreadDefer, &test, _1));
}

BOOST_AUTO_TEST_CASE ( test_rcu_deferred )
{
    cerr << "testing deferred RCU" << endl;

    int nthreads = 2;
    int nblocks = 2;

    TestBase<RcuLock> test(nthreads, nblocks);
    test.run(boost::bind(&TestBase<RcuLock>::allocThreadDefer, &test, _1));
}

struct SharedGcLockProxy : public SharedGcLock {
    static const char* name;
    SharedGcLockProxy() :
        SharedGcLock(GC_OPEN, name)
    {}
};
const char* SharedGcLockProxy::name = "gc_test.dat";

BOOST_AUTO_TEST_CASE( test_shared_lock_sync )
{
    cerr << "testing contention synchronized GcLock with shared lock" << endl;

    SharedGcLock lockGuard(GC_CREATE, SharedGcLockProxy::name);
    Call_Guard unlink_guard([&] { lockGuard.unlink(); });

    int nthreads = 8;
    int nSpinThreads = 16;
    int nblocks = 2;

    TestBase<SharedGcLockProxy> test(nthreads, nblocks, nSpinThreads);
    test.run(boost::bind(
                    &TestBase<SharedGcLockProxy>::allocThreadSync, &test, _1));

}

BOOST_AUTO_TEST_CASE( test_shared_lock_defer )
{
    cerr << "testing contended deferred GcLock with shared lock" << endl;

    SharedGcLock lockGuard(GC_CREATE, SharedGcLockProxy::name);
    Call_Guard unlink_guard([&] { lockGuard.unlink(); });

    int nthreads = 8;
    int nSpinThreads = 16;
    int nblocks = 2;

    TestBase<SharedGcLockProxy> test(nthreads, nblocks, nSpinThreads);
    test.run(boost::bind(
                    &TestBase<SharedGcLockProxy>::allocThreadSync, &test, _1));
}

BOOST_AUTO_TEST_CASE ( test_defer_race )
{
    cerr << "testing defer race" << endl;
    GcLock gc;

    boost::thread_group tg;

    volatile bool finished = false;

    int nthreads = 0;

    volatile int numStarted = 0;

    auto doTestThread = [&] ()
        {
            while (!finished) {
                ML::atomic_inc(numStarted);
                while (numStarted != nthreads) ;

                gc.deferBarrier();

                ML::atomic_dec(numStarted);
                while (numStarted != 0) ;
            }
        };

    for (unsigned i = 0;  i < nthreads;  ++i)
        tg.create_thread(doTestThread);

    int runTime = 1;

    sleep(runTime);

    finished = true;

    tg.join_all();
}

#endif

ext: cc

max_stars_repo_name: sharpyfox/soa

max_issues_repo_name: sharpyfox/soa

max_forks_repo_name: sharpyfox/soa


text:
#ifndef FUNCTIONS_HPP
#define FUNCTIONS_HPP

#include <iostream>
#include <vector>
#define _USE_MATH_DEFINES
#include <math.h>
#include <array>
#include <random>

#include <Eigen/Dense>
#include "particle.hpp"
#include "constants.hpp"

using namespace Eigen;

MatrixXd CalcInput(const float &time);

std::array<MatrixXd,2> Observation(MatrixXd &x_true, MatrixXd &xd, const MatrixXd &u, const MatrixXd &RFID);

MatrixXd MotionModel(const MatrixXd &x, const MatrixXd &u);

double Pi2Pi(const double &angle);

#endif // FUNCTIONS_HPP


text:
//
//  Copyright Silvin Lubecki 2011
//
//  Distributed under the Boost Software License, Version 1.0. (See
//  accompanying file LICENSE_1_0.txt or copy at
//  http://www.boost.org/LICENSE_1_0.txt)
//

#include "depend_pch.h"
#include "InternalModuleResolver.h"
#include "Finder_ABC.h"
#include <xeumeuleu/xml.hpp>
#include <boost/bind.hpp>
#include <boost/foreach.hpp>
#include <boost/filesystem.hpp>

namespace bfs = boost::filesystem;
using namespace depend;

namespace
{
    void AddPath( xml::xistream& xis, std::vector< std::string >& paths )
    {
        std::string path;
        xis >> path;
        paths.push_back( path );
    }
}

// -----------------------------------------------------------------------------
// Name: InternalModuleResolver constructor
// Created: SLI 2011-02-16
// -----------------------------------------------------------------------------
InternalModuleResolver::InternalModuleResolver( xml::xisubstream xis, const Finder_ABC& finder, Subject< UnitObserver_ABC >& unitObserver )
    : Observer< UnitObserver_ABC >( unitObserver )
    , finder_( finder )
{
    xis >> xml::start( "paths" )
            >> xml::list( "path", boost::bind( &AddPath, _1, boost::ref( paths_ ) ) );
}

// -----------------------------------------------------------------------------
// Name: InternalModuleResolver destructor
// Created: SLI 2011-02-16
// -----------------------------------------------------------------------------
InternalModuleResolver::~InternalModuleResolver()
{
    // NOTHING
}

// -----------------------------------------------------------------------------
// Name: InternalModuleResolver::Resolve
// Created: SLI 2011-02-17
// -----------------------------------------------------------------------------
std::string InternalModuleResolver::Resolve( const std::string& module, const std::string& file, const std::string& include ) const
{
    bfs::path fileContext = bfs::path( file ).parent_path();
    bfs::path includePath( include );
    BOOST_FOREACH( const std::string& path, paths_ )
    {
        if( finder_.Find( ( bfs::path( path ) / module / fileContext / includePath ).string() ) )
            return module;
    }
    const size_t position = include.find_first_of( '/' );
    const std::string unit = include.substr( 0, position );
    if( position != std::string::npos && units_.find( unit ) != units_.end() )
    {
        BOOST_FOREACH( const std::string& path, paths_ )
        {
            if( finder_.Find( ( bfs::path( path ) / includePath ).string() ) )
                return unit;
        }
    }
    return "";
}

// -----------------------------------------------------------------------------
// Name: InternalModuleResolver::NotifyUnit
// Created: SLI 2011-02-17
// -----------------------------------------------------------------------------
void InternalModuleResolver::NotifyUnit( const std::string& unit, const std::string& /*context*/ )
{
    units_.insert( unit );
}

max_stars_repo_name: vinsle/dependency-analysis

max_issues_repo_name: vinsle/dependency-analysis

max_forks_repo_name: vinsle/dependency-analysis


text:
#ifndef JIMBO_LOG_EXECUTIONTIME_HXX
#define JIMBO_LOG_EXECUTIONTIME_HXX

/////////////////////////////////////////////////////////
// executiontime.hxx
//
// Ben Storey
//
// Little helper if I ever want to log how long a function takes to execute
//
/////////////////////////////////////////////////////////

#include <boost/noncopyable.hpp>
#include <chrono>
#include "log/logging.hpp"

namespace jimbo
{
    namespace log
    {
        class LogExecutionTime : boost::noncopyable
        {
        public:

            LogExecutionTime() : start_(std::chrono::high_resolution_clock::now()) { }
            ~LogExecutionTime()
            {
                auto duration = std::chrono::high_resolution_clock::now() - start_;
                LOG("Block executed in " + std::to_string(std::chrono::duration_cast<std::chrono::milliseconds>(duration).count()) + " milliseconds");
            }

        private:
            std::chrono::high_resolution_clock::time_point start_;
        };
    }
}

#endif // JIMBO_LOG_EXECUTIONTIME_HXX

ext: hxx

max_stars_repo_name: BenStorey/Jimbo

max_issues_repo_name: BenStorey/Jimbo

max_forks_repo_name: BenStorey/Jimbo


text:
//
// Copyright yutopp 2013 - .
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
//

#ifndef RILL_AST_DETAIL_TREE_VISITOR_BASE_HPP
#define RILL_AST_DETAIL_TREE_VISITOR_BASE_HPP

#include <memory>
#include <iostream>
#include <typeinfo>
#include <type_traits>

#include <boost/core/demangle.hpp>

#include "../../config/macros.hpp"
#include "../../environment/environment_fwd.hpp"

#include "macros_for_visitor.hpp"
#include "visitor_delegator.hpp"
#include "tree_visitor_result_t.hpp"
#include "tree_visitor_default_value.hpp"
#include "../statement_fwd.hpp"

namespace rill
{
    namespace ast
    {
        namespace detail
        {
            // base class of ast visitors
            template<typename Derived, typename ReturnT, typename Messaging>
            struct tree_visitor_base
                : public Messaging
            {
            private:
                using mc_type = Messaging;

            public:
                typedef tree_visitor_base               self_type;
                typedef self_type const                 const_self_type;

                template<typename NodeT>
                using result_type = tree_visitor_result_t<ReturnT, NodeT>;

            public:
                tree_visitor_base()
                    : delegator_( static_cast<Derived*>( this ) )
                {}

                virtual ~tree_visitor_base() {};

            protected:
                // called from derived visitor
                template<typename Node, typename Env>
                auto invoke( std::shared_ptr<Node> const& node, std::shared_ptr<Env> const& env )
                    -> result_type<Node>
                try {
                    char storage[sizeof(std::conditional_t<!std::is_same<result_type<Node>, void>::value, result_type<Node>, char/*temp*/>)+RILL_MAX_ALIGN];
                    auto const p = node->dispatch(
                        node,
                        delegator_,
                        env,
                        static_cast<char*>( storage )
                        );

                    return make_return_value<result_type<Node>>{}( p );

                } catch( typename mc_type::message_type const& e ) {
                    if ( std::is_base_of<statement, Node>::value ) {
                        auto cp = e;    // copy
                        mc_type::save_message( std::move( cp ) );
                        mc_type::is_error_state( false );
                        return make_default_return_value<result_type<Node>>{}();       // implies failed...

                    } else {
                        throw;
                    }
                }

                template<typename Node, typename Env>
                auto invoke( std::shared_ptr<Node> const& node, std::shared_ptr<Env> const& env ) const
                    -> result_type<Node>
                try {
                    char storage[sizeof(std::conditional_t<!std::is_same<result_type<Node>, void>::value, result_type<Node>, char/*temp*/>)+RILL_MAX_ALIGN];
                    auto const p = node->dispatch(
                        node,
                        delegator_,
                        env,
                        static_cast<char*>( storage )
                        );

                    return make_return_value<result_type<Node>>{}( p );

                } catch( typename mc_type::message_type const& e ) {
                    if ( std::is_base_of<statement, Node>::value ) {
                        auto cp = e;    // copy
                        mc_type::save_message( std::move( cp ) );
                        mc_type::is_error_state( false );
                        return make_default_return_value<result_type<Node>>{}();       // implies failed...

                    } else {
                        throw;
                    }
                }

                template<typename Node>
                auto failed_to_dispatch()
                    -> result_type<Node>
                {
                    rill_dout << "!!! DEBUG: this AST node was not implemented" << std::endl
                              << "VISITOR -> " << boost::core::demangle( typeid( *this ).name() ) << std::endl
                              << "AST     -> " << boost::core::demangle( typeid( Node* ).name() ) << " / is_const: " << std::is_const<Node>::value << std::endl;

                    return make_default_return_value<result_type<Node>>{}();
                }

                template<typename Node>
                auto failed_to_dispatch() const
                    -> result_type<Node>
                {
                    rill_dout << "!!! DEBUG: this AST node was not implemented" << std::endl
                              << "VISITOR -> " << boost::core::demangle( typeid( *this ).name() ) << " / const" << std::endl
                              << "AST     -> " << boost::core::demangle( typeid( Node* ).name() ) << " / is_const: " << std::is_const<Node>::value << std::endl;

                    return make_default_return_value<result_type<Node>>{}();
                }

            private:
                visitor_delegator<Derived, ReturnT> delegator_;
            };

        } // namespace detail
    } // namespace ast
} // namespace rill

#endif /*RILL_AST_DETAIL_TREE_VISITOR_BASE_HPP*/

max_stars_repo_name: rhysd/rill

max_issues_repo_name: rhysd/rill

max_forks_repo_name: rhysd/rill


text:
#include <boost/test/unit_test.hpp>

#include <headers/logs.h>
#include "route.h"
#include "track.h"

using namespace GPS;

BOOST_AUTO_TEST_SUITE( Route_netLength )

const bool isFileName = true;
/*
 *This part of the test case checks the netlenght of the route with a change of direction in the
 *route along the gridlock
 */
//Check if function is able to determine netLength of ABBM.gpx
BOOST_AUTO_TEST_CASE( Route_ABBM )
{
    Route route = Route(LogFiles::GPXRoutesDir + "ABBM.gpx", isFileName);
    BOOST_CHECK_EQUAL(route.netLength(), 38.0 );
}
/*
 *This part checks the route length of a direct route without any chages to the direction
*/
//Check if function is able to determine netLength of ABCD.gpx
BOOST_AUTO_TEST_CASE( Route_ABCD )
{
    Route route = Route(LogFiles::GPXRoutesDir + "ABCD.gpx", isFileName);
    BOOST_CHECK_EQUAL(route.netLength(), 30.0 );
}

/*
 *This part checks the route length of a route thats made up of stationay points
 *the route shows no change therefore the length should remain stationary being zero
*/
//Check if function is able to determine netLength of RouteStationaryPoints.gpx
BOOST_AUTO_TEST_CASE( Route_RouteStationaryPoints )
{
    Route route = Route(LogFiles::GPXRoutesDir + "RouteStationaryPoints.gpx", isFileName);
    BOOST_CHECK_EQUAL(route.netLength(), 0.0 );
}

/*
 *This part checks the route length against a single point on the route as shown by the gpx file
 *Being a single point the length should not change.
*/
//Check if function is able to determine netLength of RouteSinglePosition.gpx
BOOST_AUTO_TEST_CASE( Route_RouteSinglePosition )
{
    Route route = Route(LogFiles::GPXRoutesDir + "RouteSinglePosition.gpx", isFileName);
    BOOST_CHECK_EQUAL(route.netLength(), 0.0 );
}

/*
 *This part checks the route length with a change in elevation and change in direction
 *This is a complex route and determines whether the function can determine the length
 *of the route with this variations
*/
//Check if function is able to determine netLength of Everest.gpx
BOOST_AUTO_TEST_CASE( Route_Everest )
{
    Route route = Route(LogFiles::GPXRoutesDir + "Everest.gpx", isFileName);
    BOOST_CHECK_EQUAL(route.netLength(), 141.1 );
}

/*
 *This part of the test checks the route length with an invalid input in the elevation
 *Checks to see if it can rean string inoput inplace of int value.
*/
//Check if function is able to determine netLength of InvalidInput.gpx
BOOST_AUTO_TEST_CASE( Route_InvalidInput )
{
    Route route = Route(LogFiles::GPXRoutesDir + "InvalidInput.gpx", isFileName);
    BOOST_CHECK_EQUAL(route.netLength(), 300.0 );
}

/*
 *This part checks the route length of the route edge with an elevation. The outcome should be similar to that of
 *a single point route.
*/
//Check if function is able to determine netLength of Edge.gpx
BOOST_AUTO_TEST_CASE( Route_Edge )
{
    Route route = Route(LogFiles::GPXRoutesDir + "Edge.gpx", isFileName);
    BOOST_CHECK_EQUAL(route.netLength(), 0.0 );
}

BOOST_AUTO_TEST_SUITE_END()

max_stars_repo_name: EdwinLangley/GPX-Route-and-Track

max_issues_repo_name: EdwinLangley/GPX-Route-and-Track

max_forks_repo_name: EdwinLangley/GPX-Route-and-Track


text:
// Boost.Geometry (aka GGL, Generic Geometry Library)
//
// Copyright (c) 2007-2011 Barend Gehrels, Amsterdam, the Netherlands.
// Use, modification and distribution is subject to the Boost Software License,
// Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)

// SOCI example

// a: using boost::tuple to retrieve points

// SOCI is a generic C++ template interface to access relational databases

// To build and run this example:
// 1) download SOCI from http://soci.sourceforge.net/
// 2) put it in contrib/soci-3.0.0 (or another version/folder, but then update this VCPROJ)
// 3) adapt your makefile or use this VCPROJ file
//    (note that SOCI sources are included directly, building SOCI is not necessary)
// 4) load the demo-data, see script data/cities.sql (for PostgreSQL)

#include <soci.h>
#include <soci-postgresql.h>

#include <boost/algorithm/string.hpp>
#include <boost/optional.hpp>
#include <boost/timer.hpp>
#include <boost/random.hpp>
#include <boost/tuple/tuple.hpp>

#include <iostream>
#include <istream>
#include <ostream>
#include <sstream>
#include <string>
#include <exception>

#include <boost/geometry/geometry.hpp>
#include <boost/geometry/geometries/adapted/boost_tuple.hpp>
#include <boost/geometry/domains/gis/io/wkt/wkt.hpp>

BOOST_GEOMETRY_REGISTER_BOOST_TUPLE_CS(cs::cartesian);

int main()
{
    try
    {
        soci::session sql(soci::postgresql, "dbname=ggl user=ggl password=ggl");

        int count;
        sql << "select count(*) from cities", soci::into(count);
        std::cout << "# Capitals: " << count << std::endl;

        typedef std::vector<boost::tuple<double, double> > V;

        soci::rowset<boost::tuple<double, double> > rows
            = sql.prepare << "select x(location),y(location) from cities";
        V vec;
        std::copy(rows.begin(), rows.end(), std::back_inserter(vec));

        for (V::const_iterator it = vec.begin(); it != vec.end(); ++it)
        {
            std::cout << it->get<0>() << " " << it->get<1>() << std::endl;
        }
        // Calculate distances
        for (V::const_iterator it1 = vec.begin(); it1 != vec.end(); ++it1)
        {
            for (V::const_iterator it2 = vec.begin(); it2 != vec.end(); ++it2)
            {
                std::cout << boost::geometry::dsv(*it1) << " " << boost::geometry::distance(*it1, *it2) << std::endl;
            }
        }
    }
    catch (std::exception const &e)
    {
        std::cerr << "Error: " << e.what() << '\n';
    }
    return 0;
}


text:
/****************************************************************************
 *  hipipe library
 *  Copyright (c) 2017, Cognexa Solutions s.r.o.
 *  Copyright (c) 2018, Iterait a.s.
 *  Author(s) Filip Matzner
 *
 *  This file is distributed under the MIT License.
 *  See the accompanying file LICENSE.txt for the complete license agreement.
 ****************************************************************************/

#define BOOST_TEST_DYN_LINK
#define BOOST_TEST_MODULE for_each_test

#include "common.hpp"

#include <hipipe/core/stream/for_each.hpp>

#include <boost/test/unit_test.hpp>
#include <range/v3/range/conversion.hpp>

BOOST_AUTO_TEST_CASE(test_for_each_of_two)
{
    using hipipe::stream::batch_t;
    using hipipe::stream::from;
    using hipipe::stream::to;

    batch_t batch1, batch2;
    std::vector<batch_t> data;
    batch1.insert_or_assign<Int>();
    batch1.extract<Int>().push_back(1);
    batch1.extract<Int>().push_back(3);
    batch1.insert_or_assign<Double>();
    batch1.extract<Double>().push_back(5.);
    batch1.extract<Double>().push_back(6.);
    data.push_back(std::move(batch1));
    batch2.insert_or_assign<Int>();
    batch2.extract<Int>().push_back(1);
    batch2.insert_or_assign<Double>();
    batch2.extract<Double>().push_back(2.);
    data.push_back(std::move(batch2));

    // for_each of two columns
    int sum = 0;
    std::vector<batch_t> stream = data
      | rgv::move
      | hipipe::stream::for_each(from<Int, Double>,
          [&sum](const int& v, double c) { sum += v; }
        )
      | rg::to_vector;

    BOOST_TEST(sum == 5);
    BOOST_TEST(stream.size() == 2);
    BOOST_TEST(stream.at(0).extract<Int>()    == (std::vector<int>{1, 3}));
    BOOST_TEST(stream.at(0).extract<Double>() == (std::vector<double>{5., 6.}));
    BOOST_TEST(stream.at(1).extract<Int>()    == (std::vector<int>{1}));
    BOOST_TEST(stream.at(1).extract<Double>() == (std::vector<double>{2.}));
}

BOOST_AUTO_TEST_CASE(test_for_each_mutable)
{
    using hipipe::stream::batch_t;
    using hipipe::stream::from;
    using hipipe::stream::to;

    batch_t batch1, batch2;
    std::vector<batch_t> data;
    batch1.insert_or_assign<Int>();
    batch1.extract<Int>().push_back(1);
    batch1.extract<Int>().push_back(3);
    data.push_back(std::move(batch1));
    batch2.insert_or_assign<Int>();
    batch2.extract<Int>().push_back(5);
    batch2.extract<Int>().push_back(7);
    data.push_back(std::move(batch2));

    struct {
        int i = 0;
        std::shared_ptr<int> i_ptr = std::make_shared<int>(0);
        void operator()(const int&) { *i_ptr = ++i; }
    } func;

    data
      | rgv::move
      | hipipe::stream::for_each(from<Int>, func)
      | rg::to_vector;

    BOOST_TEST(*(func.i_ptr) == 4);
}

BOOST_AUTO_TEST_CASE(test_for_each_move_only)
{
    using hipipe::stream::batch_t;
    using hipipe::stream::from;
    using hipipe::stream::to;

    batch_t batch1, batch2;
    std::vector<batch_t> data;
    batch1.insert_or_assign<Int>();
    batch1.extract<Int>().push_back(3);
    batch1.insert_or_assign<Unique>();
    batch1.extract<Unique>().push_back(std::make_unique<int>(5));
    data.push_back(std::move(batch1));
    batch2.insert_or_assign<Int>();
    batch2.extract<Int>().push_back(1);
    batch2.insert_or_assign<Unique>();
    batch2.extract<Unique>().push_back(std::make_unique<int>(2));
    data.push_back(std::move(batch2));

    std::vector<int> generated;
    data
      | rgv::move
      | for_each(from<Int, Unique>,
          [&generated](const int& v, const std::unique_ptr<int>& p) {
              generated.push_back(v + *p);
        })
      | rg::to_vector;

    BOOST_TEST(generated == (std::vector<int>{8, 3}));
}

BOOST_AUTO_TEST_CASE(test_for_each_dim0)
{
    using hipipe::stream::batch_t;
    using hipipe::stream::from;
    using hipipe::stream::to;
    using hipipe::stream::dim;

    batch_t batch1, batch2;
    std::vector<batch_t> data;
    batch1.insert_or_assign<Int>();
    batch1.extract<Int>().push_back(3);
    batch1.insert_or_assign<Unique>();
    batch1.extract<Unique>().push_back(std::make_unique<int>(5));
    data.push_back(std::move(batch1));
    batch2.insert_or_assign<Int>();
    batch2.extract<Int>().push_back(1);
    batch2.insert_or_assign<Unique>();
    batch2.extract<Unique>().push_back(std::make_unique<int>(2));
    data.push_back(std::move(batch2));

    std::vector<int> generated;
    data
      | rgv::move
      | hipipe::stream::for_each(from<Int, Unique>,
          [&generated](const std::vector<int>& int_batch,
                       const std::vector<std::unique_ptr<int>>& ptr_batch) {
              generated.push_back(*(ptr_batch[0]) + int_batch[0]);
        }, dim<0>)
      | rg::to_vector;

    BOOST_TEST(generated == (std::vector<int>{8, 3}));
}

BOOST_AUTO_TEST_CASE(test_for_each_dim2_move_only)
{
    using hipipe::stream::batch_t;
    using hipipe::stream::from;
    using hipipe::stream::to;
    using hipipe::stream::dim;

    std::vector<batch_t> data = generate_move_only_data_2d();

    std::vector<int> generated;
    data
      | rgv::move
      | hipipe::stream::for_each(from<UniqueVec>,
          [&generated](std::unique_ptr<int>& ptr) {
              generated.push_back(*ptr + 1);
          }, dim<2>)
      | rg::to_vector;

    BOOST_TEST(generated == (std::vector<int>{7, 4, 8, 5, 3, 2, 3, 9}));
}

BOOST_AUTO_TEST_CASE(test_for_each_dim2_move_only_mutable)
{
    using hipipe::stream::batch_t;
    using hipipe::stream::from;
    using hipipe::stream::to;
    using hipipe::stream::dim;

    std::vector<batch_t> data = generate_move_only_data_2d();

    std::vector<int> generated;
    data
      | rgv::move
      | hipipe::stream::for_each(from<UniqueVec>,
          [&generated, i = 4](std::unique_ptr<int>&) mutable {
              generated.push_back(i++);
          }, dim<2>)
      | rg::to_vector;

    BOOST_TEST(generated == (std::vector<int>{4, 5, 6, 7, 8, 9, 10, 11}));
}

max_stars_repo_name: iterait/hipipe

max_issues_repo_name: iterait/hipipe

max_forks_repo_name: iterait/hipipe


text:
#include "mcc.h"
#include "PointVector.h"
#include "XyzPoint.h"
#include "XyExtent.h"
#include "IClassificationVector.h"
#include "SurfaceInterpolation.h"
#include "Algorithm.h"
#include "UnclassifiedPoints.h"
#include "PointClassification.h"
#include <cmath>

#include <boost/shared_ptr.hpp>

using boost::shared_ptr;
using namespace mcc;

// Read a vector of points from arrays.
shared_ptr<PointVector> readPoints(double *x,
								   double *y,
								   double *z,
								   int n,
                                   XyExtent &                      xyExtent) {

	shared_ptr<PointVector> pts(new PointVector(n));
	xyExtent.minX = std::nan("1");
	xyExtent.minY = std::nan("1");
	xyExtent.maxX = std::nan("1");
	xyExtent.maxY = std::nan("1");

	for(int i=0; i < n; i++) {

		(*pts)[i].setCoordinates(XyzPoint(x[i], y[i], z[i]));

		xyExtent.minX = (std::isnan(xyExtent.minX) | (x[i] < xyExtent.minX)) ? x[i] : xyExtent.minX;
		xyExtent.maxX = (std::isnan(xyExtent.maxX) | (x[i] > xyExtent.maxX)) ? x[i] : xyExtent.maxX;
		xyExtent.minY = (std::isnan(xyExtent.minY) | (y[i] < xyExtent.minY)) ? y[i] : xyExtent.minY;
		xyExtent.maxY = (std::isnan(xyExtent.maxY) | (y[i] > xyExtent.maxY)) ? y[i] : xyExtent.maxY;
	}

	return pts;
}

uint8_t * mcc_classify(double *x, double *y, double *z, int n, double scaleDomain2Spacing, double curvatureThreshold) {

	XyExtent xyExtent;
	shared_ptr<PointVector> points = readPoints(x, y, z, n, xyExtent);

	SurfaceInterpolation surfaceInterpolation;
	surfaceInterpolation.setXyExtent(xyExtent);

	Algorithm algorithm(surfaceInterpolation, false, false);
	UnclassifiedPoints unclassifiedPoints(points);
	algorithm.classifyPoints(unclassifiedPoints, scaleDomain2Spacing, curvatureThreshold);

	uint8_t *classification = new uint8_t[n];
	IClassificationVector::index_type i;
	for (i.value = 0; i.value < n; i.value++) {
		if(mcc::isGround((*points)[i])) {
			classification[i.value] = 2;
		} else {
			classification[i.value] = 1;
		}
	}

	return classification;

}

double * mcc_pass(double *x, double *y, double *z, int n, double scaleDomainSpacing) {

	XyExtent xyExtent;
	shared_ptr<PointVector> points = readPoints(x, y, z, n, xyExtent);

	SurfaceInterpolation surfaceInterpolation;
	surfaceInterpolation.setXyExtent(xyExtent);

	Algorithm algorithm(surfaceInterpolation, false, false);
	UnclassifiedPoints unclassifiedPoints(points);
	algorithm.labelPointsUsingPass(unclassifiedPoints, scaleDomainSpacing);

	double *h = new double[n];
	for (int i = 0; i < n; i++) {
		h[i] = (*points)[i].h();
	}

	return h;

}

max_stars_repo_name: rmsare/pymcc

max_issues_repo_name: rmsare/pymcc

max_forks_repo_name: rmsare/pymcc


text:
#include "zurbank/zurbank.h"
#include "zurbank/rules.h"

#include "test/test_zurcoin.h"

#include <stdint.h>
#include <limits>

#include <boost/test/unit_test.hpp>

using namespace mastercore;

BOOST_FIXTURE_TEST_SUITE(zurbank_rules_txs_tests, BasicTestingSetup)

const int MAX_BLOCK = std::numeric_limits<int>::max();
const int MAX_VERSION = std::numeric_limits<uint16_t>::max();

BOOST_AUTO_TEST_CASE(simple_send_restrictions)
{
    int MSC_SEND_BLOCK = ConsensusParams().MSC_SEND_BLOCK;

    BOOST_CHECK(!IsTransactionTypeAllowed(0,                OMNI_PROPERTY_ZUR,  MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V0));
    BOOST_CHECK(!IsTransactionTypeAllowed(MSC_SEND_BLOCK,   OMNI_PROPERTY_ZUR,  MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V0));
    BOOST_CHECK(!IsTransactionTypeAllowed(MAX_BLOCK,        OMNI_PROPERTY_ZUR,  MSC_TYPE_SIMPLE_SEND, MAX_VERSION));
    BOOST_CHECK(!IsTransactionTypeAllowed(0,                OMNI_PROPERTY_MSC,  MSC_TYPE_SIMPLE_SEND, MAX_VERSION));
    BOOST_CHECK(!IsTransactionTypeAllowed(MSC_SEND_BLOCK-1, OMNI_PROPERTY_MSC,  MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V0));
    BOOST_CHECK(!IsTransactionTypeAllowed(MAX_BLOCK,        OMNI_PROPERTY_MSC,  MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V1));
    BOOST_CHECK(!IsTransactionTypeAllowed(MSC_SEND_BLOCK,   OMNI_PROPERTY_TMSC, MSC_TYPE_SIMPLE_SEND, MAX_VERSION));
    BOOST_CHECK(!IsTransactionTypeAllowed(MAX_BLOCK,        OMNI_PROPERTY_TMSC, MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V1));

    BOOST_CHECK(IsTransactionTypeAllowed(MSC_SEND_BLOCK,    OMNI_PROPERTY_MSC,  MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V0));
    BOOST_CHECK(IsTransactionTypeAllowed(MAX_BLOCK,         OMNI_PROPERTY_MSC,  MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V0));
    BOOST_CHECK(IsTransactionTypeAllowed(0,                 OMNI_PROPERTY_TMSC, MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V0));
    BOOST_CHECK(IsTransactionTypeAllowed(MAX_BLOCK,         OMNI_PROPERTY_TMSC, MSC_TYPE_SIMPLE_SEND, MP_TX_PKT_V0));
}

BOOST_AUTO_TEST_SUITE_END()


text:
#include <boost/bimap.hpp>

int main()
{
	boost::bimap<int, int> test;
}