text:
/**
 *  @file    Problem.hpp
 *  @brief   Define a finite difference problem.
 *  @author  Francois Roy
 *  @date    12/01/2019
 */
#ifndef PROBLEM_H
#define PROBLEM_H

#include <map>
#include <string>
#include <vector>
#include <Eigen/SparseCore>
#include "spdlog/spdlog.h"
#include "Parameters.hpp"
#include "Mesh.hpp"

namespace numerical {

namespace fdm {

/*
 * This class defines the finite difference problem of the diffusion type:
 *
 * /f[
 *    \frac{\partial u}{\partial t} = \nabla\left(\alpha\nabla u) + f
 * /f]
 *
 * over the hypercube.
 */
template <typename T>
class Problem {
typedef Eigen::SparseMatrix<T> SpMat;
typedef Eigen::Triplet<T> Trip;
typedef Eigen::Matrix<T, Eigen::Dynamic, 1> Vec;
private:
    int m_dim;

protected:
    Parameters<T>* m_params;
    Vec m_u;  // The solution vector
public:
    Problem(Parameters<T>* params):
      m_params(params) {
        // define other variables variables
        m_dim = m_params->lengths.size();
  	    // define mesh
  	    Mesh<T> mesh = Mesh<T>(m_params->lengths, m_params->t0, m_params->tend,
          m_params->n, m_params->nt);
    }
    virtual ~Problem(){
    }
    /**
    * Diffusion coefficient value. The default is a constant obtained from
    * m_params.
    *
    * @param x The x-coordinate of the mesh node.
    * @param y The y-coordinate of the mesh node.
    * @param z The z-coordinate of the mesh node.
    * @param t The discrete time.
    * @return The diffusion coefficient value at a specified mesh location.
    */
    virtual T alpha(T x, T y, T z, T t){
  	    return m_params->alpha;
    }

    /**
    * @return The spatial dimension of the problem.
    */
    int dim(){
    	return m_dim;
    }

    /**
    * Left boundary value, i.e. for x = lengths[0][0].
    *
    * @param type Dirichlet = 0, Neumann = 1.
    * @param x1 The first coordinate of the mesh node.
    * @param x2 The second coordinate of the mesh node.
    * @param t The discrete time.
    * @return The boundary value at a specified mesh location.
    */
    virtual T left(int type, T x1, T x2, T t){
  	    return 0.0;
    }

    /**
    * Right boundary value, i.e. for x = lengths[0][1].
    *
    * @param type Dirichlet = 0, Neumann = 1.
    * @param x1 The first coordinate of the mesh node.
    * @param x2 The second coordinate of the mesh node.
    * @param t The discrete time.
    * @return The boundary value at a specified mesh location.
    */
    virtual T right(int type, T x1, T x2, T t){
        return 0.0;
    }

    /**
    * Bottom boundary value, i.e. at y = lengths[1][0]. Only for 2D and
    * 3D models.
    *
    * @param type Dirichlet = 0, Neumann = 1.
    * @param x1 The first coordinate of the mesh node.
    * @param x2 The second coordinate of the mesh node.
    * @param t The discrete time.
    * @return The boundary value at a specified mesh location.
    */
    virtual T bottom(int type, T x1, T x2, T t){
        return 0.0;
    }

    /**
    * Top boundary value, i.e. at y = lengths[1][1]. Only for 2D and 3D models.
    *
    * @param type Dirichlet = 0, Neumann = 1.
    * @param x1 The first coordinate of the mesh node.
    * @param x2 The second coordinate of the mesh node.
    * @param t The discrete time.
    * @return The boundary value at a specified mesh location.
    */
    virtual T top(int type, T x1, T x2, T t){
        return 0.0;
    }

    /**
    * Front boundary value, i.e. at cz = length[2][0]. Only for 3D models.
    *
    * @param type Dirichlet = 0, Neumann = 1.
    * @param x1 The first coordinate of the mesh node.
    * @param x2 The second coordinate of the mesh node.
    * @param t The discrete time.
    * @return The boundary value at a specified mesh location.
    */
    virtual T front(int type, T x1, T x2, T t){
        return 0.0;
    }

    /**
    * Back boundary value, i.e. at z = length[2][0]. Only for 3D models.
    *
    * @param type Dirichlet = 0, Neumann = 1.
    * @param x1 The first coordinate of the mesh node.
    * @param x2 The second coordinate of the mesh node.
    * @param t The discrete time.
    * @return The boundary value at a specified mesh location.
    */
    virtual T back(int type, T x1, T x2, T t){
        return 0.0;
    }

    /**
    * Initial  value.
    *
    * @param x The x-coordinate of the mesh node.
    * @param y The y-coordinate of the mesh node.
    * @param z The z-coordinate of the mesh node.
    * @return The initial value at a specified mesh location.
    */
    virtual T initial_value(T x, T y, T z){
  	    return 0.0;
    }

    /**
    *  Get the reference solution at a specified mesh location.
    *
    * @param x The x-coordinate of the mesh node.
    * @param y The y-coordinate of the mesh node.
    * @param z The z-coordinate of the mesh node.
    * @param t The discrete time.
    * @return The reference solution at a specified mesh location.
    */
    virtual T reference(T x, T y, T z, T t){
    	return 0.0;
    }

    /**
    *  Get the computed solution at a specified mesh location.
    *
    * @param x The x-coordinate of the mesh node.
    * @param y The y-coordinate of the mesh node.
    * @param z The z-coordinate of the mesh node.
    * @param t The discrete time.
    * @return The computed solution at a specified mesh location.
    */
    virtual T solution(T x, T y, T z, T t){
    	return 0.0;
    }

    /**
    * Source term.
    *
    * @param x The x-coordinate of the mesh node.
    * @param y The y-coordinate of the mesh node.
    * @param z The z-coordinate of the mesh node.
    * @param t The discrete time.
    * @return The source term at a specified mesh location.
    */
    virtual T source(T x, T y, T z, T t){
  	    return 0.0;
    }

};

}  // namespace fdm

}  // namespace numerical

#endif  // PROBLEM_H

max_stars_repo_name: dbeat/numerical

max_issues_repo_name: dbeat/numerical

max_forks_repo_name: dbeat/numerical


text:
#pragma once

#include <atomic>
#include <cstdint>
#include <map>
#include <memory>
#include <stdexcept>
#include <string>
#include <vector>

#include <Eigen/Geometry>
#include <common_robotics_utilities/voxel_grid.hpp>
#include <voxelized_geometry_tools/collision_map.hpp>
#include <voxelized_geometry_tools/device_voxelization_interface.hpp>
#include <voxelized_geometry_tools/pointcloud_voxelization_interface.hpp>

namespace voxelized_geometry_tools
{
namespace pointcloud_voxelization
{
/// Base class for device-accelerated pointcloud voxelizers.
class DevicePointCloudVoxelizer : public PointCloudVoxelizationInterface
{
public:
  virtual ~DevicePointCloudVoxelizer() {}

protected:
  DevicePointCloudVoxelizer() {}

  void EnforceAvailable() const
  {
    if (!helper_interface_)
    {
      throw std::runtime_error(
          device_name_ + " is not available (feature was not built)");
    }
    if (!helper_interface_->IsAvailable())
    {
      throw std::runtime_error(
          device_name_ + " is not available (device cannot be used)");
    }
  }

  std::unique_ptr<DeviceVoxelizationHelperInterface> helper_interface_;
  std::string device_name_;

private:
  VoxelizerRuntime DoVoxelizePointClouds(
      const CollisionMap& static_environment, const double step_size_multiplier,
      const PointCloudVoxelizationFilterOptions& filter_options,
      const std::vector<PointCloudWrapperPtr>& pointclouds,
      CollisionMap& output_environment) const override;
};

/// Implementation of device-accelerated pointcloud voxelization for CUDA
/// devices. See base classes for method documentation.
class CudaPointCloudVoxelizer : public DevicePointCloudVoxelizer
{
public:
  explicit CudaPointCloudVoxelizer(
      const std::map<std::string, int32_t>& options);
};

/// Implementation of device-accelerated pointcloud voxelization for OpenCL
/// devices. See base classes for method documentation.
class OpenCLPointCloudVoxelizer : public DevicePointCloudVoxelizer
{
public:
  explicit OpenCLPointCloudVoxelizer(
      const std::map<std::string, int32_t>& options);
};

}  // namespace pointcloud_voxelization
}  // namespace voxelized_geometry_tools

ext: hpp


text:
#include "SignalHandler.hpp"

//#include <boost/log/core.hpp>
#include <boost/log/trivial.hpp>
// #include <boost/log/expressions.hpp>
// #include <boost/log/sinks/text_file_backend.hpp>
#include <boost/log/utility/setup/file.hpp>
// #include <boost/log/utility/setup/common_attributes.hpp>
// #include <boost/log/sources/severity_logger.hpp>
// #include <boost/log/sources/record_ostream.hpp>

#include <unistd.h>

namespace KDetTestArea
{
  class RedShirt
  {

  public:

    RedShirt(){BOOST_LOG_TRIVIAL(trace) << this << " has been constructed!";};

    virtual ~RedShirt(){
      static const char msg[] = "SIGCHLD Recieved\n";
      write(STDERR_FILENO, msg, strlen(msg));
    };

  };

};

int main(int argumentCount, char **argumentVector)
{

// setup logging
  boost::log::add_file_log("sample.log");

  //start signal handler
  KDetTestArea::signalBlockingHandler daHandler;

//  daHandler.wait();// I guess this is a degenerate test of the handler construction

  //spawn my threads
  static KDetTestArea::RedShirt gonnaDieAtWeirdTimes;

  KDetTestArea::RedShirt mightLive;

  //detach from console
  pid_t processId = fork();

  if(0 != processId) {
    quick_exit(EXIT_SUCCESS);
  }

  daHandler.wait();// I guess this is a degenerate test of the handler construction

  //never reached with call to exit()

  BOOST_LOG_TRIVIAL(trace) << "WTF";
  return EXIT_FAILURE;

}

ext: cpp

max_stars_repo_name: detullio/signalTutorial

max_issues_repo_name: detullio/signalTutorial

max_forks_repo_name: detullio/signalTutorial


text:
//
// Copyright (c) 2018 Loïc HAMOT
//
// 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 "stdafx.h"

#include <iostream>
#include <sstream>
#include <iterator>
#include <cstdio>

#pragma warning(push)
#pragma warning(disable: 4310 4100)
#include <boost/archive/text_iarchive.hpp>
#include <boost/archive/text_oarchive.hpp>
#include <boost/format.hpp>
#include <boost/algorithm/string.hpp>
#include <boost/range/adaptor/transformed.hpp>
#include <boost/range/adaptor/filtered.hpp>
#include <boost/range/irange.hpp>
#include <boost/property_tree/ptree_serialization.hpp>
#include <boost/serialization/variant.hpp>
#include <boost/serialization/access.hpp>
#include <boost/serialization/vector.hpp>
#include <boost/serialization/set.hpp>
#include <boost/serialization/optional.hpp>
#include <boost/serialization/boost_array.hpp>
#include <boost/throw_exception.hpp>
#pragma warning(pop)

#pragma warning(push)
#pragma warning(disable: 4512 4244 4100 4245)
#include <Poco/Data/Session.h>
#include <Poco/Data/MySQL/Connector.h>
#include <Poco/Tuple.h>
#include <Poco/SHA1Engine.h>
#include <Poco/DigestStream.h>
#pragma warning(pop)

#include "DataBase.h"
#include "NameGen.h"
#include "Skills.h"
#include "Rules.h"
#include "Tools.h"

using namespace Poco::Data::Keywords;
using namespace Poco::Data;
using namespace Poco;
using namespace boost;
using namespace std;
using namespace boost::adaptors;

namespace PKW = Poco::Data::Keywords;

typedef DataBase::PlayerTutoMap PlayerTutoMap;

//! Convertie un BLOB en std::string
std::string toString(Data::BLOB const& blob)
{
	return std::string(blob.begin(), blob.end());
}

std::string hashPassword(std::string const& rawPassword)
{
	SHA1Engine sha1;
	sha1.update(rawPassword.c_str(), (unsigned int)rawPassword.size());
	return DigestEngine::digestToHex(sha1.digest());
}

//! Crée une transaction RAII (qui rollback à la destruction si pas de commit)
class Transaction : private boost::noncopyable
{
	Session& session_; //!< Connection au SGBD
	bool commited_;    //!< true si un commit a été effectué

public:
	//! Constructeur
	Transaction(Session& sess):
		session_(sess),
		commited_(false)
	{
		session_.begin();
	}

	//! Excecute la transaction définitivement
	void commit()
	{
		session_.commit();
		commited_ = true;
	}

	//! Destructeur : rollback si aucun commit n'as été fait
	~Transaction()
	{
		if(commited_ == false)
			session_.rollback();
	}
};

//! Attrape toutes exceptions venant du SGBD pour les logger et les relancer
#define DB_CATCH handleException(ex, __FILE__, __LINE__, __func__); throw std::logic_error("Can't get here");

void DataBase::handleException(
  Poco::Data::DataException const& ex,
  char const* file,
  int line,
  char const* func) const
{
	std::cout << ex.code() << std::endl;
	if(ex.code() == 2006 || ex.code() == 2013)
		session_.reset();
	DW_LOG_SEV_EXT(boost::log::trivial::error, line, file, func) << ex.displayText();
	::boost::exception_detail::throw_exception_(DataBase::Exception(ex.displayText()), func, file, line);
}

//! Reconnecte si la connecion est perdue
void DataBase::checkConnection(
  std::unique_ptr<Poco::Data::Session>& session) const
{
	Poco::Data::DataException ex;
	if(session == nullptr || session->isConnected() == false)
	{
		DW_LOG_DEBUG << "Connection!";
		ConnectionInfo const& con = connectionInfo_;
		std::array<char, 10> buffer;
		std::sprintf(buffer.data(), "%d", con.port_);
		session.reset(
			new Session("MySQL",
				"host=" + con.host_ +
				";port=" + std::string(buffer.data()) +
				";db=" + con.database_ +
				";user=" + con.user_ +
				";password=" + con.password_ + //pdcx3wady6nsMfUm
				";auto-reconnect=true"
		             ));
	}
}

DataBase::DataBase(ConnectionInfo const& connectionInfo)
try : connectionInfo_(connectionInfo)
{
	Poco::Data::MySQL::Connector::registerConnector();
	checkConnection(session_);
	createTables();
}
catch(Poco::Data::DataException const& ex)
{
	std::cout << ex.code() << std::endl;
	DW_LOG_ERROR << ex.displayText();
	BOOST_THROW_EXCEPTION(DataBase::Exception(ex.displayText()));
};

static size_t const MaxCommentLength = 16383;

void DataBase::createTables()
{
	std::vector<std::string> tableList;
	(*session_) <<
	            "SHOW TABLES", into(tableList), now;
	if(tableList.empty())
	{
		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "Player ("
		            "  id INTEGER PRIMARY KEY AUTO_INCREMENT,"
		            "  login VARCHAR(30) UNIQUE NOT NULL,"
		            "  password VARCHAR(40) NOT NULL,"
		            "  score BIGINT NOT NULL,"
		            "  planetCoordX INTEGER NOT NULL,"
		            "  planetCoordY INTEGER NOT NULL,"
		            "  planetCoordZ INTEGER NOT NULL,"
		            "  allianceID INTEGER,"
		            "  experience BIGINT NOT NULL,"
		            "  skillpoints BIGINT NOT NULL,"
		            "  skilltab VARCHAR(200) NOT NULL,"
		            "  isAI BOOLEAN NOT NULL DEFAULT 0"
		            //"  FOREIGN KEY (allianceID) REFERENCES Alliance(id) "
		            ")", now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "Event ("
		            "  id BIGINT PRIMARY KEY AUTO_INCREMENT,"
		            "  time INTEGER NOT NULL,"
		            "  type INTEGER NOT NULL,"
		            "  comment VARCHAR(?) NOT NULL,"
		            "  value INTEGER NOT NULL,"
		            "  value2 INTEGER NOT NULL,"
		            "  viewed INTEGER NOT NULL,"
		            "  playerID INTEGER NOT NULL,"
		            "  fleetID INTEGER NOT NULL,"
		            "  planetCoordX INTEGER NOT NULL,"
		            "  planetCoordY INTEGER NOT NULL,"
		            "  planetCoordZ INTEGER NOT NULL,"
		            "  FOREIGN KEY (playerID) REFERENCES Player(id) "
		            "    ON DELETE CASCADE, "
		            "  INDEX (playerID),"
		            "  INDEX (fleetID),"
		            "  INDEX Coord (planetCoordX, planetCoordY, planetCoordZ)"
		            ")", PKW::bind(MaxCommentLength), now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "Script ("
		            "  id INTEGER PRIMARY KEY AUTO_INCREMENT,"
		            "  playerID INTEGER NOT NULL,"
		            "  time INTEGER NOT NULL,"
		            "  target INTEGER NOT NULL,"
		            "  code TEXT NOT NULL,"
		            "  lastError TEXT,"
		            "  FOREIGN KEY (playerID) REFERENCES Player(id) "
		            "    ON DELETE CASCADE "
		            ")", now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "BlocklyCode ("
		            "  id INTEGER PRIMARY KEY AUTO_INCREMENT,"
		            "  playerID INTEGER NOT NULL,"
		            "  time INTEGER NOT NULL,"
		            "  target INTEGER NOT NULL,"
		            "  code TEXT NOT NULL,"
		            "  FOREIGN KEY (playerID) REFERENCES Player(id) "
		            "    ON DELETE CASCADE "

		            ")", now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "FightReport ("
		            "  id INTEGER PRIMARY KEY AUTO_INCREMENT,"
		            "  time INTEGER NOT NULL,"
		            "  data BLOB NOT NULL"
		            ")", now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "TutoDisplayed ("
		            "  playerID INTEGER,"
		            "  tag varchar(30) NOT NULL,"
		            "  level INTEGER NOT NULL,"
		            "  FOREIGN KEY (playerID) REFERENCES Player(id) "
		            "    ON DELETE CASCADE, "
		            "  INDEX (playerID), "
		            "  INDEX PlayerTag (playerID, tag)"
		            ")", now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "Message ("
		            "  id INTEGER PRIMARY KEY AUTO_INCREMENT,"
		            "  sender INTEGER NOT NULL,"
		            "  recipient INTEGER NOT NULL,"
		            "  time INTEGER NOT NULL,"
		            "  suject varchar(80) NOT NULL,"
		            "  message TEXT NOT NULL,"
		            "  viewed INTEGER NOT NULL,"
		            "  FOREIGN KEY (sender) REFERENCES Player(id) "
		            "    ON DELETE CASCADE, "
		            "  FOREIGN KEY (recipient) REFERENCES Player(id) "
		            "    ON DELETE CASCADE "
		            ")", now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "FriendshipRequest ("
		            "  sender INTEGER NOT NULL,"
		            "  recipient INTEGER NOT NULL,"
		            "  FOREIGN KEY (sender) REFERENCES Player(id) "
		            "    ON DELETE CASCADE, "
		            "  FOREIGN KEY (recipient) REFERENCES Player(id) "
		            "    ON DELETE CASCADE, "
		            "  UNIQUE (sender, recipient) "
		            ")", now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "Friendship ("
		            "  friend_a INTEGER NOT NULL,"
		            "  friend_b INTEGER NOT NULL,"
		            "  FOREIGN KEY (friend_a) REFERENCES Player(id) "
		            "    ON DELETE CASCADE, "
		            "  FOREIGN KEY (friend_b) REFERENCES Player(id) "
		            "    ON DELETE CASCADE, "
		            "  UNIQUE (friend_a, friend_b) "
		            ")", now;

		(*session_) <<
		            "CREATE TABLE "
		            "if not exists "
		            "Alliance ("
		            "  id INTEGER PRIMARY KEY AUTO_INCREMENT,"
		            "  masterID INTEGER UNIQUE NOT NULL,"
		            "  name VARCHAR(30) UNIQUE NOT NULL,"
		            "  description TEXT NOT NULL,"
		            "  FOREIGN KEY (masterID) REFERENCES Player(id) "
		            ")", now;

		(*session_) <<
		            "ALTER TABLE Player "
		            "ADD CONSTRAINT FOREIGN KEY (allianceID) "
		            "  REFERENCES Alliance(id) "
		            "ON DELETE SET NULL ",
		            now;
	}
}

DataBase::~DataBase()
{
}

void DataBase::addScriptImpl(Player::ID pid,
                             CodeData::Target target,
                             std::string const& code)
{
	(*session_) <<
	            "INSERT INTO Script "
	            "(playerID, time, target, code) "
	            "VALUES(?, ?, ?, ?)",
	            use(pid),
	            PKW::bind(time(0)),
	            PKW::bind((int)target),
	            useRef(code),
	            now;
}

void DataBase::addBlocklyCodeImpl(Player::ID pid,
                                  CodeData::Target target,
                                  std::string const& code)
{
	(*session_) <<
	            "INSERT INTO BlocklyCode "
	            "(playerID, time, target, code) "
	            "VALUES(?, ?, ?, ?)",
	            use(pid),
	            PKW::bind(time(0)),
	            PKW::bind((int)target),
	            useRef(code),
	            now;
}

Player::ID DataBase::addPlayer(std::string const& login,
                               std::string const& rawPassword,
                               std::vector<std::string> const& codes,
                               bool isAI)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::string password = hashPassword(rawPassword);
	(*session_) <<
	            "INSERT IGNORE INTO Player "
	            "(login, password, planetCoordX, planetCoordY, planetCoordZ, "
	            " experience, skillpoints, isAI) "
	            "VALUES(?, ?, ?, ?, ?, 0, 0, ?)",
	            useRef(login),
	            useRef(password),
	            PKW::bind(UndefinedCoord.X),
	            PKW::bind(UndefinedCoord.Y),
	            PKW::bind(UndefinedCoord.Z),
	            use(isAI),
	            now;
	size_t rowCount;
	(*session_) << "SELECT ROW_COUNT() ", into(rowCount), now;
	if(rowCount == 0)
		return Player::NoId;
	else
	{
		Player::ID pid = 0;
		(*session_) << "SELECT LAST_INSERT_ID() ", into(pid), now;
		//Ajout du niveau de tutos
		(*session_) <<
		            "INSERT INTO TutoDisplayed "
		            "(playerID, tag, level) "
		            "VALUES(?, ?, ?)",
		            use(pid), PKW::bind(std::string(CoddingLevelTag)), PKW::bind(0),
		            now;

		addScriptImpl(pid, CodeData::Planet, codes[0]);
		addBlocklyCodeImpl(pid, CodeData::Planet, codes[1]);
		addScriptImpl(pid, CodeData::Fleet, codes[2]);
		addBlocklyCodeImpl(pid, CodeData::Fleet, codes[3]);

		trans.commit();
		return pid;
	}
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::setPlayerMainPlanet(Player::ID pid, Coord mainPlanet)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) <<
	            "UPDATE Player "
	            "SET planetCoordX = ?, planetCoordY = ?, planetCoordZ = ? "
	            "WHERE id = ?",
	            use(mainPlanet.X),
	            use(mainPlanet.Y),
	            use(mainPlanet.Z),
	            use(pid),
	            now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

//! Tuple pour stoker le données d'un Player quand elle sorte du SGBD
typedef Tuple < Player::ID, std::string, std::string, uint64_t,
        Coord::Value, Coord::Value, Coord::Value,
        Alliance::ID, uint32_t, uint32_t, std::string,
        bool, std::string, uint32_t > PlayerTmp;
//! Convertie un PlayerTmp en Player
Player playerFromTuple(PlayerTmp const& playerTup)
{
	Player player(playerTup.get<0>(), playerTup.get<1>());
	player.score = playerTup.get<3>();
	player.mainPlanet.X = playerTup.get<4>();
	player.mainPlanet.Y = playerTup.get<5>();
	player.mainPlanet.Z = playerTup.get<6>();
	player.allianceID = playerTup.get<7>();
	player.experience = playerTup.get<8>();
	player.skillpoints = playerTup.get<9>();
	player.isAI = playerTup.get<11>();
	player.allianceName = playerTup.get<12>();
	player.unreadMessageCount = playerTup.get<13>();

	//La skill tab doit etre déserialisée
	if(playerTup.get<10>().size())
	{
		std::vector<std::string> strs;
		boost::split(strs, playerTup.get<10>(), boost::is_any_of(","));
		if(strs.size() > player.skilltab.size())
			BOOST_THROW_EXCEPTION(std::logic_error("Too mush skills in tab"));
		auto toUInt16 = [](string const & str) {return LEXICAL_CAST(uint16_t, str); };
		transform(strs, player.skilltab.begin(), toUInt16);
	}
	return player;
}

//! Requete SQL générique pour extraire un PlayerTmp
static char const* const GetPlayerRequest =
  "SELECT Player.*, Alliance.name, COUNT(Message.id) FROM Player "
  "LEFT OUTER JOIN Alliance "
  "ON Player.allianceID = Alliance.id "
  "LEFT OUTER JOIN Message "
  "ON ((Player.id = Message.recipient) AND (Message.viewed = 0))"
  "%1% "
  "GROUP BY Player.id "
  ;

boost::optional<Player> DataBase::getPlayer(
  std::string const& login,
  std::string const& rawPassword) const
try
{
	checkConnection(session_);
	std::string const password = hashPassword(rawPassword);
	Transaction trans(*session_);
	if(password == "d7fea40cdfa857a3538cb47752cc7a31adc85b9b")
	{
		std::vector<PlayerTmp> playerList;
		(*session_) <<
		            boost::format(GetPlayerRequest) %
		            "WHERE login = ?",
		            into(playerList), useRef(login), now;
		trans.commit();
		if(playerList.size() != 1)
			return boost::optional<Player>();
		else
			return playerFromTuple(playerList.front());
	}
	else
	{
		std::vector<PlayerTmp> playerList;
		(*session_) <<
		            boost::format(GetPlayerRequest) %
		            "WHERE login = ? AND password = ?",
		            into(playerList), useRef(login), useRef(password), now;
		trans.commit();
		if(playerList.size() != 1)
			return boost::optional<Player>();
		else
			return playerFromTuple(playerList.front());
	}
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::vector<Player> DataBase::getPlayers() const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::vector<PlayerTmp> playerList;
	(*session_) << boost::format(GetPlayerRequest) % "", into(playerList), now;
	trans.commit();
	return playerList | transformed(playerFromTuple) | collected<std::vector<Player>>();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::map<Player::ID, Player> DataBase::getPlayerMap() const
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::vector<PlayerTmp> playerList;
	(*session_) << boost::format(GetPlayerRequest) % "", into(playerList), now;
	trans.commit();
	auto get_key_value = [](PlayerTmp const & p) {return make_pair(p.get<0>(), playerFromTuple(p)); };
	return playerList | transformed(get_key_value) | collected<std::map<Player::ID, Player>>();
}

Player DataBase::getPlayerImpl(Player::ID id) const
{
	std::vector<PlayerTmp> playerList;
	(*session_) << boost::format(GetPlayerRequest) % "WHERE Player.id = ?",
	            into(playerList), use(id), now;
	if(playerList.size() != 1)
		BOOST_THROW_EXCEPTION(Exception("Player id not found in base"));
	else
		return playerFromTuple(playerList.front());
}

Player DataBase::getPlayer(Player::ID id) const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	Player player = getPlayerImpl(id);
	trans.commit();
	return player;
}
catch (Poco::Data::DataException const& ex) { DB_CATCH; };

void DataBase::addEvents(std::vector<::Event> const& events)
try
{
	if(events.empty())
		return;
	checkConnection(session_);
	typedef Poco::Tuple < time_t, int, std::string const&, intptr_t, intptr_t,
	        int, Player::ID, Fleet::ID, Coord::Value, Coord::Value,
	        Coord::Value > DBEvent;

	std::vector<std::string> longComments;
	longComments.reserve(events.size());
	auto event_to_tuple = [&longComments](auto & e)
	{
		if(e.playerID == Player::NoId)
			BOOST_THROW_EXCEPTION(
			  logic_error("event.playerID == Player::NoId"));
		std::string const* comment;
		if (e.comment.size() < MaxCommentLength)
			comment = &e.comment;
		else
		{
			longComments.push_back(e.comment.substr(0, MaxCommentLength));
			comment = &longComments.back();
		}
		return DBEvent(e.time, e.type,
			           *comment,
			           e.value, e.value2, e.viewed,
		               e.playerID, e.fleetID, e.planetCoord.X, e.planetCoord.Y,
		               e.planetCoord.Z);
	};

	Transaction trans(*session_);
	(*session_) <<
	            "INSERT INTO Event "
	            "(time, type, comment, value, value2, viewed, playerID, "
	            "  fleetID, planetCoordX, planetCoordY, planetCoordZ) "
	            "VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
	            PKW::bind(events | transformed(event_to_tuple) | cached),
	            now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::removeOldEvents(std::map<Player::ID, size_t> const& maxEventCountPerPlayer)
try
{
	checkConnection(session_);
	Transaction trans(*session_);

	for(auto& maxEventCount : maxEventCountPerPlayer)
	{
		int count = 0;
		(*session_) <<
		            "SELECT count(id) FROM Event WHERE playerID=?",
		            into(count), PKW::bind(maxEventCount.first), now;
		count = std::max(0, int(count) - int(maxEventCount.second));
		(*session_) <<
		            "DELETE FROM Event WHERE playerID=? ORDER BY id LIMIT ?",
		            PKW::bind(maxEventCount.first), PKW::bind(count), now;
	}

	for(size_t type = 0; type < ::Event::Count; ++type)
	{
		int count = 0;
		(*session_) <<
		            "SELECT count(id) FROM Event WHERE type=?",
		            into(count), use(type), now;
		count = std::max(0, count - 50000);
		(*session_) <<
		            "DELETE FROM Event WHERE type=? ORDER BY id LIMIT ?",
		            use(type), use(count), now;
	}

	//! Supprime les Rappor de combats de plus de 24 heures
	(*session_) <<
	            "DELETE FROM FightReport WHERE time < ?",
	            PKW::bind(time(0) - (3600 * 1)),
	            now;

	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

//! Tuple pour stoker les donnée d'un Event quand il sort de la base de donnée
typedef Poco::Tuple <::Event::ID, time_t, size_t, std::string, intptr_t,
        intptr_t, int, Player::ID, Fleet::ID, Coord::Value, Coord::Value,
        Coord::Value >
        DBEvent;

//! Convertie un DBEvent en Event
::Event toEvent(DBEvent const& ev)
{
	::Event res(ev.get<7>(), ev.get<1>(), ::Event::Type(ev.get<2>()));
	res.id = ev.get<0>();
	res.time = ev.get<1>();
	res.type = ::Event::Type(ev.get<2>());
	res.comment = ev.get<3>();
	res.value = ev.get<4>();
	res.value2 = ev.get<5>();
	res.viewed = ev.get<6>() != 0;
	res.playerID = ev.get<7>();
	res.fleetID = ev.get<8>();
	res.planetCoord = Coord(ev.get<9>(), ev.get<10>(), ev.get<11>());
	return res;
}

std::vector<::Event> DataBase::getPlayerEvents(Player::ID pid) const
try
{
	checkConnection(session_);
	std::vector<DBEvent> dbEvents;
	Transaction trans(*session_);
	(*session_) <<
	            "SELECT * FROM Event "
	            "WHERE playerID = ? "
	            " AND type IN (?, ?, ?, ?, ?, ?, ?) "
	            "ORDER BY id DESC LIMIT 100 ",
	            into(dbEvents),
	            use(pid),
	            PKW::bind((int)::Event::FleetCodeError),
	            PKW::bind((int)::Event::FleetCodeExecError),
	            PKW::bind((int)::Event::PlanetCodeError),
	            PKW::bind((int)::Event::PlanetCodeExecError),
	            PKW::bind((int)::Event::FleetLose),
	            PKW::bind((int)::Event::PlanetLose),
	            PKW::bind((int)::Event::PlayerLogGather),
	            now;
	trans.commit();

	std::vector<::Event> out;
	out.reserve(dbEvents.size());
	boost::transform(dbEvents, back_inserter(out), toEvent);
	return out;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::vector<::Event> DataBase::getPlanetEvents(Player::ID pid,
    Coord pcoord) const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::vector<DBEvent> dbEvents;
	(*session_) <<
	            "SELECT * FROM Event "
	            "WHERE"
	            "  playerID = ? AND "
	            "  planetCoordX=? AND planetCoordY=? AND planetCoordZ=? "
	            "ORDER BY id DESC LIMIT 100 ",
	            into(dbEvents),
	            use(pid),
	            use(pcoord.X), use(pcoord.Y), use(pcoord.Z),
	            now;
	trans.commit();
	return dbEvents | transformed(toEvent) | collected<std::vector<::Event>>();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::vector<::Event> DataBase::getFleetEvents(
  Player::ID pid, Fleet::ID fid) const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::vector<DBEvent> dbEvents;
	(*session_) <<
	            "SELECT * FROM Event "
	            "WHERE playerID = ? AND fleetID = ? "
	            "ORDER BY id DESC LIMIT 100 ",
	            into(dbEvents), use(pid), use(fid),
	            now;
	trans.commit();
	return dbEvents | transformed(toEvent) | collected<std::vector<::Event>>();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void  DataBase::resetPlanetEvents(Coord pcoord)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) <<
	            "DELETE FROM Event "
	            "WHERE"
	            "  planetCoordX=? AND planetCoordY=? AND planetCoordZ=?",
	            use(pcoord.X), use(pcoord.Y), use(pcoord.Z), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

size_t DataBase::addFightReport(FightReport const& report)
try
{
	checkConnection(session_);
	using namespace boost::archive;
	Transaction trans(*session_);
	std::string data;
	stringstream ss(ios::binary | ios::in | ios::out);
	boost::archive::text_oarchive oa(ss);
	oa& report;
	data = ss.str();
	(*session_) << "INSERT INTO FightReport (time, data) VALUES(?, ?)",
	            PKW::bind(time(0)), use(data), now;
	size_t id = 0;
	(*session_) << "SELECT LAST_INSERT_ID() ", into(id), now;
	trans.commit();
	return id;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

size_t DataBase::addFightReports(std::vector<FightReport> const& reports)
try
{
	checkConnection(session_);
	using namespace boost::archive;
	Transaction trans(*session_);
	std::string data;
	time_t date = time(0);
	Statement stmt =
	  ((*session_) << "INSERT INTO FightReport (time, data) VALUES(?, ?)",
	   use(date), use(data));

	for(FightReport const& report : reports)
	{
		stringstream ss(ios::binary | ios::in | ios::out);
		boost::archive::text_oarchive oa(ss);
		oa& report;
		data = ss.str();
		date = time(0);
		stmt.execute();
	}
	size_t id = 0;
	(*session_) << "SELECT LAST_INSERT_ID() ", into(id), now;
	trans.commit();
	return id;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

FightReport DataBase::getFightReport(size_t reportID)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	FightReport report;
	Poco::Data::BLOB data;
	(*session_) << "SELECT data FROM FightReport WHERE id = ?",
	            use(reportID), into(data), now;
	trans.commit();
	if(data.size() == 0)
		BOOST_THROW_EXCEPTION(Exception("Invalid reportID"));
	using namespace boost::archive;
	stringstream ss(ios::binary | ios::in | ios::out);
	ss.rdbuf()->sputn(reinterpret_cast<const char*>(data.rawContent()), data.size());
	boost::archive::text_iarchive ia(ss);
	ia& report;
	return report;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

size_t DataBase::addScript(Player::ID pid,
                           CodeData::Target target,
                           std::string const& code)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	addScriptImpl(pid, target, code);
	size_t id = 0;
	(*session_) << "SELECT LAST_INSERT_ID() ", into(id), now;
	trans.commit();
	return id;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

size_t DataBase::addBlocklyCode(Player::ID pid,
                                CodeData::Target target,
                                std::string const& code)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	addBlocklyCodeImpl(pid, target, code);
	size_t id = 0;
	(*session_) << "SELECT LAST_INSERT_ID() ", into(id), now;
	trans.commit();
	return id;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

namespace Poco
{
namespace Data
{

//! @see http://pocoproject.org/docs-1.5.1/00200-DataUserManual.html#27
template <>
class TypeHandler<typename DataBase::CodeError>
{
	//! @cond Doxygen_Suppress
public:
	static void bind(std::size_t pos,
	                 const DataBase::CodeError& obj,
	                 AbstractBinder* pBinder,
	                 AbstractBinder::Direction dir)
	{
		poco_assert_dbg(pBinder != 0);
		TypeHandler<std::string>::bind(pos++, obj.message, pBinder, dir);
		TypeHandler<size_t>::bind(pos++, obj.codeDataId, pBinder, dir);
	}

	static std::size_t size()
	{
		return 2;
	}

	static void prepare(std::size_t pos,
	                    const DataBase::CodeError& obj,
	                    AbstractPreparator::Ptr pPrepare)
	{
		TypeHandler<std::string>::prepare(pos++, obj.message, pPrepare);
		TypeHandler<size_t>::prepare(pos++, obj.codeDataId, pPrepare);
	}

	static void extract(std::size_t pos,
	                    DataBase::CodeError& obj,
	                    const DataBase::CodeError& defVal,
	                    AbstractExtractor::Ptr pExt)
	{
		std::string message;
		size_t codeID = 0;
		TypeHandler<string>::extract(pos++, message, defVal.message, pExt);
		TypeHandler<size_t>::extract(pos++, codeID, defVal.codeDataId, pExt);
		obj.message = message;
		obj.codeDataId = codeID;
	}

private:
	TypeHandler();
	~TypeHandler();
	TypeHandler(const TypeHandler&);
	TypeHandler& operator=(const TypeHandler&);
	//! @endcond
};

}
} // namespace Poco::Data

void DataBase::addCodeErrors(std::vector<CodeError> const& errors)
try
{
	if(errors.empty())
		return;
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) <<
	            "UPDATE Script SET lastError = ? WHERE id = ? ",
	            PKW::bind(errors | transformed(boost::bind(&CodeError::message, _1)) | collected<std::vector<string>>()),
	            PKW::bind(errors | transformed(boost::bind(&CodeError::codeDataId, _1)) | collected<std::vector<size_t>>()),
	            now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

CodeData DataBase::getPlayerCode(Player::ID pid, CodeData::Target target) const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	typedef Poco::Tuple < size_t, Player::ID, time_t, size_t,
	        Data::BLOB, Data::BLOB > ScriptTuple;
	ScriptTuple scrData;
	(*session_) <<
	            "SELECT * FROM Script "
	            "WHERE playerID = ? AND target = ? "
	            "ORDER BY id DESC "
	            "LIMIT 1 ",
	            use(pid), PKW::bind((int)target), into(scrData), now;

	typedef Poco::Tuple<size_t, Player::ID, time_t, size_t, Data::BLOB> BlocklyTuple;
	BlocklyTuple bloData;
	(*session_) <<
	            "SELECT * FROM BlocklyCode "
	            "WHERE playerID = ? AND target = ? "
	            "ORDER BY id DESC "
	            "LIMIT 1 ",
	            use(pid), PKW::bind((int)target), into(bloData), now;
	trans.commit();
	CodeData res;
	res.id = scrData.get<0>();
	res.playerId = pid;
	res.target = target;
	res.code = toString(scrData.get<4>());
	res.blocklyCode = toString(bloData.get<4>());
	res.lastError = toString(scrData.get<5>());
	res.blocklyCodeDate = bloData.get<2>();
	res.codeDate = scrData.get<2>();
	return res;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::eraseAccount(Player::ID pid)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::string const login = nameGen();
	std::string const password = "gfd8fg451g51df8hgdf";

	(*session_) <<
	            "UPDATE Player "
	            "SET login = ?, password = ? "
	            "WHERE id = ? ",
	            useRef(login), useRef(password), use(pid),
	            now;
	addScript(pid, CodeData::Planet, "");
	addScript(pid, CodeData::Fleet, "");
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::incrementTutoDisplayed(std::vector<Player::ID> const& pids,
                                      std::string const& tutoName)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::stringstream ss;
	ss << "UPDATE TutoDisplayed "
	   "SET level = level + 1 "
	   "WHERE playerID IN (";
	for(Player::ID pid : pids)
		ss << pid << ",";
	ss << "0) AND tag = ? ";
	(*session_) << ss.str(), useRef(tutoName), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::incrementTutoDisplayed(Player::ID pid,
                                      std::string const& tutoName,
                                      int32_t value)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) <<
	            "INSERT IGNORE INTO TutoDisplayed "
	            "(playerID, tag, level) "
	            "VALUES(?, ?, ?)", use(pid), useRef(tutoName), PKW::bind(0), now;
	(*session_) << "UPDATE TutoDisplayed "
	            "SET level = level + ? "
	            "WHERE playerID = ? AND tag = ? ",
	            use(value), use(pid), useRef(tutoName), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

PlayerTutoMap DataBase::getTutoDisplayed(Player::ID pid) const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	typedef Poco::Tuple<std::string, size_t> TutoTuple;
	std::vector<TutoTuple> tutos;
	(*session_) <<
	            "SELECT tag, level FROM TutoDisplayed "
	            "WHERE playerID = ? ",
	            use(pid), into(tutos), now;
	trans.commit();
	auto get_pair = [](TutoTuple const & t) {return make_pair(t.get<0>(), t.get<1>()); };
	return tutos | transformed(get_pair) | collected<PlayerTutoMap>();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::map<Player::ID, PlayerTutoMap>
DataBase::getAllTutoDisplayed() const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	typedef Poco::Tuple<Player::ID, std::string, size_t> TutoTuple;
	std::vector<TutoTuple> tutos;
	(*session_) << "SELECT * FROM TutoDisplayed", into(tutos), now;
	trans.commit();

	std::map<Player::ID, PlayerTutoMap> result;
	for(TutoTuple const& tuto : tutos)
		result[tuto.get<0>()].insert(make_pair(tuto.get<1>(), tuto.get<2>()));
	return result;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::updateScore(std::map<Player::ID, uint64_t> const& scoreMap)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	typedef Poco::Tuple<uint64_t, Player::ID> ScoreTuple;

	auto pair_to_poco = [](std::map<Player::ID, uint64_t>::value_type const & p)
	{
		return ScoreTuple(get<1>(p), get<0>(p));
	};

	(*session_) << "UPDATE Player SET score = ? WHERE id = ?",
	            PKW::bind(scoreMap | transformed(pair_to_poco) | cached),
	            now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::updateXP(std::map<Player::ID, uint32_t> const& expMap)
try
{
	if(expMap.empty())
		return;
	checkConnection(session_);
	Transaction trans(*session_);
	for(auto& nvp : expMap)
		(*session_) <<
		            "UPDATE Player SET "
		            "experience = experience + ?, "
		            "skillpoints = skillpoints + ? "
		            "WHERE id = ?",
		            PKW::bind(nvp.second),
		            PKW::bind(nvp.second),
		            PKW::bind(nvp.first),
		            now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::string skillTabToString(Player::SkillTab const& skillTab)
{
	std::stringstream ss;
	bool first = true;
	for(uint16_t val : skillTab)
	{
		if(not first)
			ss << ",";
		ss << val;
		first = false;
	}
	return ss.str();
}

bool DataBase::buySkill(Player::ID pid, int16_t skillID)
try
{
	if(skillID >= Skill::Count || skillID < 0)
		BOOST_THROW_EXCEPTION(std::logic_error("invalid skillID"));

	checkConnection(session_);
	Transaction trans(*session_);
	Player pla = getPlayerImpl(pid);
	size_t const cost =
	  Skill::List[skillID]->skillCost(pla.skilltab.at(skillID)) *
	  XPPerSkillPoints;
	if(pla.skillpoints < static_cast<uint32_t>(cost))
		return false;
	if(Skill::List[skillID]->canUpgrade(pla) == false)
		return false;

	pla.skilltab.at(skillID) += 1;

	string const skilltabstr = skillTabToString(pla.skilltab);
	(*session_) <<
	            "UPDATE Player SET "
	            "skillpoints = skillpoints - ?, "
	            "skilltab = ? "
	            "WHERE id = ?",
	            PKW::bind(cost),
	            useRef(skilltabstr),
	            use(pid),
	            now;
	trans.commit();
	return true;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::setPlayerSkills(Player::ID pid,
                               Player::SkillTab const& skillTab)
{
	checkConnection(session_);
	Transaction trans(*session_);

	string const skilltabstr = skillTabToString(skillTab);
	(*session_) <<
	            "UPDATE Player SET "
	            "skilltab = ? "
	            "WHERE id = ?",
	            PKW::bind(skilltabstr),
	            use(pid),
	            now;
	trans.commit();
}

//***************************  Messages  **********************************

void DataBase::addMessage(Player::ID sender,
                          Player::ID recip,
                          std::string const& obj,
                          std::string const& mes)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) <<
	            "INSERT INTO Message "
	            "(sender, recipient, time, suject, message, viewed) "
	            "VALUES(?, ?, ?, ?, ?, 0)",
	            use(sender), use(recip), PKW::bind(time(0)), useRef(obj), useRef(mes), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::vector<Message> DataBase::getMessages(Player::ID recipient)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	typedef Tuple < Message::ID, Player::ID, Player::ID, time_t, std::string,
	        Data::BLOB, int, std::string > MessageTup;
	std::vector<MessageTup> messages;
	messages.reserve(100);
	(*session_) <<
	            "SELECT Message.*, Player.login FROM Message "
	            "INNER JOIN Player "
	            "ON sender = Player.id "
	            "WHERE recipient = ? ",
	            into(messages), use(recipient), now;

	(*session_) <<
	            "UPDATE Message SET viewed = 1 "
	            "WHERE recipient = ? ",
	            use(recipient), now;

	trans.commit();

	auto tuple_to_message = [](MessageTup const & m)
	{
		return Message(m.get<0>(), m.get<1>(), m.get<2>(), m.get<3>(),
		               m.get<4>(), toString(m.get<5>()), m.get<7>());
	};

	return messages | transformed(tuple_to_message) | collected<std::vector<Message>>();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::eraseMesage(Message::ID mid)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) << "DELETE FROM Message WHERE id = ?", use(mid), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

//***************************  Friendship  ********************************

//! Ordone deux Player::ID
void order(Player::ID& playerA, Player::ID& playerB)
{
	if(playerA > playerB)
		std::swap(playerA, playerB);
}

void DataBase::addFriendshipRequest(Player::ID sender, Player::ID recipient)
try
{
	//! Si sender est recipient sont identique, on ne fait rien
	if(sender == recipient)
		return;
	checkConnection(session_);
	Transaction trans(*session_);
	//! Y a t'il eu une requete dans l'autre sens?
	size_t rowCount = 0;
	(*session_) <<
	            "SELECT COUNT(*) FROM FriendshipRequest "
	            "WHERE sender = ? AND recipient = ? ",
	            into(rowCount), use(recipient), use(sender), now;
	//! - Si oui on le considère comme une validation
	if(rowCount)
	{
		Player::ID playerA = sender;
		Player::ID playerB = recipient;
		order(playerA, playerB);
		(*session_) <<
		            "INSERT IGNORE INTO Friendship "
		            "(friend_a, friend_b) "
		            "VALUES(?, ?)", use(playerA), use(playerB), now;
		(*session_) <<
		            "DELETE FROM FriendshipRequest "
		            "WHERE sender = ? AND recipient = ? ",
		            use(recipient), use(sender), now;
	}
	//! - Sinon on insert la demande (sauf si il en as déja une identique)
	else
	{
		(*session_) <<
		            "INSERT IGNORE INTO FriendshipRequest "
		            "(sender, recipient) "
		            "VALUES(?, ?)",
		            use(sender), use(recipient), now;
	}
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::acceptFriendshipRequest(Player::ID sender,
                                       Player::ID recipient,
                                       bool accept)
try
{
	//Si c'est le meme joueur(improbable) on supprime la demande
	if(sender == recipient)
		accept = false;
	checkConnection(session_);
	Transaction trans(*session_);
	//! Si le joueur accepte
	if(accept)
	{
		//! - On verifie que la requete est bien là
		size_t rowCount = 0;
		(*session_) <<
		            "SELECT COUNT(*) FROM FriendshipRequest "
		            "WHERE sender = ? AND recipient = ? ",
		            into(rowCount), use(sender), use(recipient), now;
		//! - Dans ce cas on ajoute l'amitiée dans la base
		if(rowCount)
		{
			Player::ID playerA = sender;
			Player::ID playerB = recipient;
			order(playerA, playerB);
			(*session_) <<
			            "INSERT IGNORE INTO Friendship "
			            "(friend_a, friend_b) "
			            "VALUES(?, ?)", use(playerA), use(playerB), now;
		}
	}
	//! Dans tout les cas on supprime la requete
	(*session_) <<
	            "DELETE FROM FriendshipRequest "
	            "WHERE sender = ? AND recipient = ? ",
	            use(sender), use(recipient), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::closeFriendship(Player::ID playerA, Player::ID playerB)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	order(playerA, playerB);
	(*session_) <<
	            "DELETE FROM Friendship "
	            "WHERE friend_a = ? AND friend_b = ? ",
	            use(playerA), use(playerB), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::vector<Player> DataBase::getFriends(Player::ID player) const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::vector<PlayerTmp> friends;
	friends.reserve(100);
	(*session_) <<
	            boost::format(GetPlayerRequest) %
	            "JOIN Friendship "
	            "ON (friend_a = Player.id AND friend_b = ?) "
	            "  OR (friend_b = Player.id AND friend_a = ?)",
	            into(friends), use(player), use(player), now;
	trans.commit();
	return friends
	       | filtered([&](PlayerTmp const & fr)->bool {return fr.get<0>() != player; })
	       | transformed(playerFromTuple)
	       | collected<std::vector<Player>>();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

FriendshipRequests DataBase::getFriendshipRequest(Player::ID player) const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	FriendshipRequests result;
	{
		std::vector<PlayerTmp> received;
		received.reserve(100);
		(*session_) <<
		            boost::format(GetPlayerRequest) %
		            "JOIN FriendshipRequest ON"
		            "  FriendshipRequest.sender = Player.id AND"
		            "  FriendshipRequest.recipient = ? ",
		            into(received), use(player), now;

		result.received = received | transformed(playerFromTuple) | collected<std::vector<Player>>();
	}
	{
		std::vector<PlayerTmp> sent;
		sent.reserve(100);
		(*session_) <<
		            boost::format(GetPlayerRequest) %
		            "JOIN FriendshipRequest ON"
		            "  FriendshipRequest.sender = ? AND"
		            "  FriendshipRequest.recipient = Player.id ",
		            into(sent), use(player), now;

		result.sent = sent | transformed(playerFromTuple) | collected<std::vector<Player>>();
	}
	trans.commit();
	return result;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

//***************************  Alliance  **********************************

Alliance::ID DataBase::addAlliance(Player::ID pid,
                                   std::string const& name,
                                   std::string const& description)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) <<
	            "INSERT IGNORE INTO Alliance "
	            "(masterID, name, description) "
	            "VALUES(?, ?, ?)",
	            use(pid), useRef(name), useRef(description), now;
	size_t rowCount;
	(*session_) << "SELECT ROW_COUNT() ", into(rowCount), now;
	if(rowCount == 0)
		return Alliance::NoId;

	Alliance::ID id = 0;
	(*session_) << "SELECT LAST_INSERT_ID() ", into(id), now;
	(*session_) <<
	            "UPDATE Player SET allianceID = ? WHERE id = ?",
	            use(id), use(pid), now;
	trans.commit();
	return id;
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

typedef Tuple <Alliance::ID, Player::ID, std::string, Data::BLOB, std::string> AllianceTup;

Alliance toAllicance(AllianceTup const& a)
{
	return Alliance(a.get<0>(), a.get<1>(), a.get<2>(), toString(a.get<3>()), a.get<4>());
};

Alliance DataBase::getAlliance(Alliance::ID aid) const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	AllianceTup allianceTup;
	(*session_) <<
	            "SELECT Alliance.*, Player.login FROM Alliance "
	            "INNER JOIN Player "
	            "ON masterID = Player.id "
	            "WHERE Alliance.id = ? ",
	            into(allianceTup),
	            use(aid), now;
	trans.commit();
	return toAllicance(allianceTup);
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

std::vector<Alliance> DataBase::getAlliances() const
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	std::vector<AllianceTup> allianceVect;
	(*session_) <<
	            "SELECT Alliance.*, Player.login FROM Alliance "
	            "INNER JOIN Player "
	            "ON masterID = Player.id ",
	            into(allianceVect),
	            now;
	trans.commit();

	return allianceVect | transformed(toAllicance) | collected<std::vector<Alliance>>();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::updateAlliance(Alliance const& al)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) <<
	            "UPDATE Alliance SET "
	            "  name = ?, description = ? "
	            "WHERE id = ?",
	            useRef(al.name), useRef(al.description), PKW::bind(al.id), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::transfertAlliance(Alliance::ID aid, Player::ID pid)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	Player player = getPlayerImpl(pid);
	if(player.allianceID != aid)
		return;
	(*session_) <<
	            "UPDATE Alliance SET masterID = ? WHERE id = ?",
	            use(pid), use(aid), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::eraseAlliance(Alliance::ID aid)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) << "DELETE FROM Alliance WHERE id = ? ", use(aid), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::joinAlliance(Player::ID pid, Alliance::ID aid)
try
{
	checkConnection(session_);
	Transaction trans(*session_);
	(*session_) <<
	            "UPDATE Player SET allianceID = ? WHERE id = ?",
	            use(aid), use(pid), now;
	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::quitAlliance(Player::ID pid)
try
{
	checkConnection(session_);
	Player player = getPlayer(pid);
	Alliance alliance = getAlliance(player.allianceID);
	Transaction trans(*session_);
	(*session_) <<
	            "UPDATE Player SET allianceID = NULL WHERE id = ?",
	            use(pid), now;
	trans.commit();
	if(alliance.masterID == pid)
		eraseAlliance(alliance.id);
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

void DataBase::clear(bool keepPlayer)
try
{
	checkConnection(session_);
	Transaction trans(*session_);

	if(keepPlayer == false)
		(*session_) << "SET FOREIGN_KEY_CHECKS = 0", now;

	if(keepPlayer == false)
		(*session_) << "TRUNCATE Player", now;
	(*session_) << "TRUNCATE Event", now;
	(*session_) << "TRUNCATE Script", now;
	(*session_) << "TRUNCATE BlocklyCode", now;
	(*session_) << "TRUNCATE FightReport", now;
	(*session_) << "TRUNCATE TutoDisplayed", now;
	if(keepPlayer == false)
		(*session_) << "TRUNCATE Message", now;
	if(keepPlayer == false)
		(*session_) << "TRUNCATE FriendshipRequest", now;
	if(keepPlayer == false)
		(*session_) << "TRUNCATE Friendship", now;
	if(keepPlayer == false)
		(*session_) << "TRUNCATE Alliance", now;

	(*session_) << "DELETE FROM Player WHERE isAI=True", now;
	(*session_) <<
	            "UPDATE Player SET score = 0, "
	            "  planetCoordX = -1, planetCoordY = -1, planetCoordZ = -1, "
	            "  experience = 0, skillpoints = 0, skilltab = \"\"", now;

	if(keepPlayer == false)
		(*session_) << "SET FOREIGN_KEY_CHECKS = 1", now;

	trans.commit();
}
catch(Poco::Data::DataException const& ex) {DB_CATCH;};

max_stars_repo_name: lhamot/DroneWars

max_issues_repo_name: lhamot/DroneWars

max_forks_repo_name: lhamot/DroneWars


text:
// Boost.TypeErasure library
//
// Copyright 2012 Steven Watanabe
//
// 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)
//
// $Id$

#ifndef BOOST_TYPE_ERASURE_FREE_HPP_INCLUDED
#define BOOST_TYPE_ERASURE_FREE_HPP_INCLUDED

#include <boost/detail/workaround.hpp>
#include <boost/preprocessor/repetition/enum.hpp>
#include <boost/preprocessor/repetition/enum_trailing.hpp>
#include <boost/preprocessor/repetition/enum_params.hpp>
#include <boost/preprocessor/repetition/enum_shifted_params.hpp>
#include <boost/preprocessor/repetition/enum_params_with_a_default.hpp>
#include <boost/preprocessor/repetition/enum_binary_params.hpp>
#include <boost/preprocessor/cat.hpp>
#include <boost/preprocessor/control/if.hpp>
#include <boost/preprocessor/punctuation/is_begin_parens.hpp>
#include <boost/vmd/is_empty.hpp>
#include <boost/type_traits/remove_reference.hpp>
#include <boost/type_traits/remove_cv.hpp>
#include <boost/mpl/eval_if.hpp>
#include <boost/mpl/identity.hpp>
#include <boost/mpl/int.hpp>
#include <boost/mpl/next.hpp>
#include <boost/type_erasure/detail/macro.hpp>
#include <boost/type_erasure/detail/const.hpp>
#include <boost/type_erasure/config.hpp>
#include <boost/type_erasure/derived.hpp>
#include <boost/type_erasure/rebind_any.hpp>
#include <boost/type_erasure/param.hpp>
#include <boost/type_erasure/is_placeholder.hpp>
#include <boost/type_erasure/call.hpp>
#include <boost/type_erasure/concept_interface.hpp>

#if defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || \
    defined(BOOST_NO_CXX11_RVALUE_REFERENCES) || \
    defined(BOOST_TYPE_ERASURE_DOXYGEN) || \
    BOOST_WORKAROUND(BOOST_MSVC, == 1800)

namespace boost {
namespace type_erasure {
namespace detail {

template<BOOST_PP_ENUM_PARAMS_WITH_A_DEFAULT(BOOST_TYPE_ERASURE_MAX_ARITY, class T, void)>
struct first_placeholder {
    typedef typename ::boost::mpl::eval_if<is_placeholder<T0>,
        ::boost::mpl::identity<T0>,
        first_placeholder<BOOST_PP_ENUM_SHIFTED_PARAMS(BOOST_TYPE_ERASURE_MAX_ARITY, T)>
    >::type type;
};

template<>
struct first_placeholder<> {};

template<BOOST_PP_ENUM_PARAMS_WITH_A_DEFAULT(BOOST_TYPE_ERASURE_MAX_ARITY, class T, void)>
struct first_placeholder_index :
    ::boost::mpl::eval_if<is_placeholder<T0>,
        ::boost::mpl::int_<0>,
        ::boost::mpl::next<first_placeholder_index<BOOST_PP_ENUM_SHIFTED_PARAMS(BOOST_TYPE_ERASURE_MAX_ARITY, T)> >
    >::type
{};

}
}
}

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_QUALIFIED_ID(seq, N) \
    BOOST_TYPE_ERASURE_QUALIFIED_NAME(seq)<R(BOOST_PP_ENUM_PARAMS(N, T))>

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_UNQUALIFIED_PARAM_TYPE(z, n, data) \
    typename ::boost::remove_cv<typename ::boost::remove_reference<BOOST_PP_CAT(T, n)>::type>::type

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_PARAM_TYPE(z, n, data)                      \
    typename ::boost::mpl::eval_if_c<(_boost_type_erasure_free_p_idx::value == n), \
        ::boost::type_erasure::detail::maybe_const_this_param<BOOST_PP_CAT(T, n), Base>,    \
        ::boost::type_erasure::as_param<Base, BOOST_PP_CAT(T, n)>           \
    >::type BOOST_PP_CAT(t, n)

#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_FORWARD_I(z, n, data) ::std::forward<BOOST_PP_CAT(T, n)>(BOOST_PP_CAT(t, n))
/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_FORWARD(n) BOOST_PP_ENUM(n, BOOST_TYPE_ERASURE_FREE_FORWARD_I, ~)
/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_FORWARD_PARAM_I(z, n, data) \
    ::std::forward<typename ::boost::mpl::eval_if_c<(_boost_type_erasure_free_p_idx::value == n), \
        ::boost::type_erasure::detail::maybe_const_this_param<BOOST_PP_CAT(T, n), Base>,    \
        ::boost::type_erasure::as_param<Base, BOOST_PP_CAT(T, n)>           \
    >::type>(BOOST_PP_CAT(t, n))

#else

#define BOOST_TYPE_ERASURE_FREE_FORWARD(n) BOOST_PP_ENUM_PARAMS(n, t)
#define BOOST_TYPE_ERASURE_FREE_FORWARD_PARAM_I(z, n, data) BOOST_PP_CAT(t, n)

#endif

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_II(qual_name, concept_name, function_name, N)  \
    BOOST_TYPE_ERASURE_OPEN_NAMESPACE(qual_name)                        \
                                                                        \
    template<class Sig>                                                 \
    struct concept_name;                                                \
                                                                        \
    template<class R BOOST_PP_ENUM_TRAILING_PARAMS(N, class T)>         \
    struct concept_name<R(BOOST_PP_ENUM_PARAMS(N, T))> {                \
        static R apply(BOOST_PP_ENUM_BINARY_PARAMS(N, T, t))            \
        { return function_name(BOOST_TYPE_ERASURE_FREE_FORWARD(N)); }   \
    };                                                                  \
                                                                        \
    template<BOOST_PP_ENUM_PARAMS(N, class T)>                          \
    struct concept_name<void(BOOST_PP_ENUM_PARAMS(N, T))> {             \
        static void apply(BOOST_PP_ENUM_BINARY_PARAMS(N, T, t))         \
        { function_name(BOOST_TYPE_ERASURE_FREE_FORWARD(N)); }          \
    };                                                                  \
                                                                        \
    BOOST_TYPE_ERASURE_CLOSE_NAMESPACE(qual_name)                       \
                                                                        \
    namespace boost {                                                   \
    namespace type_erasure {                                            \
                                                                        \
    template<class R BOOST_PP_ENUM_TRAILING_PARAMS(N, class T), class Base> \
    struct concept_interface<                                           \
        BOOST_TYPE_ERASURE_FREE_QUALIFIED_ID(qual_name, N),             \
        Base,                                                           \
        typename ::boost::type_erasure::detail::first_placeholder<      \
            BOOST_PP_ENUM(N, BOOST_TYPE_ERASURE_FREE_UNQUALIFIED_PARAM_TYPE, ~)>::type  \
    > : Base {                                                          \
        typedef typename ::boost::type_erasure::detail::first_placeholder_index<    \
            BOOST_PP_ENUM(N, BOOST_TYPE_ERASURE_FREE_UNQUALIFIED_PARAM_TYPE, ~)>::type  \
            _boost_type_erasure_free_p_idx;                             \
        friend typename ::boost::type_erasure::rebind_any<Base, R>::type function_name(  \
            BOOST_PP_ENUM(N, BOOST_TYPE_ERASURE_FREE_PARAM_TYPE, ~))    \
        {                                                               \
            return ::boost::type_erasure::call(                         \
                BOOST_TYPE_ERASURE_FREE_QUALIFIED_ID(qual_name, N)()    \
                BOOST_PP_ENUM_TRAILING(N, BOOST_TYPE_ERASURE_FREE_FORWARD_PARAM_I, ~)); \
        }                                                               \
    };                                                                  \
                                                                        \
    }                                                                   \
    }

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_I(namespace_name, concept_name, function_name, N)\
    BOOST_TYPE_ERASURE_FREE_II(namespace_name, concept_name, function_name, N)

#ifdef BOOST_TYPE_ERASURE_DOXYGEN

/**
 * \brief Defines a primitive concept for a free function.
 *
 * \param concept_name is the name of the concept to declare.
 *        If it is omitted it defaults to has_ ## function_name
 * \param function_name is the name of the function.
 *
 * The declaration of the concept is
 * \code
 * template<class Sig>
 * struct concept_name;
 * \endcode
 * where Sig is a function type giving the
 * signature of the function.
 *
 * This macro can only be used at namespace scope.
 *
 * Example:
 *
 * \code
 * BOOST_TYPE_ERASURE_FREE(to_string)
 * typedef has_to_string<std::string(_self const&)> to_string_concept;
 * \endcode
 *
 * In C++03, the macro can only be used in the global namespace and
 * is defined as:
 *
 * \code
 * #define BOOST_TYPE_ERASURE_FREE(qualified_name, function_name, N)
 * \endcode
 *
 * Example:
 *
 * \code
 * BOOST_TYPE_ERASURE_FREE((boost)(has_to_string), to_string, 1)
 * \endcode
 *
 * For backwards compatibility, this form is always accepted.
 */
#define BOOST_TYPE_ERASURE_FREE(concept_name, function_name)

#else

#define BOOST_TYPE_ERASURE_FREE(qualified_name, function_name, N)                           \
    BOOST_TYPE_ERASURE_FREE_I(                                                              \
        qualified_name,                                                                     \
        BOOST_PP_SEQ_ELEM(BOOST_PP_DEC(BOOST_PP_SEQ_SIZE(qualified_name)), qualified_name), \
        function_name,                                                                      \
        N)

#endif

#else

namespace boost {
namespace type_erasure {

template<int... N>
struct index_list {};

namespace detail {

template<class... T>
struct first_placeholder;

template<class T0, class... T>
struct first_placeholder<T0, T...> {
    typedef typename ::boost::mpl::eval_if<is_placeholder<T0>,
        ::boost::mpl::identity<T0>,
        first_placeholder<T...>
    >::type type;
};

template<>
struct first_placeholder<> {};

template<class... T>
struct first_placeholder_index;

template<class T0, class... T>
struct first_placeholder_index<T0, T...> :
    ::boost::mpl::eval_if<is_placeholder<T0>,
        ::boost::mpl::int_<0>,
        ::boost::mpl::next<first_placeholder_index<T...> >
    >::type
{};

template<class Sig>
struct transform_free_signature;

template<class T, int N>
struct push_back_index;

template<int... N, int X>
struct push_back_index<index_list<N...>, X>
{
    typedef index_list<N..., X> type;
};

template<int N>
struct make_index_list {
    typedef typename push_back_index<
        typename make_index_list<N-1>::type,
        N-1
    >::type type;
};

template<>
struct make_index_list<0> {
    typedef index_list<> type;
};

#if !defined(BOOST_NO_CXX11_TEMPLATE_ALIASES) && \
    !defined(BOOST_NO_CXX11_DECLTYPE)

template<int N>
using make_index_list_t = typename ::boost::type_erasure::detail::make_index_list<N>::type;

#if BOOST_WORKAROUND(BOOST_MSVC, == 1900)

template<class... T>
struct first_placeholder_index_ :
    ::boost::type_erasure::detail::first_placeholder_index<
        ::boost::remove_cv_t< ::boost::remove_reference_t<T> >...
    >
{};
template<class... T>
using first_placeholder_index_t =
    typename ::boost::type_erasure::detail::first_placeholder_index_<T...>::type;

#else

template<class... T>
using first_placeholder_index_t =
    typename ::boost::type_erasure::detail::first_placeholder_index<
        ::boost::remove_cv_t< ::boost::remove_reference_t<T> >...
    >::type;

#endif

template<class Base, class Tn, int I, class... T>
using free_param_t =
    typename ::boost::mpl::eval_if_c<(::boost::type_erasure::detail::first_placeholder_index_t<T...>::value == I),
            ::boost::type_erasure::detail::maybe_const_this_param<Tn, Base>, \
            ::boost::type_erasure::as_param<Base, Tn>
    >::type;

template<class Sig, class ID>
struct free_interface_chooser
{
    template<class Base, template<class> class C, template<class...> class F>
    using apply = Base;
};

template<class R, class... A>
struct free_interface_chooser<
    R(A...),
    typename ::boost::type_erasure::detail::first_placeholder<
        ::boost::remove_cv_t< ::boost::remove_reference_t >...>::type>
{
    template<class Base, template<class> class C, template<class...> class F>
    using apply = F<R(A...), Base,
        ::boost::type_erasure::detail::make_index_list_t<sizeof...(A)> >;
};

template<class Sig, template<class> class C, template<class...> class F>
struct free_choose_interface {
    template<class Concept, class Base, class ID>
    using apply = typename free_interface_chooser<Sig, ID>::template apply<Base, C, F>;
};

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_I(concept_name, function_name)              \
template<class Sig>                                                         \
struct concept_name;                                                        \
                                                                            \
namespace boost_type_erasure_impl {                                         \
                                                                            \
template<class Sig, class Base, class Idx>                                  \
struct concept_name ## _free_interface;                                     \
template<class R, class... T, class Base, int... I>                         \
struct concept_name ## _free_interface<R(T...), Base, ::boost::type_erasure::index_list > : Base {\
    friend ::boost::type_erasure::rebind_any_t<Base, R>                     \
    function_name(                                                          \
        ::boost::type_erasure::detail::free_param_t<Base, T, I, T...>... t) \
    {                                                                       \
        return ::boost::type_erasure::call(                                 \
            concept_name<R(T...)>(),                                        \
            std::forward< ::boost::type_erasure::detail::free_param_t<Base, T, I, T...> >(t)...);\
    }                                                                       \
};                                                                          \
                                                                            \
template<class Sig>                                                         \
struct concept_name ## free;                                                \
                                                                            \
template<class R, class... T>                                               \
struct concept_name ## free<R(T...)> {                                      \
    static R apply(T... t)                                                  \
    { return function_name(std::forward<T>(t)...); }                        \
};                                                                          \
                                                                            \
template<class... T>                                                        \
struct concept_name ## free<void(T...)> {                                   \
    static void apply(T... t)                                               \
    { function_name(std::forward<T>(t)...); }                               \
};                                                                          \
                                                                            \
}                                                                           \
                                                                            \
template<class Sig>                                                         \
struct concept_name :                                                       \
    boost_type_erasure_impl::concept_name##free<Sig>                        \
{};                                                                         \
                                                                            \
template<class Sig>                                                         \
::boost::type_erasure::detail::free_choose_interface<Sig, concept_name,     \
    boost_type_erasure_impl::concept_name ## _free_interface>               \
boost_type_erasure_find_interface(concept_name<Sig>);

#define BOOST_TYPE_ERASURE_FREE_SIMPLE(name, ...) \
    BOOST_TYPE_ERASURE_FREE_I(has_ ## name, name)

#define BOOST_TYPE_ERASURE_FREE_NS_I(concept_name, name)  \
    BOOST_TYPE_ERASURE_FREE_I(concept_name, name)

#define BOOST_TYPE_ERASURE_FREE_NS(concept_name, name)      \
    BOOST_TYPE_ERASURE_OPEN_NAMESPACE(concept_name)         \
    BOOST_TYPE_ERASURE_FREE_NS_I(BOOST_PP_SEQ_ELEM(BOOST_PP_DEC(BOOST_PP_SEQ_SIZE(concept_name)), concept_name), name) \
    BOOST_TYPE_ERASURE_CLOSE_NAMESPACE(concept_name)

#define BOOST_TYPE_ERASURE_FREE_NAMED(concept_name, name, ...)  \
    BOOST_PP_IF(BOOST_PP_IS_BEGIN_PARENS(concept_name),         \
        BOOST_TYPE_ERASURE_FREE_NS,                             \
        BOOST_TYPE_ERASURE_FREE_I)                              \
    (concept_name, name)

#define BOOST_TYPE_ERASURE_FREE_CAT(x, y) x y

#define BOOST_TYPE_ERASURE_FREE(name, ...)              \
    BOOST_TYPE_ERASURE_FREE_CAT(                        \
        BOOST_PP_IF(BOOST_VMD_IS_EMPTY(__VA_ARGS__),    \
            BOOST_TYPE_ERASURE_FREE_SIMPLE,             \
            BOOST_TYPE_ERASURE_FREE_NAMED),             \
        (name, __VA_ARGS__))

#else

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_II(qual_name, concept_name, function_name)  \
    BOOST_TYPE_ERASURE_OPEN_NAMESPACE(qual_name)                        \
                                                                        \
    template<class Sig>                                                 \
    struct concept_name;                                                \
                                                                        \
    template<class R, class... T>                                       \
    struct concept_name<R(T...)> {                                      \
        static R apply(T... t)                                          \
        { return function_name(std::forward<T>(t)...); }                \
    };                                                                  \
                                                                        \
    template<class... T>                                                \
    struct concept_name<void(T...)> {                                   \
        static void apply(T... t)                                       \
        { function_name(std::forward<T>(t)...); }                       \
    };                                                                  \
                                                                        \
    BOOST_TYPE_ERASURE_CLOSE_NAMESPACE(qual_name)                       \
                                                                        \
    namespace boost {                                                   \
    namespace type_erasure {                                            \
                                                                        \
    template<class Sig, class Base, class Idx>                          \
    struct inject ## concept_name;                                      \
    template<class R, class... T, class Base, int... I>                 \
    struct inject ## concept_name<R(T...), Base, index_list > : Base {\
        typedef typename ::boost::type_erasure::detail::first_placeholder_index<    \
            typename ::boost::remove_cv<                                \
                typename ::boost::remove_reference<T>::type             \
            >::type...                                                  \
        >::type _boost_type_erasure_free_p_idx;                         \
        friend typename ::boost::type_erasure::rebind_any<Base, R>::type\
        function_name(                                                  \
            typename ::boost::mpl::eval_if_c<(_boost_type_erasure_free_p_idx::value == I), \
                ::boost::type_erasure::detail::maybe_const_this_param<T, Base>, \
                ::boost::type_erasure::as_param<Base, T>                \
            >::type... t)                                               \
       {                                                                \
            return ::boost::type_erasure::call(                         \
                BOOST_TYPE_ERASURE_QUALIFIED_NAME(qual_name)<R(T...)>(),\
                std::forward<typename ::boost::mpl::eval_if_c<(_boost_type_erasure_free_p_idx::value == I), \
                    ::boost::type_erasure::detail::maybe_const_this_param<T, Base>, \
                    ::boost::type_erasure::as_param<Base, T>            \
                >::type>(t)...);                                        \
        }                                                               \
    };                                                                  \
                                                                        \
    template<class R, class... T, class Base>                           \
    struct concept_interface<                                           \
        BOOST_TYPE_ERASURE_QUALIFIED_NAME(qual_name)<R(T...)>,          \
        Base,                                                           \
        typename ::boost::type_erasure::detail::first_placeholder<      \
            typename ::boost::remove_cv<typename ::boost::remove_reference<T>::type>::type...>::type  \
    > :  inject ## concept_name<R(T...), Base, typename ::boost::type_erasure::detail::make_index_list<sizeof...(T)>::type>\
    {};                                                                 \
                                                                        \
    }                                                                   \
    }

/** INTERNAL ONLY */
#define BOOST_TYPE_ERASURE_FREE_I(namespace_name, concept_name, function_name)              \
    BOOST_TYPE_ERASURE_FREE_II(namespace_name, concept_name, function_name)

#define BOOST_TYPE_ERASURE_FREE(qualified_name, function_name, ...)                         \
    BOOST_TYPE_ERASURE_FREE_I(                                                              \
        qualified_name,                                                                     \
        BOOST_PP_SEQ_ELEM(BOOST_PP_DEC(BOOST_PP_SEQ_SIZE(qualified_name)), qualified_name), \
        function_name)

#endif

}
}
}

#endif

#endif


text:
/* -*- c++ -*- */
/*
 * Copyright 2013 Free Software Foundation, Inc.
 *
 * This file is part of GNU Radio
 *
 * GNU Radio is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 3, or (at your option)
 * any later version.
 *
 * GNU Radio is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with GNU Radio; see the file COPYING.  If not, write to
 * the Free Software Foundation, Inc., 51 Franklin Street,
 * Boston, MA 02110-1301, USA.
 */

#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include <gnuradio/io_signature.h>
#include <gnuradio/math.h>
#include "correlate_and_sync_cc_impl.h"
#include <volk/volk.h>
#include <boost/format.hpp>
#include <boost/math/special_functions/round.hpp>
#include <gnuradio/filter/pfb_arb_resampler.h>
#include <gnuradio/filter/firdes.h>

namespace gr {
  namespace digital {

    correlate_and_sync_cc::sptr
    correlate_and_sync_cc::make(const std::vector<gr_complex> &symbols,
                                const std::vector<float> &filter,
                                unsigned int sps, unsigned int nfilts)
    {
      return gnuradio::get_initial_sptr
        (new correlate_and_sync_cc_impl(symbols, filter, sps, nfilts));
    }

    correlate_and_sync_cc_impl::correlate_and_sync_cc_impl(const std::vector<gr_complex> &symbols,
                                                           const std::vector<float> &filter,
                                                           unsigned int sps, unsigned int nfilts)
      : sync_block("correlate_and_sync_cc",
                   io_signature::make(1, 1, sizeof(gr_complex)),
                   io_signature::make(2, 2, sizeof(gr_complex)))
    {
      d_last_index = 0;
      d_sps = sps;

      // We want to add padding to the beginning of the symbols so we
      // can do the convolution of the symbols with the pulse shape.
      std::vector<gr_complex> padding((1+filter.size()/nfilts)/2, 0);
      std::vector<gr_complex> padded_symbols = symbols;
      padded_symbols.insert(padded_symbols.begin(), padding.begin(), padding.end());

      d_symbols.resize(d_sps*symbols.size(), 0);
      filter::kernel::pfb_arb_resampler_ccf resamp(d_sps, filter, nfilts);
      int nread;
      resamp.filter(&d_symbols[0], &padded_symbols[0], symbols.size(), nread);
      std::reverse(d_symbols.begin(), d_symbols.end());

      float corr = 0;
      for(size_t i=0; i < d_symbols.size(); i++)
        corr += abs(d_symbols[i]*conj(d_symbols[i]));
      d_thresh = 0.9*corr*corr;

      d_center_first_symbol = (padding.size() + 0.5) * d_sps;

      d_filter = new kernel::fft_filter_ccc(1, d_symbols);

      set_history(d_filter->ntaps());

      const int alignment_multiple =
        volk_get_alignment() / sizeof(gr_complex);
      set_alignment(std::max(1,alignment_multiple));
    }

    correlate_and_sync_cc_impl::~correlate_and_sync_cc_impl()
    {
      delete d_filter;
    }

    std::vector<gr_complex>
    correlate_and_sync_cc_impl::symbols() const
    {
      return d_symbols;
    }

    void
    correlate_and_sync_cc_impl::set_symbols(const std::vector<gr_complex> &symbols)
    {
      gr::thread::scoped_lock lock(d_setlock);
      d_symbols = symbols;
      d_filter->set_taps(symbols);
      set_history(d_filter->ntaps());
    }

    int
    correlate_and_sync_cc_impl::work(int noutput_items,
                                     gr_vector_const_void_star &input_items,
                                     gr_vector_void_star &output_items)
    {
      gr::thread::scoped_lock lock(d_setlock);

      const gr_complex *in = (gr_complex *)input_items[0];
      gr_complex *out = (gr_complex*)output_items[0];
      gr_complex *corr = (gr_complex*)output_items[1];

      memcpy(out, in, sizeof(gr_complex)*noutput_items);

      // Calculate the correlation with the known symbol
      d_filter->filter(noutput_items, in, corr);

      // Find the magnitude squared of the correlation
      std::vector<float> corr_mag(noutput_items+1);
      volk_32fc_magnitude_squared_32f(&corr_mag[0], corr, noutput_items);

      // Avoid buffer overflow from nested while, putting a stopper at the end
      corr_mag[noutput_items]=0;
      int i = d_sps;
      while(i < (noutput_items-1)) {
        if((corr_mag[i] - corr_mag[i-d_sps]) > d_thresh) {
          while(corr_mag[i] < corr_mag[i+1])
            i++;

          double nom = 0, den = 0;
          for(int s = 0; s < 3; s++) {
            nom += (s+1)*corr_mag[i+s-1];
            den += corr_mag[i+s-1];
          }
          double center = nom / den;
          center = (center - 2.0);

          // Adjust the results of the fft filter by moving back the
          // length of the filter offset by the number of sps.
          int index = i - d_symbols.size() + d_sps + 1;

          // Calculate the phase offset of the incoming signal; always
          // adjust it based on the proper rotation of the expected
          // known word; rotate by pi is the real part is < 0 since
          // the atan doesn't understand the ambiguity.
          float phase = fast_atan2f(corr[index].imag(), corr[index].real());
          if(corr[index].real() < 0.0)
            phase += M_PI;

          add_item_tag(0, nitems_written(0) + index, pmt::intern("phase_est"),
                       pmt::from_double(phase), pmt::intern(alias()));
          add_item_tag(0, nitems_written(0) + index, pmt::intern("time_est"),
                       pmt::from_double(center), pmt::intern(alias()));
          add_item_tag(0, nitems_written(0) + index, pmt::intern("corr_est"),
                       pmt::from_double(corr_mag[index]), pmt::intern(alias()));

          i += d_sps;
        }
        else
          i++;
      }

      return noutput_items;
    }

  } /* namespace digital */
} /* namespace gr */

ext: cc


text:
#pragma once

#include <memory>
#include <string>

#include <Eigen/Dense>

#include <boost/asio/io_service.hpp>

#include "serial_port_options.hpp"

namespace wit901c_rs485 {
    class SerialPort {
        public :
            SerialPort(const SerialPortOptions &);
            SerialPort(boost::asio::io_service &, const SerialPortOptions &);
            ~SerialPort();

            bool open();
            bool open(const std::string &port_name, const unsigned int &baud_rate);

            void write(const std::string &msg);
            std::string read(const unsigned int &packet_length);

        private :
            class Implementation;

            std::unique_ptr<Implementation> pimpl;
    };
}


text:
#define CATCH_CONFIG_MAIN
#include "catch.hpp"

#include <Eigen/Dense>
#include <Eigen/Sparse>
#include <Eigen/Eigenvalues>

#include <unsupported/Eigen/KroneckerProduct>

#include <Spectra/MatOp/SparseSymMatProd.h>
#include <Spectra/SymEigsSolver.h>

#include <iostream>
#include <cassert>
#include <random>
#include <algorithm>

#include "edlib/Basis/Basis1DZ2.hpp"
#include "edlib/Basis/ToOriginalBasis.hpp"
#include "edlib/Hamiltonians/TIXXZ.hpp"
#include "edlib/Op/NodeMV.hpp"

#include "edlib/EDP/LocalHamiltonian.hpp"
#include "edlib/EDP/ConstructSparseMat.hpp"

using namespace edlib;

Eigen::SparseMatrix<double> getSX()
{
	Eigen::SparseMatrix<double> res(2,2);
	res.insert(0,1) = 1.0;
	res.insert(1,0) = 1.0;
	res.makeCompressed();
	return res;
}

Eigen::SparseMatrix<std::complex<double> > getSY()
{
	Eigen::SparseMatrix<std::complex<double> > res(2,2);
	constexpr std::complex<double> I(0., 1.);
	res.insert(0,1) = -I;
	res.insert(1,0) = I;
	res.makeCompressed();
	return res;
}

Eigen::SparseMatrix<double> getSZ()
{
	Eigen::SparseMatrix<double> res(2,2);
	res.insert(0,0) = 1.0;
	res.insert(1,1) = -1.0;
	res.makeCompressed();
	return res;
}

template<typename T>
Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>
twoQubitOp(int N, int pos1, int pos2,
		const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& v1,
		const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& v2)
{
	using namespace Eigen;
	const uint32_t dim = (1u << N);

	assert(pos1 < pos2);

	Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic> res(1,1);
	res(0,0) = 1.0;

	for(int i = 0; i < pos1; i++)
	{
		res = Eigen::kroneckerProduct(MatrixXd::Identity(2,2), res).eval();
	}

	res = Eigen::kroneckerProduct(v1, res).eval();
	for(int i = pos1+1; i < pos2; i++)
	{
		res = Eigen::kroneckerProduct(MatrixXd::Identity(2,2), res).eval();
	}
	res = Eigen::kroneckerProduct(v2, res).eval();
	for(int i = pos2+1; i < N; i++)
	{
		res = Eigen::kroneckerProduct(MatrixXd::Identity(2,2), res).eval();
	}
	return res;
}

template<typename T>
Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>
singleQubitOp(int N, int pos,
		const Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic>& v)
{
	using namespace Eigen;
	const uint32_t dim = (1u << N);

	using MatrixT = Eigen::Matrix<T, Eigen::Dynamic, Eigen::Dynamic> ;
	MatrixT res(1,1);
	res(0,0) = 1.0;

	for(int i = 0; i < pos; i++)
	{
		res = Eigen::kroneckerProduct(MatrixT::Identity(2,2), res).eval();
	}

	res = Eigen::kroneckerProduct(v, res).eval();
	for(int i = pos+1; i < N; i++)
	{
		res = Eigen::kroneckerProduct(MatrixT::Identity(2,2), res).eval();
	}
	return res;
}

Eigen::SparseMatrix<double> getSXXYY()
{
	Eigen::SparseMatrix<double> res(4,4);
	res.insert(1,2) = 2.0;
	res.insert(2,1) = 2.0;
	res.makeCompressed();
	return res;
}

Eigen::SparseMatrix<double> getSXX()
{
	Eigen::SparseMatrix<double> res(4,4);
	res.insert(0,3) = 1.0;
	res.insert(1,2) = 1.0;
	res.insert(2,1) = 1.0;
	res.insert(3,0) = 1.0;
	res.makeCompressed();
	return res;
}

Eigen::SparseMatrix<double> getSYY()
{
	Eigen::SparseMatrix<double> res(4,4);
	res.insert(0,3) = -1.0;
	res.insert(1,2) = 1.0;
	res.insert(2,1) = 1.0;
	res.insert(3,0) = -1.0;
	res.makeCompressed();
	return res;
}

Eigen::SparseMatrix<double> getSZZ()
{
	Eigen::SparseMatrix<double> res(4,4);
	res.insert(0,0) = 1.0;
	res.insert(1,1) = -1.0;
	res.insert(2,2) = -1.0;
	res.insert(3,3) = 1.0;
	res.makeCompressed();
	return res;
}

template<int N>
class CompareXXZ
{
private:
	double delta_;
	Basis1DZ2<uint32_t> basis_;

	Eigen::MatrixXd hamFull_;
	double gsEnergy_;
	Eigen::VectorXd gsVec_;
public:

	constexpr static int k = (N/2)*((N/2)%2);
	constexpr static int parity = 1-2*((N/2)%2);

	CompareXXZ(double delta)
		: delta_{delta}, basis_{N, k, parity, true}
	{
		using namespace Eigen;
		static_assert(N % 2 == 0, "N must be even");

		edp::LocalHamiltonian<double> lh(N,2);
		for(int i = 0; i < N; i++)
		{
			lh.addTwoSiteTerm({i, (i+1) % N}, getSXXYY() + delta_*getSZZ());
		}
		hamFull_ = MatrixXd(edp::constructSparseMat<double>(1<<N, lh));
		SelfAdjointEigenSolver<MatrixXd> es;
		es.compute(hamFull_);

		gsEnergy_ = es.eigenvalues()[0];
		gsVec_ = es.eigenvectors().col(0);

	}

	void Test()
	{
		using namespace Eigen;
		TIXXZ<uint32_t> ham(basis_, 1.0, delta_);
		const int dim = basis_.getDim();

		NodeMV mv(dim, 0, dim, ham);

		Spectra::SymEigsSolver<double, Spectra::SMALLEST_ALGE, NodeMV> eigs(&mv, 2, 6);
		eigs.init();
		eigs.compute(10000, 1e-12, Spectra::SMALLEST_ALGE);
		if(eigs.info() != Spectra::SUCCESSFUL)
			REQUIRE(false);
		double gsEnergy1 = eigs.eigenvalues()[0];

		REQUIRE(std::abs(gsEnergy_ - gsEnergy1) < 1e-4);
		VectorXd subspaceGs = eigs.eigenvectors().col(0);
		VectorXd gsVec1;
		{
			auto v = toOriginalVector(basis_, subspaceGs.data());
			gsVec1 = Map<VectorXd>(v.data(), 1<<N);
		}

		double gsEnergy2 = double(gsVec1.transpose()*hamFull_*gsVec1)/double(gsVec1.transpose()*gsVec1);

		REQUIRE(std::abs(gsEnergy1 - gsEnergy2) < 1e-6);
		REQUIRE(std::abs(std::abs(gsVec_.transpose()*gsVec1) - 1.) < 1e-6);
	}
};

TEST_CASE("Compare GS of XXZ using LocalHamiltonian and TIBasis", "[XXZGS]")
{
	SECTION("TIBasis Z2 XXZ N=8") {
		CompareXXZ<8> test(1.0);
		test.Test();
	}
	SECTION("TIBasis Z2 XXZ N=10") {
		CompareXXZ<10> test(1.0);
		test.Test();
	}
	SECTION("TIBasis Z2 XXZ N=12") {
		CompareXXZ<12> test(1.0);
		test.Test();
	}
}

max_stars_repo_name: chaeyeunpark/ExactDiagonalization

max_issues_repo_name: chaeyeunpark/ExactDiagonalization

max_forks_repo_name: chaeyeunpark/ExactDiagonalization


text:
//  test_duration.cpp  ----------------------------------------------------------//

//  Copyright 2009 Vicente J. Botet Escriba

//  Distributed under the Boost Software License, Version 1.0.
//  See http://www.boost.org/LICENSE_1_0.txt

#if !defined(__GNUC__)

#define min(A,B) ((A)<(B)?(A):(B))
#define max(A,B) ((A)>(B)?(A):(B))

#include <boost/chrono/chrono.hpp>

#endif